From 84d903c42e0f4654b4d93362db3d007bce4acdc6 Mon Sep 17 00:00:00 2001 From: "Devin W. Hurley" Date: Wed, 13 Jul 2022 16:29:39 -0400 Subject: [PATCH 001/111] [Security Solution] [Platform] Fix performance issue related to building alert body when large fields response is present (#135956) TL;DR: When a security rule's search response has a lot of values in the fields section, the rule could timeout while trying to build the body of the alert to be indexed. This commit fixes that. For example if a rule was querying an index with a lot of runtime fields mapped on it, those runtime fields would come back in the `fields` section of the search response. When we build the body of the alert we merge data from the `_source` and `fields` properties in the search response. From 8.0 until now we would copy every value in `fields` individually and simultaneously copy every value previously iterated over into a new instance of the alert object. We are now mutating the object instead. Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../merge_missing_fields_with_source.test.ts | 35 +- .../merge_missing_fields_with_source.ts | 4 +- .../security_and_spaces/group1/runtime.ts | 10 + .../security_solution/runtime/mappings.json | 7002 ++++++++++++++++- 4 files changed, 7047 insertions(+), 4 deletions(-) diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.test.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.test.ts index eb21579ddea87..a5c811bc1a5c1 100644 --- a/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.test.ts +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.test.ts @@ -4,7 +4,7 @@ * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ - +import { performance } from 'perf_hooks'; import { mergeMissingFieldsWithSource } from './merge_missing_fields_with_source'; import type { SignalSourceHit } from '../../types'; import { emptyEsResult } from '../../__mocks__/empty_signal_source_hit'; @@ -294,6 +294,16 @@ describe('merge_missing_fields_with_source', () => { 'bar.foo': [], }; + const bigFields: SignalSourceHit['fields'] = [...Array(7000).keys()].reduce( + (acc, item, index) => { + return { + [`my-runtime-field-${index}`]: ['nice'], + ...acc, + }; + }, + {} + ); + test('when source is an empty array (f_[]), merged doc is empty array (f_[])"', () => { const _source: SignalSourceHit['_source'] = { 'bar.foo': [], @@ -356,6 +366,29 @@ describe('merge_missing_fields_with_source', () => { const merged = mergeMissingFieldsWithSource({ doc, ignoreFields: [] })._source; expect(merged).toEqual(_source); }); + + /** + * tests for https://github.com/elastic/kibana/issues/135963 + * This test will fail when we replace the import + * import { set } from '@elastic/safer-lodash-set'; + * to use the fp version + * import { set } from '@elastic/safer-lodash-set/fp'; + * and switch around the return inside of filteredEntries.reduce + * to be the following: + * return set(fieldsKey, valueToMerge, merged); + */ + test('when fields is big', () => { + const _source: SignalSourceHit['_source'] = { + 'bar.foo': [], + }; + const doc: SignalSourceHit = { ...emptyEsResult(), _source, fields: bigFields }; + const start = performance.now(); + // we don't care about the response just determining performance + // eslint-disable-next-line @typescript-eslint/no-unused-expressions + mergeMissingFieldsWithSource({ doc, ignoreFields: [] })._source; + const end = performance.now(); + expect(end - start).toBeLessThan(500); + }); }); }); diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.ts index 28269652ae5e8..89695f6b562b0 100644 --- a/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.ts +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/signals/source_fields_merging/strategies/merge_missing_fields_with_source.ts @@ -6,7 +6,7 @@ */ import { get } from 'lodash/fp'; -import { set } from '@elastic/safer-lodash-set/fp'; +import { set } from '@elastic/safer-lodash-set'; import type { SignalSource } from '../../types'; import { filterFieldEntries } from '../utils/filter_field_entries'; import type { FieldsType, MergeStrategyFunction } from '../types'; @@ -44,7 +44,7 @@ export const mergeMissingFieldsWithSource: MergeStrategyFunction = ({ doc, ignor const valueInMergedDocument = get(fieldsKey, merged); const valueToMerge = recursiveUnboxingFields(fieldsValue, valueInMergedDocument); - return set(fieldsKey, valueToMerge, merged); + return set(merged, fieldsKey, valueToMerge); }, { ...source } ); diff --git a/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/runtime.ts b/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/runtime.ts index e6d1ef69f0913..6c6b33d4a54e3 100644 --- a/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/runtime.ts +++ b/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/runtime.ts @@ -6,6 +6,7 @@ */ import expect from '@kbn/expect'; +import { performance } from 'perf_hooks'; import { FtrProviderContext } from '../../common/ftr_provider_context'; import { @@ -49,6 +50,15 @@ export default ({ getService }: FtrProviderContext) => { await deleteAllAlerts(supertest, log); }); + it('should execute a rule to completion and not timeout when there are a lot of runtime fields', async () => { + const rule = getRuleForSignalTesting(['runtime']); + const { id } = await createRule(supertest, log, rule); + const start = performance.now(); + await waitForRuleSuccessOrStatus(supertest, log, id); + const end = performance.now(); + expect(end - start).to.be.lessThan(10000); + }); + it('should copy normal non-runtime data set from the source index into the signals index in the same position when the target is ECS compatible', async () => { const rule = getRuleForSignalTesting(['runtime']); const { id } = await createRule(supertest, log, rule); diff --git a/x-pack/test/functional/es_archives/security_solution/runtime/mappings.json b/x-pack/test/functional/es_archives/security_solution/runtime/mappings.json index 33235d0171837..8fde854cb3b89 100644 --- a/x-pack/test/functional/es_archives/security_solution/runtime/mappings.json +++ b/x-pack/test/functional/es_archives/security_solution/runtime/mappings.json @@ -10,7 +10,7007 @@ "script": { "source": "emit(doc['host.name'].value)" } - } + }, + "my-runtime-field-6999": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6998": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6997": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6996": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6995": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6994": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6993": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6992": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6991": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6990": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6989": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6988": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6987": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6986": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6985": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6984": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6983": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6982": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6981": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6980": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6979": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6978": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6977": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6976": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6975": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6974": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6973": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6972": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6971": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6970": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6969": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6968": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6967": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6966": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6965": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6964": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6963": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6962": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6961": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6960": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6959": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6958": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6957": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6956": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6955": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6954": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6953": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6952": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6951": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6950": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6949": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6948": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6947": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6946": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6945": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6944": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6943": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6942": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6941": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6940": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6939": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6938": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6937": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6936": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6935": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6934": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6933": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6932": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6931": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6930": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6929": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6928": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6927": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6926": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6925": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6924": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6923": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6922": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6921": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6920": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6919": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6918": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6917": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6916": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6915": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6914": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6913": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6912": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6911": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6910": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6909": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6908": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6907": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6906": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6905": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6904": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6903": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6902": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6901": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6900": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6899": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6898": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6897": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6896": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6895": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6894": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6893": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6892": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6891": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6890": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6889": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6888": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6887": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6886": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6885": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6884": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6883": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6882": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6881": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6880": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6879": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6878": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6877": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6876": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6875": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6874": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6873": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6872": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6871": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6870": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6869": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6868": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6867": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6866": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6865": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6864": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6863": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6862": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6861": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6860": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6859": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6858": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6857": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6856": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6855": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6854": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6853": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6852": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6851": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6850": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6849": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6848": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6847": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6846": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6845": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6844": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6843": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6842": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6841": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6840": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6839": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6838": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6837": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6836": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6835": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6834": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6833": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6832": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6831": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6830": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6829": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6828": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6827": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6826": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6825": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6824": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6823": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6822": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6821": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6820": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6819": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6818": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6817": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6816": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6815": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6814": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6813": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6812": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6811": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6810": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6809": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6808": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6807": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6806": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6805": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6804": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6803": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6802": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6801": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6800": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6799": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6798": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6797": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6796": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6795": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6794": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6793": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6792": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6791": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6790": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6789": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6788": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6787": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6786": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6785": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6784": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6783": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6782": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6781": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6780": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6779": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6778": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6777": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6776": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6775": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6774": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6773": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6772": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6771": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6770": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6769": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6768": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6767": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6766": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6765": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6764": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6763": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6762": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6761": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6760": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6759": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6758": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6757": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6756": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6755": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6754": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6753": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6752": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6751": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6750": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6749": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6748": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6747": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6746": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6745": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6744": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6743": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6742": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6741": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6740": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6739": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6738": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6737": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6736": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6735": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6734": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6733": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6732": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6731": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6730": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6729": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6728": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6727": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6726": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6725": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6724": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6723": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6722": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6721": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6720": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6719": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6718": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6717": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6716": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6715": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6714": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6713": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6712": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6711": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6710": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6709": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6708": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6707": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6706": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6705": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6704": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6703": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6702": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6701": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6700": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6699": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6698": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6697": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6696": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6695": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6694": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6693": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6692": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6691": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6690": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6689": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6688": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6687": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6686": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6685": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6684": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6683": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6682": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6681": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6680": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6679": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6678": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6677": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6676": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6675": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6674": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6673": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6672": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6671": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6670": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6669": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6668": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6667": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6666": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6665": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6664": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6663": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6662": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6661": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6660": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6659": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6658": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6657": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6656": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6655": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6654": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6653": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6652": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6651": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6650": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6649": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6648": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6647": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6646": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6645": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6644": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6643": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6642": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6641": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6640": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6639": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6638": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6637": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6636": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6635": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6634": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6633": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6632": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6631": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6630": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6629": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6628": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6627": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6626": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6625": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6624": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6623": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6622": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6621": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6620": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6619": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6618": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6617": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6616": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6615": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6614": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6613": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6612": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6611": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6610": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6609": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6608": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6607": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6606": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6605": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6604": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6603": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6602": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6601": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6600": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6599": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6598": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6597": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6596": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6595": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6594": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6593": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6592": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6591": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6590": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6589": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6588": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6587": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6586": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6585": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6584": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6583": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6582": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6581": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6580": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6579": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6578": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6577": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6576": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6575": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6574": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6573": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6572": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6571": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6570": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6569": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6568": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6567": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6566": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6565": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6564": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6563": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6562": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6561": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6560": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6559": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6558": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6557": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6556": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6555": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6554": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6553": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6552": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6551": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6550": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6549": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6548": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6547": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6546": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6545": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6544": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6543": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6542": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6541": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6540": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6539": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6538": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6537": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6536": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6535": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6534": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6533": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6532": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6531": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6530": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6529": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6528": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6527": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6526": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6525": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6524": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6523": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6522": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6521": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6520": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6519": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6518": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6517": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6516": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6515": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6514": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6513": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6512": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6511": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6510": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6509": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6508": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6507": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6506": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6505": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6504": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6503": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6502": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6501": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6500": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6499": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6498": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6497": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6496": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6495": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6494": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6493": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6492": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6491": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6490": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6489": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6488": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6487": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6486": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6485": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6484": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6483": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6482": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6481": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6480": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6479": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6478": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6477": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6476": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6475": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6474": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6473": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6472": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6471": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6470": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6469": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6468": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6467": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6466": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6465": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6464": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6463": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6462": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6461": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6460": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6459": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6458": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6457": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6456": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6455": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6454": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6453": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6452": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6451": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6450": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6449": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6448": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6447": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6446": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6445": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6444": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6443": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6442": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6441": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6440": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6439": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6438": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6437": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6436": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6435": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6434": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6433": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6432": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6431": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6430": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6429": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6428": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6427": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6426": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6425": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6424": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6423": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6422": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6421": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6420": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6419": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6418": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6417": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6416": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6415": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6414": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6413": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6412": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6411": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6410": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6409": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6408": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6407": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6406": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6405": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6404": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6403": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6402": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6401": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6400": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6399": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6398": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6397": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6396": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6395": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6394": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6393": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6392": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6391": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6390": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6389": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6388": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6387": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6386": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6385": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6384": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6383": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6382": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6381": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6380": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6379": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6378": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6377": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6376": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6375": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6374": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6373": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6372": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6371": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6370": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6369": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6368": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6367": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6366": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6365": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6364": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6363": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6362": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6361": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6360": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6359": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6358": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6357": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6356": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6355": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6354": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6353": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6352": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6351": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6350": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6349": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6348": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6347": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6346": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6345": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6344": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6343": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6342": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6341": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6340": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6339": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6338": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6337": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6336": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6335": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6334": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6333": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6332": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6331": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6330": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6329": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6328": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6327": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6326": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6325": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6324": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6323": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6322": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6321": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6320": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6319": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6318": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6317": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6316": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6315": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6314": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6313": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6312": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6311": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6310": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6309": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6308": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6307": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6306": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6305": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6304": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6303": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6302": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6301": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6300": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6299": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6298": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6297": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6296": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6295": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6294": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6293": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6292": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6291": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6290": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6289": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6288": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6287": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6286": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6285": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6284": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6283": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6282": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6281": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6280": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6279": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6278": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6277": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6276": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6275": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6274": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6273": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6272": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6271": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6270": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6269": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6268": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6267": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6266": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6265": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6264": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6263": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6262": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6261": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6260": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6259": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6258": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6257": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6256": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6255": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6254": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6253": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6252": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6251": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6250": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6249": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6248": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6247": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6246": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6245": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6244": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6243": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6242": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6241": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6240": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6239": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6238": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6237": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6236": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6235": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6234": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6233": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6232": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6231": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6230": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6229": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6228": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6227": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6226": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6225": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6224": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6223": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6222": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6221": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6220": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6219": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6218": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6217": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6216": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6215": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6214": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6213": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6212": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6211": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6210": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6209": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6208": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6207": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6206": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6205": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6204": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6203": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6202": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6201": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6200": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6199": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6198": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6197": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6196": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6195": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6194": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6193": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6192": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6191": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6190": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6189": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6188": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6187": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6186": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6185": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6184": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6183": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6182": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6181": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6180": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6179": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6178": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6177": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6176": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6175": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6174": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6173": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6172": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6171": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6170": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6169": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6168": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6167": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6166": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6165": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6164": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6163": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6162": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6161": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6160": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6159": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6158": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6157": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6156": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6155": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6154": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6153": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6152": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6151": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6150": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6149": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6148": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6147": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6146": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6145": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6144": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6143": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6142": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6141": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6140": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6139": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6138": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6137": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6136": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6135": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6134": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6133": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6132": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6131": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6130": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6129": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6128": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6127": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6126": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6125": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6124": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6123": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6122": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6121": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6120": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6119": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6118": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6117": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6116": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6115": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6114": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6113": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6112": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6111": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6110": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6109": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6108": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6107": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6106": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6105": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6104": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6103": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6102": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6101": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6100": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6099": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6098": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6097": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6096": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6095": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6094": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6093": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6092": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6091": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6090": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6089": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6088": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6087": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6086": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6085": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6084": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6083": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6082": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6081": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6080": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6079": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6078": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6077": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6076": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6075": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6074": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6073": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6072": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6071": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6070": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6069": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6068": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6067": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6066": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6065": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6064": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6063": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6062": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6061": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6060": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6059": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6058": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6057": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6056": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6055": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6054": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6053": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6052": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6051": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6050": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6049": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6048": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6047": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6046": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6045": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6044": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6043": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6042": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6041": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6040": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6039": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6038": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6037": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6036": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6035": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6034": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6033": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6032": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6031": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6030": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6029": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6028": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6027": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6026": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6025": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6024": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6023": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6022": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6021": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6020": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6019": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6018": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6017": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6016": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6015": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6014": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6013": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6012": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6011": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6010": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6009": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6008": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6007": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6006": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6005": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6004": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6003": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6002": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6001": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6000": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5999": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5998": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5997": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5996": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5995": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5994": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5993": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5992": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5991": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5990": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5989": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5988": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5987": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5986": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5985": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5984": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5983": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5982": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5981": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5980": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5979": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5978": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5977": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5976": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5975": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5974": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5973": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5972": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5971": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5970": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5969": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5968": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5967": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5966": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5965": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5964": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5963": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5962": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5961": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5960": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5959": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5958": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5957": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5956": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5955": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5954": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5953": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5952": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5951": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5950": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5949": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5948": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5947": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5946": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5945": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5944": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5943": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5942": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5941": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5940": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5939": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5938": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5937": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5936": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5935": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5934": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5933": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5932": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5931": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5930": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5929": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5928": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5927": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5926": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5925": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5924": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5923": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5922": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5921": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5920": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5919": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5918": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5917": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5916": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5915": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5914": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5913": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5912": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5911": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5910": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5909": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5908": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5907": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5906": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5905": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5904": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5903": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5902": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5901": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5900": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5899": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5898": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5897": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5896": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5895": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5894": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5893": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5892": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5891": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5890": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5889": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5888": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5887": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5886": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5885": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5884": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5883": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5882": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5881": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5880": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5879": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5878": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5877": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5876": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5875": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5874": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5873": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5872": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5871": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5870": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5869": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5868": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5867": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5866": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5865": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5864": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5863": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5862": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5861": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5860": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5859": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5858": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5857": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5856": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5855": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5854": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5853": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5852": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5851": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5850": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5849": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5848": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5847": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5846": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5845": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5844": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5843": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5842": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5841": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5840": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5839": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5838": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5837": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5836": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5835": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5834": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5833": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5832": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5831": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5830": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5829": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5828": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5827": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5826": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5825": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5824": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5823": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5822": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5821": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5820": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5819": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5818": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5817": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5816": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5815": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5814": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5813": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5812": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5811": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5810": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5809": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5808": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5807": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5806": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5805": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5804": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5803": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5802": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5801": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5800": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5799": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5798": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5797": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5796": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5795": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5794": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5793": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5792": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5791": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5790": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5789": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5788": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5787": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5786": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5785": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5784": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5783": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5782": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5781": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5780": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5779": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5778": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5777": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5776": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5775": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5774": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5773": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5772": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5771": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5770": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5769": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5768": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5767": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5766": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5765": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5764": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5763": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5762": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5761": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5760": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5759": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5758": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5757": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5756": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5755": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5754": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5753": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5752": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5751": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5750": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5749": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5748": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5747": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5746": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5745": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5744": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5743": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5742": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5741": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5740": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5739": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5738": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5737": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5736": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5735": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5734": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5733": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5732": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5731": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5730": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5729": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5728": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5727": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5726": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5725": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5724": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5723": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5722": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5721": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5720": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5719": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5718": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5717": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5716": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5715": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5714": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5713": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5712": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5711": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5710": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5709": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5708": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5707": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5706": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5705": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5704": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5703": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5702": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5701": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5700": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5699": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5698": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5697": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5696": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5695": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5694": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5693": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5692": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5691": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5690": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5689": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5688": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5687": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5686": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5685": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5684": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5683": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5682": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5681": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5680": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5679": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5678": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5677": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5676": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5675": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5674": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5673": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5672": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5671": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5670": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5669": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5668": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5667": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5666": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5665": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5664": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5663": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5662": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5661": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5660": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5659": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5658": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5657": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5656": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5655": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5654": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5653": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5652": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5651": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5650": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5649": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5648": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5647": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5646": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5645": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5644": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5643": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5642": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5641": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5640": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5639": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5638": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5637": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5636": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5635": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5634": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5633": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5632": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5631": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5630": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5629": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5628": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5627": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5626": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5625": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5624": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5623": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5622": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5621": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5620": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5619": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5618": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5617": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5616": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5615": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5614": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5613": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5612": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5611": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5610": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5609": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5608": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5607": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5606": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5605": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5604": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5603": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5602": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5601": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5600": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5599": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5598": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5597": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5596": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5595": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5594": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5593": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5592": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5591": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5590": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5589": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5588": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5587": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5586": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5585": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5584": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5583": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5582": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5581": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5580": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5579": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5578": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5577": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5576": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5575": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5574": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5573": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5572": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5571": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5570": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5569": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5568": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5567": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5566": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5565": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5564": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5563": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5562": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5561": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5560": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5559": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5558": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5557": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5556": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5555": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5554": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5553": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5552": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5551": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5550": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5549": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5548": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5547": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5546": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5545": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5544": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5543": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5542": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5541": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5540": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5539": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5538": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5537": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5536": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5535": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5534": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5533": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5532": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5531": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5530": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5529": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5528": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5527": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5526": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5525": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5524": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5523": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5522": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5521": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5520": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5519": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5518": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5517": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5516": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5515": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5514": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5513": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5512": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5511": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5510": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5509": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5508": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5507": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5506": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5505": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5504": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5503": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5502": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5501": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5500": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5499": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5498": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5497": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5496": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5495": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5494": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5493": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5492": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5491": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5490": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5489": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5488": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5487": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5486": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5485": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5484": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5483": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5482": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5481": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5480": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5479": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5478": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5477": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5476": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5475": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5474": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5473": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5472": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5471": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5470": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5469": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5468": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5467": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5466": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5465": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5464": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5463": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5462": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5461": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5460": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5459": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5458": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5457": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5456": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5455": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5454": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5453": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5452": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5451": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5450": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5449": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5448": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5447": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5446": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5445": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5444": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5443": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5442": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5441": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5440": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5439": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5438": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5437": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5436": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5435": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5434": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5433": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5432": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5431": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5430": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5429": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5428": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5427": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5426": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5425": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5424": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5423": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5422": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5421": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5420": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5419": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5418": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5417": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5416": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5415": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5414": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5413": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5412": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5411": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5410": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5409": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5408": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5407": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5406": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5405": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5404": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5403": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5402": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5401": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5400": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5399": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5398": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5397": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5396": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5395": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5394": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5393": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5392": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5391": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5390": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5389": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5388": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5387": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5386": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5385": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5384": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5383": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5382": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5381": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5380": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5379": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5378": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5377": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5376": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5375": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5374": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5373": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5372": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5371": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5370": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5369": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5368": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5367": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5366": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5365": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5364": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5363": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5362": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5361": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5360": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5359": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5358": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5357": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5356": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5355": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5354": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5353": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5352": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5351": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5350": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5349": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5348": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5347": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5346": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5345": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5344": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5343": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5342": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5341": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5340": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5339": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5338": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5337": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5336": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5335": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5334": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5333": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5332": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5331": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5330": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5329": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5328": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5327": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5326": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5325": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5324": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5323": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5322": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5321": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5320": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5319": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5318": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5317": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5316": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5315": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5314": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5313": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5312": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5311": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5310": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5309": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5308": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5307": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5306": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5305": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5304": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5303": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5302": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5301": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5300": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5299": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5298": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5297": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5296": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5295": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5294": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5293": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5292": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5291": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5290": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5289": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5288": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5287": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5286": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5285": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5284": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5283": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5282": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5281": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5280": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5279": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5278": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5277": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5276": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5275": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5274": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5273": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5272": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5271": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5270": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5269": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5268": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5267": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5266": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5265": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5264": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5263": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5262": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5261": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5260": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5259": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5258": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5257": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5256": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5255": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5254": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5253": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5252": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5251": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5250": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5249": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5248": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5247": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5246": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5245": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5244": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5243": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5242": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5241": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5240": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5239": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5238": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5237": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5236": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5235": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5234": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5233": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5232": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5231": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5230": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5229": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5228": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5227": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5226": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5225": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5224": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5223": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5222": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5221": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5220": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5219": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5218": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5217": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5216": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5215": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5214": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5213": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5212": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5211": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5210": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5209": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5208": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5207": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5206": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5205": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5204": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5203": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5202": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5201": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5200": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5199": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5198": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5197": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5196": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5195": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5194": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5193": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5192": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5191": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5190": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5189": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5188": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5187": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5186": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5185": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5184": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5183": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5182": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5181": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5180": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5179": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5178": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5177": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5176": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5175": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5174": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5173": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5172": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5171": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5170": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5169": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5168": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5167": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5166": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5165": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5164": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5163": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5162": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5161": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5160": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5159": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5158": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5157": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5156": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5155": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5154": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5153": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5152": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5151": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5150": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5149": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5148": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5147": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5146": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5145": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5144": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5143": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5142": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5141": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5140": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5139": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5138": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5137": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5136": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5135": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5134": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5133": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5132": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5131": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5130": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5129": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5128": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5127": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5126": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5125": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5124": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5123": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5122": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5121": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5120": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5119": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5118": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5117": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5116": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5115": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5114": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5113": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5112": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5111": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5110": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5109": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5108": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5107": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5106": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5105": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5104": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5103": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5102": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5101": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5100": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5099": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5098": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5097": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5096": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5095": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5094": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5093": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5092": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5091": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5090": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5089": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5088": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5087": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5086": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5085": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5084": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5083": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5082": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5081": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5080": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5079": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5078": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5077": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5076": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5075": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5074": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5073": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5072": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5071": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5070": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5069": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5068": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5067": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5066": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5065": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5064": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5063": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5062": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5061": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5060": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5059": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5058": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5057": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5056": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5055": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5054": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5053": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5052": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5051": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5050": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5049": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5048": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5047": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5046": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5045": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5044": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5043": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5042": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5041": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5040": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5039": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5038": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5037": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5036": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5035": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5034": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5033": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5032": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5031": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5030": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5029": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5028": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5027": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5026": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5025": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5024": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5023": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5022": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5021": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5020": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5019": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5018": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5017": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5016": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5015": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5014": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5013": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5012": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5011": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5010": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5009": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5008": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5007": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5006": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5005": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5004": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5003": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5002": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5001": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5000": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4999": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4998": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4997": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4996": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4995": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4994": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4993": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4992": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4991": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4990": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4989": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4988": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4987": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4986": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4985": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4984": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4983": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4982": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4981": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4980": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4979": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4978": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4977": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4976": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4975": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4974": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4973": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4972": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4971": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4970": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4969": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4968": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4967": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4966": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4965": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4964": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4963": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4962": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4961": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4960": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4959": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4958": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4957": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4956": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4955": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4954": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4953": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4952": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4951": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4950": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4949": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4948": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4947": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4946": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4945": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4944": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4943": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4942": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4941": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4940": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4939": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4938": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4937": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4936": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4935": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4934": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4933": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4932": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4931": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4930": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4929": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4928": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4927": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4926": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4925": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4924": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4923": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4922": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4921": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4920": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4919": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4918": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4917": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4916": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4915": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4914": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4913": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4912": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4911": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4910": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4909": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4908": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4907": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4906": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4905": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4904": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4903": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4902": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4901": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4900": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4899": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4898": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4897": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4896": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4895": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4894": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4893": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4892": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4891": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4890": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4889": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4888": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4887": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4886": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4885": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4884": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4883": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4882": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4881": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4880": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4879": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4878": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4877": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4876": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4875": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4874": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4873": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4872": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4871": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4870": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4869": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4868": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4867": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4866": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4865": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4864": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4863": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4862": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4861": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4860": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4859": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4858": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4857": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4856": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4855": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4854": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4853": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4852": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4851": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4850": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4849": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4848": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4847": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4846": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4845": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4844": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4843": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4842": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4841": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4840": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4839": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4838": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4837": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4836": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4835": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4834": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4833": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4832": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4831": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4830": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4829": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4828": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4827": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4826": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4825": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4824": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4823": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4822": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4821": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4820": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4819": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4818": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4817": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4816": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4815": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4814": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4813": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4812": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4811": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4810": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4809": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4808": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4807": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4806": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4805": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4804": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4803": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4802": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4801": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4800": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4799": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4798": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4797": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4796": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4795": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4794": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4793": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4792": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4791": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4790": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4789": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4788": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4787": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4786": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4785": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4784": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4783": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4782": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4781": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4780": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4779": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4778": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4777": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4776": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4775": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4774": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4773": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4772": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4771": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4770": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4769": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4768": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4767": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4766": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4765": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4764": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4763": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4762": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4761": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4760": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4759": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4758": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4757": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4756": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4755": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4754": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4753": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4752": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4751": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4750": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4749": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4748": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4747": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4746": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4745": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4744": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4743": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4742": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4741": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4740": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4739": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4738": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4737": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4736": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4735": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4734": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4733": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4732": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4731": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4730": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4729": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4728": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4727": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4726": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4725": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4724": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4723": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4722": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4721": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4720": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4719": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4718": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4717": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4716": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4715": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4714": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4713": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4712": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4711": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4710": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4709": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4708": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4707": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4706": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4705": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4704": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4703": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4702": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4701": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4700": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4699": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4698": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4697": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4696": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4695": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4694": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4693": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4692": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4691": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4690": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4689": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4688": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4687": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4686": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4685": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4684": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4683": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4682": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4681": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4680": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4679": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4678": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4677": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4676": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4675": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4674": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4673": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4672": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4671": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4670": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4669": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4668": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4667": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4666": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4665": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4664": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4663": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4662": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4661": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4660": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4659": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4658": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4657": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4656": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4655": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4654": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4653": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4652": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4651": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4650": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4649": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4648": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4647": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4646": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4645": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4644": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4643": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4642": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4641": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4640": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4639": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4638": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4637": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4636": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4635": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4634": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4633": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4632": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4631": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4630": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4629": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4628": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4627": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4626": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4625": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4624": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4623": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4622": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4621": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4620": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4619": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4618": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4617": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4616": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4615": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4614": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4613": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4612": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4611": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4610": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4609": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4608": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4607": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4606": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4605": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4604": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4603": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4602": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4601": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4600": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4599": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4598": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4597": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4596": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4595": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4594": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4593": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4592": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4591": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4590": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4589": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4588": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4587": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4586": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4585": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4584": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4583": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4582": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4581": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4580": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4579": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4578": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4577": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4576": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4575": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4574": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4573": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4572": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4571": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4570": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4569": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4568": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4567": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4566": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4565": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4564": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4563": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4562": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4561": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4560": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4559": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4558": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4557": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4556": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4555": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4554": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4553": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4552": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4551": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4550": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4549": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4548": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4547": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4546": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4545": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4544": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4543": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4542": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4541": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4540": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4539": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4538": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4537": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4536": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4535": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4534": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4533": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4532": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4531": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4530": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4529": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4528": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4527": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4526": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4525": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4524": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4523": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4522": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4521": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4520": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4519": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4518": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4517": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4516": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4515": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4514": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4513": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4512": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4511": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4510": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4509": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4508": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4507": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4506": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4505": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4504": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4503": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4502": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4501": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4500": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4499": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4498": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4497": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4496": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4495": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4494": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4493": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4492": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4491": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4490": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4489": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4488": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4487": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4486": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4485": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4484": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4483": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4482": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4481": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4480": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4479": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4478": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4477": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4476": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4475": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4474": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4473": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4472": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4471": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4470": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4469": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4468": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4467": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4466": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4465": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4464": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4463": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4462": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4461": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4460": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4459": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4458": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4457": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4456": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4455": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4454": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4453": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4452": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4451": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4450": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4449": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4448": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4447": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4446": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4445": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4444": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4443": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4442": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4441": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4440": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4439": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4438": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4437": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4436": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4435": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4434": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4433": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4432": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4431": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4430": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4429": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4428": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4427": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4426": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4425": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4424": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4423": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4422": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4421": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4420": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4419": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4418": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4417": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4416": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4415": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4414": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4413": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4412": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4411": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4410": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4409": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4408": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4407": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4406": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4405": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4404": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4403": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4402": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4401": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4400": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4399": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4398": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4397": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4396": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4395": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4394": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4393": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4392": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4391": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4390": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4389": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4388": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4387": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4386": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4385": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4384": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4383": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4382": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4381": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4380": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4379": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4378": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4377": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4376": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4375": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4374": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4373": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4372": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4371": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4370": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4369": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4368": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4367": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4366": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4365": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4364": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4363": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4362": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4361": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4360": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4359": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4358": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4357": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4356": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4355": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4354": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4353": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4352": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4351": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4350": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4349": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4348": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4347": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4346": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4345": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4344": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4343": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4342": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4341": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4340": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4339": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4338": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4337": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4336": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4335": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4334": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4333": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4332": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4331": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4330": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4329": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4328": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4327": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4326": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4325": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4324": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4323": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4322": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4321": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4320": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4319": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4318": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4317": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4316": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4315": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4314": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4313": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4312": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4311": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4310": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4309": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4308": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4307": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4306": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4305": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4304": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4303": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4302": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4301": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4300": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4299": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4298": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4297": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4296": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4295": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4294": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4293": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4292": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4291": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4290": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4289": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4288": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4287": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4286": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4285": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4284": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4283": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4282": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4281": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4280": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4279": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4278": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4277": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4276": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4275": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4274": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4273": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4272": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4271": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4270": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4269": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4268": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4267": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4266": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4265": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4264": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4263": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4262": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4261": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4260": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4259": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4258": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4257": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4256": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4255": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4254": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4253": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4252": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4251": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4250": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4249": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4248": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4247": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4246": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4245": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4244": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4243": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4242": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4241": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4240": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4239": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4238": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4237": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4236": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4235": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4234": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4233": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4232": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4231": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4230": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4229": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4228": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4227": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4226": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4225": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4224": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4223": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4222": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4221": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4220": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4219": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4218": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4217": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4216": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4215": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4214": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4213": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4212": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4211": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4210": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4209": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4208": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4207": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4206": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4205": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4204": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4203": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4202": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4201": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4200": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4199": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4198": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4197": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4196": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4195": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4194": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4193": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4192": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4191": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4190": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4189": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4188": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4187": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4186": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4185": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4184": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4183": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4182": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4181": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4180": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4179": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4178": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4177": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4176": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4175": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4174": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4173": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4172": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4171": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4170": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4169": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4168": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4167": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4166": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4165": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4164": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4163": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4162": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4161": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4160": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4159": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4158": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4157": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4156": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4155": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4154": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4153": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4152": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4151": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4150": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4149": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4148": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4147": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4146": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4145": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4144": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4143": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4142": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4141": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4140": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4139": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4138": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4137": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4136": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4135": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4134": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4133": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4132": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4131": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4130": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4129": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4128": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4127": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4126": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4125": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4124": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4123": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4122": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4121": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4120": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4119": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4118": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4117": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4116": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4115": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4114": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4113": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4112": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4111": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4110": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4109": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4108": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4107": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4106": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4105": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4104": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4103": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4102": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4101": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4100": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4099": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4098": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4097": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4096": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4095": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4094": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4093": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4092": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4091": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4090": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4089": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4088": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4087": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4086": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4085": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4084": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4083": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4082": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4081": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4080": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4079": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4078": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4077": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4076": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4075": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4074": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4073": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4072": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4071": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4070": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4069": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4068": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4067": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4066": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4065": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4064": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4063": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4062": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4061": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4060": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4059": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4058": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4057": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4056": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4055": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4054": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4053": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4052": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4051": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4050": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4049": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4048": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4047": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4046": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4045": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4044": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4043": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4042": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4041": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4040": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4039": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4038": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4037": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4036": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4035": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4034": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4033": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4032": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4031": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4030": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4029": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4028": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4027": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4026": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4025": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4024": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4023": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4022": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4021": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4020": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4019": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4018": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4017": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4016": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4015": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4014": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4013": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4012": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4011": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4010": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4009": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4008": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4007": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4006": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4005": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4004": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4003": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4002": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4001": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4000": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3999": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3998": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3997": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3996": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3995": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3994": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3993": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3992": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3991": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3990": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3989": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3988": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3987": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3986": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3985": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3984": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3983": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3982": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3981": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3980": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3979": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3978": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3977": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3976": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3975": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3974": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3973": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3972": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3971": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3970": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3969": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3968": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3967": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3966": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3965": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3964": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3963": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3962": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3961": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3960": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3959": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3958": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3957": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3956": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3955": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3954": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3953": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3952": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3951": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3950": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3949": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3948": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3947": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3946": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3945": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3944": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3943": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3942": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3941": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3940": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3939": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3938": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3937": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3936": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3935": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3934": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3933": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3932": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3931": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3930": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3929": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3928": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3927": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3926": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3925": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3924": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3923": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3922": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3921": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3920": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3919": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3918": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3917": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3916": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3915": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3914": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3913": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3912": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3911": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3910": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3909": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3908": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3907": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3906": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3905": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3904": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3903": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3902": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3901": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3900": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3899": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3898": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3897": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3896": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3895": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3894": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3893": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3892": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3891": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3890": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3889": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3888": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3887": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3886": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3885": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3884": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3883": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3882": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3881": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3880": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3879": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3878": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3877": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3876": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3875": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3874": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3873": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3872": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3871": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3870": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3869": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3868": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3867": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3866": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3865": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3864": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3863": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3862": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3861": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3860": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3859": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3858": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3857": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3856": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3855": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3854": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3853": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3852": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3851": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3850": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3849": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3848": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3847": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3846": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3845": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3844": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3843": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3842": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3841": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3840": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3839": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3838": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3837": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3836": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3835": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3834": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3833": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3832": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3831": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3830": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3829": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3828": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3827": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3826": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3825": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3824": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3823": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3822": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3821": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3820": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3819": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3818": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3817": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3816": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3815": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3814": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3813": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3812": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3811": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3810": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3809": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3808": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3807": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3806": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3805": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3804": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3803": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3802": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3801": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3800": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3799": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3798": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3797": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3796": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3795": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3794": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3793": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3792": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3791": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3790": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3789": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3788": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3787": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3786": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3785": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3784": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3783": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3782": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3781": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3780": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3779": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3778": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3777": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3776": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3775": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3774": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3773": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3772": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3771": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3770": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3769": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3768": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3767": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3766": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3765": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3764": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3763": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3762": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3761": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3760": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3759": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3758": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3757": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3756": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3755": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3754": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3753": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3752": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3751": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3750": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3749": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3748": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3747": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3746": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3745": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3744": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3743": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3742": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3741": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3740": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3739": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3738": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3737": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3736": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3735": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3734": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3733": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3732": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3731": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3730": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3729": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3728": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3727": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3726": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3725": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3724": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3723": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3722": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3721": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3720": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3719": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3718": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3717": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3716": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3715": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3714": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3713": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3712": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3711": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3710": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3709": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3708": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3707": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3706": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3705": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3704": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3703": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3702": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3701": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3700": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3699": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3698": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3697": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3696": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3695": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3694": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3693": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3692": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3691": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3690": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3689": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3688": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3687": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3686": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3685": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3684": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3683": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3682": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3681": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3680": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3679": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3678": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3677": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3676": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3675": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3674": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3673": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3672": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3671": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3670": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3669": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3668": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3667": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3666": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3665": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3664": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3663": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3662": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3661": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3660": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3659": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3658": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3657": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3656": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3655": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3654": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3653": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3652": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3651": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3650": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3649": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3648": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3647": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3646": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3645": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3644": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3643": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3642": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3641": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3640": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3639": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3638": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3637": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3636": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3635": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3634": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3633": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3632": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3631": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3630": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3629": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3628": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3627": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3626": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3625": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3624": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3623": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3622": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3621": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3620": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3619": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3618": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3617": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3616": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3615": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3614": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3613": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3612": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3611": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3610": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3609": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3608": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3607": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3606": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3605": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3604": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3603": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3602": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3601": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3600": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3599": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3598": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3597": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3596": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3595": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3594": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3593": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3592": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3591": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3590": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3589": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3588": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3587": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3586": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3585": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3584": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3583": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3582": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3581": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3580": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3579": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3578": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3577": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3576": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3575": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3574": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3573": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3572": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3571": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3570": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3569": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3568": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3567": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3566": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3565": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3564": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3563": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3562": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3561": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3560": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3559": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3558": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3557": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3556": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3555": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3554": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3553": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3552": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3551": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3550": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3549": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3548": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3547": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3546": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3545": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3544": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3543": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3542": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3541": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3540": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3539": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3538": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3537": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3536": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3535": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3534": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3533": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3532": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3531": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3530": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3529": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3528": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3527": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3526": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3525": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3524": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3523": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3522": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3521": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3520": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3519": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3518": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3517": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3516": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3515": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3514": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3513": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3512": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3511": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3510": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3509": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3508": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3507": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3506": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3505": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3504": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3503": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3502": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3501": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3500": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3499": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3498": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3497": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3496": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3495": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3494": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3493": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3492": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3491": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3490": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3489": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3488": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3487": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3486": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3485": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3484": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3483": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3482": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3481": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3480": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3479": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3478": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3477": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3476": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3475": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3474": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3473": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3472": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3471": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3470": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3469": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3468": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3467": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3466": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3465": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3464": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3463": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3462": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3461": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3460": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3459": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3458": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3457": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3456": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3455": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3454": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3453": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3452": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3451": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3450": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3449": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3448": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3447": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3446": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3445": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3444": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3443": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3442": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3441": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3440": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3439": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3438": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3437": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3436": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3435": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3434": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3433": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3432": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3431": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3430": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3429": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3428": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3427": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3426": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3425": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3424": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3423": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3422": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3421": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3420": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3419": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3418": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3417": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3416": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3415": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3414": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3413": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3412": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3411": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3410": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3409": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3408": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3407": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3406": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3405": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3404": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3403": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3402": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3401": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3400": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3399": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3398": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3397": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3396": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3395": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3394": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3393": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3392": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3391": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3390": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3389": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3388": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3387": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3386": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3385": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3384": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3383": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3382": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3381": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3380": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3379": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3378": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3377": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3376": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3375": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3374": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3373": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3372": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3371": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3370": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3369": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3368": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3367": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3366": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3365": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3364": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3363": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3362": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3361": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3360": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3359": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3358": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3357": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3356": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3355": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3354": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3353": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3352": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3351": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3350": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3349": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3348": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3347": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3346": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3345": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3344": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3343": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3342": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3341": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3340": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3339": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3338": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3337": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3336": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3335": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3334": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3333": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3332": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3331": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3330": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3329": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3328": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3327": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3326": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3325": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3324": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3323": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3322": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3321": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3320": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3319": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3318": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3317": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3316": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3315": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3314": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3313": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3312": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3311": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3310": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3309": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3308": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3307": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3306": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3305": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3304": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3303": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3302": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3301": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3300": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3299": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3298": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3297": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3296": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3295": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3294": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3293": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3292": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3291": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3290": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3289": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3288": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3287": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3286": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3285": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3284": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3283": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3282": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3281": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3280": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3279": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3278": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3277": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3276": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3275": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3274": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3273": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3272": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3271": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3270": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3269": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3268": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3267": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3266": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3265": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3264": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3263": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3262": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3261": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3260": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3259": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3258": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3257": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3256": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3255": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3254": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3253": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3252": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3251": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3250": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3249": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3248": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3247": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3246": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3245": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3244": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3243": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3242": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3241": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3240": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3239": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3238": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3237": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3236": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3235": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3234": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3233": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3232": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3231": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3230": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3229": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3228": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3227": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3226": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3225": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3224": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3223": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3222": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3221": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3220": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3219": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3218": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3217": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3216": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3215": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3214": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3213": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3212": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3211": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3210": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3209": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3208": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3207": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3206": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3205": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3204": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3203": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3202": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3201": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3200": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3199": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3198": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3197": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3196": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3195": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3194": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3193": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3192": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3191": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3190": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3189": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3188": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3187": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3186": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3185": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3184": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3183": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3182": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3181": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3180": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3179": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3178": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3177": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3176": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3175": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3174": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3173": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3172": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3171": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3170": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3169": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3168": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3167": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3166": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3165": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3164": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3163": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3162": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3161": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3160": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3159": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3158": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3157": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3156": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3155": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3154": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3153": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3152": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3151": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3150": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3149": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3148": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3147": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3146": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3145": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3144": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3143": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3142": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3141": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3140": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3139": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3138": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3137": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3136": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3135": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3134": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3133": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3132": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3131": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3130": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3129": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3128": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3127": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3126": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3125": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3124": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3123": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3122": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3121": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3120": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3119": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3118": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3117": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3116": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3115": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3114": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3113": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3112": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3111": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3110": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3109": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3108": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3107": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3106": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3105": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3104": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3103": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3102": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3101": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3100": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3099": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3098": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3097": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3096": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3095": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3094": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3093": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3092": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3091": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3090": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3089": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3088": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3087": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3086": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3085": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3084": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3083": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3082": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3081": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3080": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3079": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3078": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3077": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3076": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3075": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3074": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3073": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3072": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3071": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3070": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3069": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3068": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3067": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3066": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3065": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3064": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3063": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3062": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3061": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3060": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3059": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3058": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3057": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3056": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3055": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3054": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3053": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3052": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3051": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3050": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3049": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3048": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3047": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3046": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3045": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3044": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3043": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3042": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3041": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3040": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3039": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3038": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3037": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3036": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3035": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3034": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3033": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3032": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3031": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3030": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3029": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3028": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3027": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3026": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3025": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3024": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3023": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3022": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3021": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3020": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3019": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3018": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3017": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3016": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3015": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3014": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3013": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3012": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3011": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3010": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3009": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3008": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3007": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3006": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3005": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3004": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3003": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3002": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3001": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3000": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2999": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2998": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2997": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2996": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2995": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2994": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2993": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2992": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2991": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2990": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2989": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2988": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2987": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2986": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2985": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2984": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2983": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2982": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2981": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2980": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2979": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2978": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2977": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2976": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2975": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2974": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2973": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2972": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2971": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2970": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2969": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2968": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2967": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2966": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2965": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2964": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2963": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2962": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2961": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2960": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2959": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2958": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2957": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2956": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2955": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2954": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2953": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2952": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2951": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2950": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2949": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2948": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2947": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2946": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2945": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2944": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2943": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2942": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2941": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2940": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2939": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2938": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2937": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2936": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2935": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2934": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2933": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2932": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2931": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2930": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2929": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2928": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2927": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2926": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2925": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2924": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2923": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2922": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2921": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2920": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2919": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2918": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2917": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2916": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2915": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2914": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2913": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2912": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2911": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2910": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2909": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2908": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2907": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2906": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2905": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2904": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2903": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2902": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2901": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2900": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2899": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2898": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2897": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2896": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2895": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2894": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2893": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2892": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2891": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2890": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2889": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2888": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2887": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2886": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2885": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2884": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2883": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2882": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2881": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2880": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2879": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2878": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2877": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2876": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2875": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2874": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2873": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2872": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2871": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2870": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2869": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2868": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2867": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2866": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2865": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2864": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2863": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2862": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2861": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2860": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2859": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2858": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2857": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2856": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2855": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2854": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2853": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2852": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2851": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2850": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2849": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2848": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2847": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2846": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2845": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2844": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2843": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2842": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2841": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2840": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2839": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2838": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2837": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2836": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2835": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2834": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2833": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2832": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2831": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2830": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2829": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2828": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2827": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2826": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2825": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2824": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2823": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2822": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2821": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2820": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2819": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2818": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2817": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2816": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2815": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2814": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2813": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2812": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2811": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2810": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2809": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2808": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2807": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2806": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2805": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2804": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2803": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2802": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2801": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2800": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2799": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2798": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2797": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2796": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2795": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2794": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2793": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2792": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2791": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2790": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2789": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2788": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2787": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2786": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2785": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2784": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2783": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2782": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2781": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2780": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2779": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2778": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2777": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2776": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2775": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2774": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2773": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2772": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2771": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2770": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2769": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2768": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2767": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2766": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2765": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2764": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2763": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2762": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2761": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2760": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2759": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2758": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2757": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2756": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2755": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2754": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2753": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2752": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2751": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2750": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2749": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2748": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2747": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2746": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2745": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2744": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2743": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2742": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2741": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2740": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2739": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2738": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2737": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2736": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2735": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2734": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2733": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2732": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2731": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2730": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2729": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2728": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2727": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2726": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2725": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2724": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2723": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2722": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2721": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2720": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2719": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2718": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2717": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2716": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2715": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2714": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2713": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2712": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2711": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2710": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2709": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2708": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2707": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2706": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2705": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2704": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2703": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2702": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2701": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2700": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2699": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2698": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2697": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2696": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2695": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2694": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2693": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2692": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2691": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2690": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2689": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2688": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2687": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2686": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2685": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2684": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2683": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2682": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2681": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2680": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2679": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2678": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2677": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2676": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2675": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2674": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2673": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2672": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2671": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2670": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2669": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2668": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2667": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2666": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2665": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2664": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2663": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2662": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2661": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2660": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2659": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2658": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2657": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2656": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2655": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2654": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2653": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2652": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2651": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2650": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2649": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2648": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2647": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2646": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2645": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2644": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2643": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2642": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2641": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2640": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2639": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2638": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2637": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2636": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2635": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2634": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2633": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2632": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2631": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2630": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2629": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2628": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2627": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2626": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2625": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2624": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2623": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2622": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2621": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2620": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2619": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2618": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2617": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2616": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2615": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2614": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2613": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2612": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2611": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2610": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2609": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2608": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2607": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2606": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2605": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2604": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2603": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2602": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2601": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2600": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2599": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2598": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2597": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2596": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2595": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2594": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2593": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2592": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2591": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2590": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2589": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2588": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2587": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2586": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2585": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2584": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2583": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2582": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2581": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2580": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2579": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2578": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2577": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2576": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2575": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2574": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2573": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2572": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2571": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2570": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2569": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2568": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2567": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2566": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2565": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2564": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2563": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2562": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2561": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2560": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2559": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2558": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2557": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2556": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2555": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2554": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2553": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2552": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2551": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2550": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2549": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2548": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2547": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2546": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2545": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2544": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2543": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2542": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2541": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2540": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2539": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2538": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2537": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2536": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2535": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2534": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2533": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2532": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2531": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2530": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2529": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2528": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2527": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2526": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2525": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2524": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2523": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2522": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2521": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2520": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2519": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2518": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2517": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2516": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2515": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2514": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2513": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2512": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2511": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2510": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2509": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2508": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2507": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2506": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2505": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2504": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2503": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2502": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2501": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2500": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2499": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2498": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2497": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2496": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2495": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2494": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2493": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2492": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2491": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2490": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2489": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2488": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2487": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2486": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2485": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2484": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2483": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2482": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2481": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2480": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2479": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2478": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2477": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2476": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2475": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2474": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2473": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2472": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2471": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2470": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2469": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2468": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2467": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2466": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2465": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2464": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2463": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2462": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2461": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2460": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2459": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2458": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2457": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2456": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2455": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2454": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2453": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2452": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2451": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2450": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2449": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2448": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2447": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2446": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2445": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2444": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2443": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2442": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2441": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2440": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2439": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2438": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2437": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2436": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2435": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2434": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2433": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2432": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2431": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2430": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2429": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2428": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2427": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2426": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2425": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2424": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2423": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2422": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2421": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2420": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2419": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2418": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2417": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2416": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2415": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2414": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2413": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2412": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2411": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2410": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2409": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2408": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2407": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2406": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2405": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2404": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2403": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2402": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2401": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2400": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2399": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2398": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2397": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2396": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2395": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2394": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2393": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2392": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2391": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2390": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2389": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2388": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2387": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2386": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2385": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2384": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2383": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2382": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2381": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2380": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2379": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2378": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2377": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2376": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2375": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2374": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2373": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2372": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2371": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2370": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2369": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2368": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2367": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2366": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2365": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2364": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2363": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2362": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2361": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2360": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2359": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2358": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2357": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2356": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2355": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2354": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2353": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2352": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2351": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2350": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2349": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2348": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2347": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2346": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2345": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2344": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2343": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2342": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2341": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2340": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2339": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2338": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2337": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2336": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2335": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2334": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2333": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2332": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2331": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2330": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2329": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2328": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2327": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2326": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2325": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2324": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2323": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2322": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2321": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2320": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2319": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2318": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2317": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2316": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2315": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2314": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2313": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2312": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2311": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2310": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2309": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2308": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2307": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2306": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2305": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2304": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2303": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2302": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2301": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2300": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2299": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2298": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2297": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2296": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2295": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2294": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2293": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2292": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2291": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2290": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2289": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2288": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2287": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2286": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2285": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2284": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2283": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2282": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2281": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2280": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2279": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2278": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2277": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2276": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2275": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2274": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2273": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2272": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2271": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2270": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2269": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2268": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2267": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2266": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2265": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2264": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2263": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2262": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2261": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2260": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2259": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2258": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2257": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2256": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2255": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2254": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2253": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2252": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2251": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2250": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2249": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2248": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2247": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2246": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2245": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2244": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2243": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2242": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2241": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2240": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2239": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2238": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2237": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2236": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2235": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2234": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2233": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2232": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2231": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2230": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2229": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2228": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2227": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2226": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2225": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2224": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2223": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2222": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2221": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2220": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2219": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2218": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2217": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2216": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2215": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2214": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2213": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2212": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2211": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2210": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2209": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2208": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2207": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2206": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2205": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2204": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2203": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2202": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2201": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2200": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2199": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2198": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2197": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2196": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2195": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2194": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2193": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2192": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2191": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2190": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2189": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2188": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2187": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2186": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2185": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2184": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2183": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2182": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2181": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2180": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2179": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2178": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2177": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2176": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2175": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2174": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2173": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2172": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2171": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2170": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2169": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2168": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2167": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2166": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2165": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2164": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2163": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2162": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2161": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2160": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2159": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2158": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2157": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2156": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2155": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2154": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2153": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2152": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2151": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2150": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2149": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2148": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2147": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2146": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2145": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2144": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2143": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2142": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2141": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2140": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2139": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2138": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2137": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2136": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2135": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2134": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2133": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2132": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2131": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2130": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2129": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2128": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2127": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2126": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2125": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2124": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2123": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2122": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2121": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2120": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2119": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2118": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2117": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2116": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2115": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2114": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2113": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2112": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2111": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2110": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2109": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2108": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2107": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2106": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2105": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2104": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2103": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2102": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2101": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2100": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2099": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2098": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2097": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2096": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2095": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2094": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2093": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2092": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2091": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2090": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2089": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2088": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2087": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2086": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2085": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2084": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2083": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2082": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2081": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2080": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2079": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2078": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2077": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2076": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2075": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2074": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2073": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2072": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2071": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2070": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2069": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2068": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2067": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2066": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2065": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2064": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2063": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2062": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2061": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2060": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2059": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2058": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2057": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2056": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2055": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2054": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2053": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2052": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2051": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2050": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2049": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2048": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2047": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2046": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2045": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2044": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2043": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2042": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2041": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2040": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2039": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2038": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2037": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2036": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2035": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2034": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2033": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2032": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2031": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2030": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2029": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2028": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2027": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2026": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2025": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2024": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2023": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2022": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2021": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2020": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2019": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2018": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2017": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2016": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2015": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2014": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2013": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2012": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2011": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2010": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2009": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2008": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2007": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2006": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2005": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2004": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2003": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2002": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2001": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2000": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1999": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1998": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1997": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1996": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1995": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1994": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1993": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1992": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1991": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1990": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1989": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1988": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1987": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1986": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1985": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1984": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1983": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1982": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1981": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1980": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1979": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1978": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1977": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1976": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1975": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1974": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1973": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1972": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1971": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1970": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1969": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1968": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1967": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1966": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1965": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1964": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1963": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1962": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1961": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1960": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1959": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1958": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1957": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1956": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1955": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1954": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1953": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1952": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1951": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1950": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1949": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1948": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1947": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1946": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1945": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1944": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1943": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1942": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1941": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1940": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1939": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1938": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1937": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1936": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1935": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1934": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1933": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1932": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1931": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1930": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1929": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1928": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1927": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1926": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1925": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1924": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1923": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1922": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1921": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1920": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1919": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1918": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1917": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1916": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1915": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1914": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1913": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1912": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1911": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1910": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1909": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1908": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1907": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1906": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1905": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1904": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1903": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1902": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1901": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1900": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1899": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1898": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1897": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1896": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1895": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1894": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1893": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1892": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1891": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1890": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1889": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1888": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1887": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1886": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1885": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1884": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1883": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1882": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1881": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1880": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1879": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1878": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1877": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1876": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1875": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1874": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1873": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1872": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1871": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1870": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1869": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1868": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1867": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1866": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1865": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1864": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1863": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1862": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1861": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1860": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1859": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1858": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1857": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1856": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1855": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1854": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1853": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1852": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1851": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1850": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1849": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1848": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1847": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1846": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1845": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1844": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1843": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1842": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1841": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1840": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1839": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1838": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1837": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1836": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1835": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1834": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1833": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1832": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1831": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1830": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1829": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1828": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1827": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1826": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1825": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1824": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1823": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1822": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1821": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1820": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1819": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1818": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1817": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1816": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1815": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1814": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1813": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1812": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1811": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1810": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1809": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1808": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1807": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1806": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1805": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1804": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1803": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1802": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1801": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1800": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1799": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1798": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1797": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1796": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1795": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1794": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1793": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1792": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1791": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1790": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1789": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1788": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1787": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1786": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1785": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1784": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1783": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1782": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1781": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1780": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1779": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1778": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1777": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1776": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1775": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1774": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1773": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1772": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1771": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1770": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1769": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1768": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1767": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1766": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1765": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1764": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1763": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1762": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1761": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1760": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1759": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1758": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1757": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1756": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1755": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1754": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1753": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1752": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1751": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1750": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1749": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1748": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1747": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1746": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1745": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1744": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1743": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1742": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1741": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1740": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1739": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1738": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1737": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1736": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1735": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1734": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1733": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1732": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1731": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1730": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1729": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1728": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1727": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1726": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1725": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1724": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1723": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1722": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1721": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1720": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1719": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1718": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1717": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1716": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1715": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1714": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1713": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1712": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1711": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1710": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1709": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1708": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1707": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1706": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1705": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1704": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1703": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1702": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1701": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1700": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1699": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1698": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1697": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1696": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1695": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1694": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1693": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1692": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1691": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1690": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1689": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1688": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1687": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1686": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1685": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1684": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1683": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1682": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1681": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1680": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1679": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1678": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1677": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1676": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1675": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1674": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1673": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1672": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1671": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1670": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1669": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1668": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1667": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1666": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1665": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1664": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1663": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1662": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1661": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1660": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1659": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1658": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1657": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1656": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1655": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1654": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1653": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1652": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1651": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1650": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1649": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1648": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1647": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1646": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1645": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1644": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1643": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1642": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1641": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1640": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1639": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1638": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1637": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1636": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1635": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1634": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1633": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1632": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1631": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1630": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1629": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1628": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1627": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1626": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1625": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1624": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1623": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1622": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1621": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1620": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1619": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1618": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1617": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1616": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1615": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1614": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1613": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1612": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1611": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1610": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1609": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1608": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1607": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1606": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1605": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1604": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1603": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1602": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1601": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1600": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1599": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1598": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1597": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1596": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1595": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1594": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1593": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1592": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1591": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1590": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1589": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1588": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1587": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1586": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1585": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1584": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1583": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1582": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1581": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1580": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1579": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1578": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1577": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1576": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1575": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1574": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1573": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1572": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1571": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1570": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1569": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1568": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1567": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1566": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1565": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1564": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1563": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1562": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1561": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1560": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1559": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1558": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1557": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1556": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1555": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1554": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1553": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1552": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1551": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1550": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1549": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1548": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1547": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1546": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1545": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1544": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1543": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1542": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1541": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1540": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1539": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1538": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1537": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1536": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1535": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1534": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1533": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1532": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1531": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1530": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1529": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1528": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1527": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1526": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1525": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1524": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1523": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1522": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1521": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1520": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1519": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1518": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1517": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1516": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1515": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1514": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1513": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1512": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1511": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1510": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1509": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1508": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1507": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1506": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1505": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1504": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1503": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1502": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1501": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1500": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1499": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1498": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1497": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1496": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1495": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1494": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1493": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1492": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1491": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1490": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1489": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1488": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1487": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1486": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1485": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1484": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1483": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1482": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1481": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1480": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1479": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1478": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1477": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1476": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1475": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1474": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1473": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1472": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1471": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1470": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1469": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1468": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1467": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1466": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1465": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1464": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1463": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1462": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1461": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1460": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1459": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1458": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1457": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1456": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1455": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1454": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1453": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1452": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1451": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1450": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1449": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1448": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1447": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1446": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1445": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1444": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1443": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1442": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1441": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1440": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1439": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1438": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1437": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1436": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1435": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1434": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1433": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1432": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1431": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1430": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1429": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1428": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1427": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1426": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1425": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1424": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1423": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1422": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1421": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1420": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1419": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1418": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1417": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1416": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1415": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1414": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1413": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1412": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1411": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1410": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1409": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1408": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1407": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1406": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1405": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1404": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1403": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1402": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1401": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1400": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1399": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1398": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1397": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1396": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1395": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1394": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1393": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1392": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1391": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1390": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1389": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1388": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1387": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1386": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1385": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1384": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1383": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1382": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1381": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1380": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1379": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1378": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1377": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1376": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1375": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1374": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1373": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1372": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1371": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1370": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1369": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1368": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1367": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1366": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1365": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1364": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1363": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1362": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1361": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1360": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1359": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1358": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1357": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1356": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1355": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1354": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1353": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1352": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1351": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1350": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1349": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1348": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1347": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1346": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1345": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1344": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1343": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1342": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1341": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1340": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1339": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1338": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1337": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1336": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1335": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1334": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1333": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1332": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1331": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1330": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1329": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1328": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1327": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1326": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1325": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1324": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1323": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1322": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1321": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1320": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1319": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1318": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1317": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1316": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1315": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1314": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1313": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1312": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1311": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1310": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1309": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1308": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1307": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1306": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1305": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1304": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1303": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1302": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1301": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1300": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1299": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1298": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1297": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1296": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1295": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1294": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1293": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1292": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1291": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1290": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1289": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1288": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1287": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1286": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1285": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1284": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1283": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1282": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1281": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1280": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1279": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1278": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1277": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1276": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1275": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1274": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1273": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1272": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1271": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1270": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1269": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1268": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1267": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1266": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1265": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1264": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1263": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1262": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1261": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1260": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1259": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1258": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1257": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1256": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1255": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1254": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1253": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1252": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1251": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1250": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1249": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1248": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1247": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1246": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1245": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1244": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1243": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1242": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1241": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1240": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1239": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1238": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1237": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1236": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1235": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1234": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1233": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1232": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1231": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1230": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1229": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1228": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1227": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1226": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1225": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1224": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1223": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1222": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1221": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1220": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1219": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1218": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1217": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1216": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1215": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1214": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1213": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1212": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1211": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1210": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1209": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1208": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1207": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1206": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1205": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1204": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1203": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1202": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1201": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1200": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1199": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1198": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1197": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1196": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1195": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1194": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1193": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1192": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1191": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1190": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1189": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1188": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1187": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1186": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1185": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1184": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1183": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1182": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1181": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1180": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1179": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1178": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1177": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1176": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1175": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1174": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1173": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1172": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1171": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1170": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1169": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1168": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1167": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1166": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1165": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1164": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1163": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1162": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1161": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1160": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1159": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1158": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1157": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1156": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1155": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1154": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1153": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1152": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1151": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1150": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1149": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1148": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1147": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1146": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1145": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1144": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1143": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1142": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1141": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1140": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1139": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1138": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1137": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1136": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1135": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1134": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1133": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1132": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1131": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1130": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1129": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1128": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1127": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1126": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1125": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1124": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1123": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1122": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1121": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1120": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1119": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1118": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1117": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1116": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1115": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1114": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1113": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1112": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1111": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1110": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1109": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1108": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1107": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1106": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1105": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1104": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1103": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1102": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1101": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1100": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1099": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1098": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1097": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1096": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1095": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1094": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1093": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1092": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1091": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1090": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1089": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1088": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1087": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1086": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1085": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1084": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1083": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1082": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1081": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1080": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1079": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1078": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1077": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1076": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1075": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1074": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1073": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1072": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1071": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1070": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1069": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1068": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1067": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1066": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1065": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1064": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1063": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1062": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1061": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1060": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1059": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1058": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1057": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1056": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1055": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1054": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1053": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1052": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1051": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1050": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1049": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1048": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1047": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1046": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1045": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1044": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1043": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1042": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1041": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1040": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1039": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1038": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1037": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1036": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1035": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1034": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1033": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1032": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1031": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1030": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1029": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1028": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1027": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1026": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1025": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1024": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1023": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1022": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1021": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1020": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1019": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1018": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1017": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1016": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1015": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1014": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1013": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1012": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1011": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1010": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1009": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1008": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1007": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1006": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1005": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1004": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1003": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1002": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1001": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1000": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-999": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-998": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-997": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-996": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-995": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-994": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-993": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-992": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-991": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-990": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-989": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-988": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-987": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-986": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-985": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-984": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-983": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-982": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-981": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-980": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-979": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-978": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-977": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-976": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-975": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-974": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-973": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-972": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-971": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-970": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-969": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-968": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-967": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-966": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-965": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-964": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-963": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-962": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-961": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-960": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-959": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-958": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-957": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-956": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-955": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-954": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-953": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-952": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-951": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-950": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-949": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-948": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-947": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-946": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-945": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-944": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-943": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-942": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-941": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-940": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-939": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-938": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-937": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-936": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-935": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-934": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-933": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-932": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-931": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-930": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-929": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-928": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-927": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-926": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-925": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-924": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-923": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-922": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-921": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-920": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-919": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-918": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-917": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-916": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-915": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-914": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-913": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-912": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-911": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-910": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-909": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-908": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-907": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-906": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-905": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-904": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-903": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-902": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-901": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-900": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-899": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-898": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-897": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-896": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-895": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-894": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-893": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-892": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-891": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-890": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-889": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-888": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-887": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-886": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-885": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-884": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-883": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-882": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-881": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-880": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-879": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-878": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-877": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-876": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-875": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-874": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-873": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-872": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-871": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-870": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-869": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-868": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-867": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-866": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-865": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-864": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-863": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-862": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-861": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-860": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-859": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-858": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-857": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-856": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-855": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-854": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-853": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-852": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-851": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-850": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-849": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-848": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-847": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-846": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-845": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-844": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-843": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-842": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-841": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-840": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-839": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-838": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-837": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-836": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-835": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-834": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-833": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-832": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-831": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-830": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-829": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-828": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-827": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-826": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-825": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-824": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-823": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-822": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-821": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-820": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-819": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-818": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-817": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-816": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-815": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-814": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-813": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-812": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-811": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-810": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-809": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-808": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-807": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-806": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-805": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-804": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-803": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-802": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-801": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-800": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-799": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-798": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-797": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-796": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-795": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-794": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-793": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-792": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-791": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-790": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-789": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-788": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-787": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-786": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-785": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-784": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-783": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-782": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-781": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-780": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-779": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-778": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-777": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-776": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-775": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-774": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-773": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-772": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-771": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-770": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-769": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-768": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-767": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-766": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-765": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-764": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-763": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-762": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-761": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-760": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-759": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-758": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-757": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-756": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-755": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-754": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-753": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-752": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-751": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-750": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-749": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-748": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-747": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-746": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-745": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-744": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-743": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-742": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-741": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-740": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-739": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-738": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-737": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-736": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-735": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-734": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-733": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-732": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-731": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-730": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-729": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-728": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-727": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-726": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-725": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-724": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-723": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-722": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-721": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-720": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-719": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-718": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-717": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-716": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-715": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-714": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-713": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-712": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-711": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-710": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-709": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-708": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-707": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-706": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-705": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-704": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-703": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-702": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-701": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-700": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-699": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-698": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-697": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-696": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-695": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-694": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-693": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-692": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-691": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-690": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-689": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-688": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-687": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-686": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-685": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-684": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-683": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-682": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-681": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-680": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-679": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-678": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-677": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-676": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-675": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-674": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-673": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-672": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-671": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-670": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-669": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-668": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-667": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-666": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-665": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-664": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-663": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-662": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-661": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-660": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-659": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-658": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-657": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-656": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-655": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-654": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-653": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-652": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-651": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-650": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-649": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-648": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-647": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-646": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-645": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-644": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-643": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-642": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-641": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-640": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-639": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-638": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-637": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-636": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-635": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-634": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-633": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-632": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-631": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-630": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-629": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-628": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-627": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-626": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-625": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-624": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-623": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-622": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-621": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-620": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-619": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-618": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-617": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-616": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-615": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-614": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-613": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-612": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-611": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-610": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-609": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-608": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-607": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-606": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-605": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-604": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-603": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-602": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-601": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-600": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-599": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-598": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-597": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-596": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-595": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-594": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-593": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-592": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-591": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-590": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-589": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-588": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-587": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-586": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-585": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-584": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-583": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-582": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-581": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-580": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-579": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-578": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-577": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-576": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-575": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-574": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-573": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-572": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-571": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-570": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-569": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-568": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-567": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-566": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-565": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-564": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-563": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-562": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-561": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-560": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-559": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-558": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-557": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-556": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-555": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-554": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-553": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-552": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-551": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-550": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-549": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-548": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-547": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-546": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-545": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-544": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-543": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-542": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-541": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-540": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-539": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-538": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-537": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-536": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-535": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-534": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-533": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-532": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-531": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-530": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-529": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-528": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-527": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-526": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-525": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-524": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-523": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-522": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-521": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-520": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-519": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-518": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-517": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-516": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-515": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-514": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-513": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-512": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-511": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-510": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-509": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-508": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-507": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-506": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-505": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-504": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-503": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-502": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-501": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-500": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-499": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-498": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-497": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-496": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-495": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-494": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-493": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-492": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-491": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-490": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-489": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-488": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-487": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-486": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-485": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-484": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-483": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-482": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-481": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-480": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-479": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-478": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-477": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-476": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-475": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-474": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-473": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-472": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-471": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-470": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-469": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-468": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-467": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-466": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-465": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-464": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-463": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-462": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-461": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-460": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-459": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-458": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-457": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-456": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-455": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-454": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-453": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-452": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-451": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-450": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-449": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-448": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-447": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-446": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-445": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-444": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-443": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-442": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-441": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-440": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-439": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-438": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-437": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-436": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-435": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-434": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-433": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-432": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-431": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-430": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-429": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-428": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-427": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-426": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-425": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-424": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-423": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-422": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-421": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-420": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-419": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-418": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-417": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-416": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-415": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-414": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-413": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-412": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-411": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-410": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-409": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-408": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-407": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-406": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-405": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-404": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-403": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-402": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-401": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-400": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-399": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-398": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-397": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-396": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-395": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-394": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-393": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-392": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-391": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-390": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-389": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-388": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-387": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-386": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-385": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-384": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-383": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-382": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-381": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-380": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-379": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-378": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-377": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-376": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-375": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-374": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-373": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-372": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-371": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-370": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-369": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-368": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-367": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-366": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-365": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-364": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-363": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-362": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-361": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-360": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-359": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-358": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-357": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-356": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-355": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-354": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-353": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-352": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-351": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-350": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-349": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-348": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-347": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-346": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-345": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-344": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-343": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-342": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-341": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-340": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-339": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-338": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-337": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-336": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-335": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-334": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-333": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-332": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-331": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-330": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-329": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-328": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-327": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-326": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-325": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-324": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-323": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-322": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-321": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-320": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-319": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-318": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-317": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-316": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-315": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-314": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-313": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-312": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-311": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-310": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-309": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-308": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-307": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-306": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-305": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-304": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-303": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-302": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-301": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-300": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-299": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-298": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-297": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-296": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-295": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-294": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-293": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-292": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-291": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-290": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-289": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-288": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-287": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-286": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-285": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-284": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-283": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-282": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-281": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-280": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-279": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-278": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-277": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-276": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-275": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-274": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-273": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-272": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-271": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-270": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-269": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-268": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-267": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-266": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-265": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-264": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-263": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-262": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-261": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-260": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-259": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-258": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-257": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-256": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-255": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-254": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-253": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-252": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-251": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-250": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-249": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-248": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-247": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-246": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-245": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-244": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-243": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-242": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-241": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-240": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-239": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-238": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-237": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-236": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-235": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-234": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-233": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-232": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-231": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-230": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-229": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-228": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-227": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-226": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-225": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-224": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-223": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-222": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-221": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-220": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-219": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-218": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-217": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-216": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-215": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-214": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-213": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-212": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-211": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-210": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-209": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-208": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-207": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-206": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-205": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-204": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-203": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-202": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-201": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-200": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-199": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-198": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-197": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-196": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-195": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-194": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-193": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-192": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-191": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-190": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-189": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-188": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-187": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-186": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-185": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-184": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-183": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-182": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-181": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-180": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-179": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-178": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-177": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-176": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-175": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-174": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-173": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-172": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-171": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-170": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-169": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-168": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-167": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-166": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-165": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-164": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-163": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-162": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-161": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-160": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-159": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-158": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-157": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-156": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-155": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-154": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-153": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-152": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-151": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-150": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-149": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-148": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-147": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-146": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-145": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-144": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-143": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-142": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-141": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-140": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-139": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-138": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-137": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-136": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-135": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-134": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-133": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-132": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-131": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-130": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-129": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-128": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-127": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-126": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-125": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-124": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-123": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-122": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-121": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-120": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-119": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-118": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-117": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-116": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-115": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-114": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-113": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-112": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-111": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-110": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-109": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-108": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-107": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-106": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-105": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-104": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-103": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-102": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-101": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-100": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-99": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-98": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-97": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-96": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-95": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-94": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-93": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-92": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-91": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-90": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-89": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-88": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-87": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-86": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-85": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-84": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-83": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-82": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-81": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-80": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-79": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-78": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-77": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-76": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-75": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-74": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-73": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-72": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-71": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-70": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-69": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-68": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-67": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-66": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-65": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-64": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-63": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-62": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-61": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-60": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-59": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-58": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-57": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-56": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-55": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-54": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-53": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-52": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-51": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-50": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-49": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-48": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-47": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-46": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-45": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-44": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-43": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-42": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-41": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-40": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-39": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-38": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-37": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-36": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-35": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-34": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-33": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-32": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-31": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-30": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-29": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-28": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-27": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-26": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-25": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-24": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-23": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-22": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-21": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-20": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-19": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-18": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-17": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-16": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-15": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-14": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-13": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-12": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-11": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-10": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-9": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-8": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-7": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-6": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-5": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-4": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-3": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-2": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-1": { "type": "keyword", "script": { "source": "emit('nice')" } }, + "my-runtime-field-0": { "type": "keyword", "script": { "source": "emit('nice')" } } }, "properties": { "@timestamp": { From 7f664f578866ea9d5d7a960c99e39545b6075ed0 Mon Sep 17 00:00:00 2001 From: Zacqary Adam Xeper Date: Wed, 13 Jul 2022 16:02:10 -0500 Subject: [PATCH 002/111] [RAM] Remove ability to enter negative numbers in snooze recurrence UI (#136235) * [RAM] Remove ability to enter negative numbers in snooze recurrence UI * Add onBlur to number field * Add NumberField test --- .../rule_snooze/helpers/number_field.test.tsx | 69 +++++++++++++++++++ .../rule_snooze/helpers/number_field.tsx | 45 ++++++++++++ .../custom_recurrence_scheduler.tsx | 6 +- .../recurrence_scheduler/index.tsx | 6 +- 4 files changed, 120 insertions(+), 6 deletions(-) create mode 100644 x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.test.tsx create mode 100644 x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.tsx diff --git a/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.test.tsx b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.test.tsx new file mode 100644 index 0000000000000..d3ae27c5bd211 --- /dev/null +++ b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.test.tsx @@ -0,0 +1,69 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { mountWithIntl } from '@kbn/test-jest-helpers'; +import React from 'react'; +import { NumberField } from './number_field'; + +describe('NumberField', () => { + const onChange = jest.fn(); + + beforeEach(() => { + onChange.mockReset(); + }); + + test('allows any value with no defined min or max', () => { + const wrapper = mountWithIntl(); + wrapper + .find('input') + .first() + .simulate('change', { target: { value: 3 } }); + + expect(onChange).toHaveBeenCalledWith(3); + + wrapper + .find('input') + .first() + .simulate('change', { target: { value: 0 } }); + + expect(onChange).toHaveBeenCalledWith(0); + }); + + test('constrains value to defined min', () => { + const wrapper = mountWithIntl(); + wrapper + .find('input') + .first() + .simulate('change', { target: { value: 1 } }); + + expect(onChange).toHaveBeenCalledWith(1); + + wrapper + .find('input') + .first() + .simulate('change', { target: { value: -1 } }); + + expect(onChange).not.toHaveBeenCalledWith(-1); + }); + + test('constrains value to defined max', () => { + const wrapper = mountWithIntl(); + wrapper + .find('input') + .first() + .simulate('change', { target: { value: -1 } }); + + expect(onChange).toHaveBeenCalledWith(-1); + + wrapper + .find('input') + .first() + .simulate('change', { target: { value: 11 } }); + + expect(onChange).not.toHaveBeenCalledWith(11); + }); +}); diff --git a/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.tsx b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.tsx new file mode 100644 index 0000000000000..2483f6fc4a43c --- /dev/null +++ b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/helpers/number_field.tsx @@ -0,0 +1,45 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React, { useState, useCallback } from 'react'; +import { EuiFieldNumber, EuiFieldNumberProps } from '@elastic/eui'; + +export const NumberField: React.FC< + EuiFieldNumberProps & { + onChange: (value: string) => void; + } +> = (props) => { + const [displayValue, setDisplayValue] = useState(props.value); + const min = typeof props.min !== 'undefined' ? props.min : -Infinity; + const max = typeof props.max !== 'undefined' ? props.max : Infinity; + + const onChange = useCallback( + (e) => { + const { value } = e.target; + const isValid = !isNaN(Number(value)) && value >= min && value <= max; + if (isValid || value === '') { + setDisplayValue(value); + } + if (isValid && props.onChange) { + props.onChange(value); + } + }, + [props, setDisplayValue, max, min] + ); + + const onBlur = useCallback( + (e) => { + if (isNaN(Number(displayValue)) || displayValue === '') { + setDisplayValue(props.value); + } + if (props.onBlur) props.onBlur(e); + }, + [displayValue, props, setDisplayValue] + ); + + return ; +}; diff --git a/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/custom_recurrence_scheduler.tsx b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/custom_recurrence_scheduler.tsx index 4a94c43e4810e..b7568cfdc99db 100644 --- a/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/custom_recurrence_scheduler.tsx +++ b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/custom_recurrence_scheduler.tsx @@ -7,7 +7,6 @@ import { EuiButtonGroup, - EuiFieldNumber, EuiFormControlLayout, EuiFormRow, EuiSelect, @@ -19,6 +18,7 @@ import deepEqual from 'fast-deep-equal'; import { Moment } from 'moment'; import React, { useCallback, useEffect, useMemo, useState, useRef } from 'react'; +import { NumberField } from '../helpers/number_field'; import { RRuleFrequency } from '../../../../../../types'; import { I18N_WEEKDAY_OPTIONS } from './constants'; import { @@ -140,12 +140,12 @@ export const CustomRecurrenceScheduler: React.FC } )} > - setInterval(Number(e.target.value))} + onChange={(value) => setInterval(Number(value))} /> diff --git a/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/index.tsx b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/index.tsx index fbd5082d0f131..4220e287c5f17 100644 --- a/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/index.tsx +++ b/x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rule_snooze/recurrence_scheduler/index.tsx @@ -8,7 +8,6 @@ import { EuiButtonGroup, EuiDatePicker, - EuiFieldNumber, EuiFormControlLayout, EuiFormRow, EuiHorizontalRule, @@ -21,6 +20,7 @@ import { Moment } from 'moment'; import React from 'react'; import { useEffect, useMemo, useRef, useState } from 'react'; +import { NumberField } from '../helpers/number_field'; import { RRuleFrequency, RecurrenceSchedule } from '../../../../../../types'; import { i18nMonthDayDate } from '../../../../../lib/i18n_month_day_date'; import { @@ -276,11 +276,11 @@ export const RecurrenceScheduler: React.FC = ({ } )} > - setOccurrrences(Number(e.target.value))} + onChange={(value) => setOccurrrences(Number(value))} /> From f074c397c537029e0b9a1ea8bf3cb9ef52a3dc04 Mon Sep 17 00:00:00 2001 From: Spencer Date: Wed, 13 Jul 2022 16:36:39 -0500 Subject: [PATCH 003/111] [ftr] add support for launching a dedicated task runner Kibana node (#135875) * [ftr] add support for launching a dedicated task runner Kibana node * Update run_kibana_server.ts * disable the optimizer in kbn-tasks proc when running locally * remove paths module * include decicated task proc in promises array * add getSupertest() helper to DedicatesTaskRunner service * avoid caching a supertest instance, just create one on request * remove surprise dependents on KIBANA_ROOT const * remove modifications to test/analytics/config.ts --- packages/kbn-test/BUILD.bazel | 2 + packages/kbn-test/src/es/test_es_cluster.ts | 10 +- .../functional_test_runner.ts | 2 + .../lib/config/schema.ts | 1 + .../lib/dedicated_task_runner.ts | 138 ++++++++++++++++++ .../src/functional_test_runner/lib/index.ts | 1 + .../functional_test_runner/public_types.ts | 19 ++- .../src/functional_tests/lib/index.ts | 1 - .../src/functional_tests/lib/paths.ts | 21 --- .../functional_tests/lib/run_elasticsearch.ts | 4 +- .../functional_tests/lib/run_kibana_server.ts | 97 ++++++++---- .../kbn-test/src/functional_tests/tasks.ts | 15 +- packages/kbn-test/src/index.ts | 3 - test/examples/config.js | 8 +- x-pack/test/examples/config.ts | 3 +- x-pack/test/licensing_plugin/config.public.ts | 3 +- x-pack/test/plugin_functional/config.ts | 3 +- .../services/endpoint_telemetry.ts | 3 +- 18 files changed, 255 insertions(+), 79 deletions(-) create mode 100644 packages/kbn-test/src/functional_test_runner/lib/dedicated_task_runner.ts delete mode 100644 packages/kbn-test/src/functional_tests/lib/paths.ts diff --git a/packages/kbn-test/BUILD.bazel b/packages/kbn-test/BUILD.bazel index e2824076e80b9..b854379eb536b 100644 --- a/packages/kbn-test/BUILD.bazel +++ b/packages/kbn-test/BUILD.bazel @@ -76,6 +76,7 @@ RUNTIME_DEPS = [ "@npm//rxjs", "@npm//semver", "@npm//strip-ansi", + "@npm//supertest", "@npm//xmlbuilder", "@npm//xml2js", ] @@ -123,6 +124,7 @@ TYPES_DEPS = [ "@npm//@types/react-redux", "@npm//@types/react-router-dom", "@npm//@types/semver", + "@npm//@types/supertest", "@npm//@types/uuid", "@npm//@types/xml2js", ] diff --git a/packages/kbn-test/src/es/test_es_cluster.ts b/packages/kbn-test/src/es/test_es_cluster.ts index 1eb48ca58d950..8c650ec9b6051 100644 --- a/packages/kbn-test/src/es/test_es_cluster.ts +++ b/packages/kbn-test/src/es/test_es_cluster.ts @@ -19,11 +19,11 @@ import type { ChildProcess } from 'child_process'; import { Cluster } from '@kbn/es'; import { Client, HttpConnection } from '@elastic/elasticsearch'; import type { ToolingLog } from '@kbn/tooling-log'; +import { REPO_ROOT } from '@kbn/utils'; + import { CI_PARALLEL_PROCESS_PREFIX } from '../ci_parallel_process_prefix'; import { esTestConfig } from './es_test_config'; -import { KIBANA_ROOT } from '..'; - interface TestEsClusterNodesOptions { name: string; /** @@ -168,7 +168,7 @@ export function createTestEsCluster< password = 'changeme', license = 'basic', log, - basePath = Path.resolve(KIBANA_ROOT, '.es'), + basePath = Path.resolve(REPO_ROOT, '.es'), esFrom = esTestConfig.getBuildFrom(), dataArchive, nodes = [{ name: 'node-01' }], @@ -196,7 +196,7 @@ export function createTestEsCluster< const config = { version: esTestConfig.getVersion(), installPath: Path.resolve(basePath, clusterName), - sourcePath: Path.resolve(KIBANA_ROOT, '../elasticsearch'), + sourcePath: Path.resolve(REPO_ROOT, '../elasticsearch'), password, license, basePath, @@ -321,7 +321,7 @@ export function createTestEsCluster< } const uuid = Uuid.v4(); - const debugPath = Path.resolve(KIBANA_ROOT, `data/es_debug_${uuid}.tar.gz`); + const debugPath = Path.resolve(REPO_ROOT, `data/es_debug_${uuid}.tar.gz`); log.error(`[es] debug files found, archiving install to ${debugPath}`); const archiver = createArchiver('tar', { gzip: true }); const promise = pipeline(archiver, Fs.createWriteStream(debugPath)); diff --git a/packages/kbn-test/src/functional_test_runner/functional_test_runner.ts b/packages/kbn-test/src/functional_test_runner/functional_test_runner.ts index 9de6500a45323..4e549e960dc26 100644 --- a/packages/kbn-test/src/functional_test_runner/functional_test_runner.ts +++ b/packages/kbn-test/src/functional_test_runner/functional_test_runner.ts @@ -24,6 +24,7 @@ import { Config, SuiteTracker, EsVersion, + DedicatedTaskRunner, } from './lib'; import { createEsClientForFtrConfig } from '../es'; @@ -242,6 +243,7 @@ export class FunctionalTestRunner { config: () => config, dockerServers: () => dockerServers, esVersion: () => this.esVersion, + dedicatedTaskRunner: () => new DedicatedTaskRunner(config, this.log), }); return await handler(config, lifecycle, coreProviders); diff --git a/packages/kbn-test/src/functional_test_runner/lib/config/schema.ts b/packages/kbn-test/src/functional_test_runner/lib/config/schema.ts index bf652bf8c8444..6f5757a73ea0a 100644 --- a/packages/kbn-test/src/functional_test_runner/lib/config/schema.ts +++ b/packages/kbn-test/src/functional_test_runner/lib/config/schema.ts @@ -216,6 +216,7 @@ export const schema = Joi.object() sourceArgs: Joi.array(), serverArgs: Joi.array(), installDir: Joi.string(), + useDedicatedTaskRunner: Joi.boolean().default(false), /** Options for how FTR should execute and interact with Kibana */ runOptions: Joi.object() .keys({ diff --git a/packages/kbn-test/src/functional_test_runner/lib/dedicated_task_runner.ts b/packages/kbn-test/src/functional_test_runner/lib/dedicated_task_runner.ts new file mode 100644 index 0000000000000..20b5e0387c719 --- /dev/null +++ b/packages/kbn-test/src/functional_test_runner/lib/dedicated_task_runner.ts @@ -0,0 +1,138 @@ +/* + * 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 Url from 'url'; + +import { ToolingLog } from '@kbn/tooling-log'; +import Supertest from 'supertest'; + +import { KbnClient } from '../../kbn_client'; +import { Config } from './config'; +import { getKibanaCliArg } from '../../functional_tests/lib/kibana_cli_args'; + +export class DedicatedTaskRunner { + static getPort(uiPort: number) { + return uiPort + 13; + } + + static getUuid(mainUuid: string) { + if (mainUuid.length !== 36) { + throw new Error(`invalid mainUuid: ${mainUuid}`); + } + + return `00000000-${mainUuid.slice(9)}`; + } + + /** + * True when the FTR config indicates that Kibana has a dedicated task runner process, otherwise false. If this + * property is false then all other methods on this class will throw when they are called, so if you're not + * certain where your code will be run make sure to check `dedicatedTaskRunner.enabled` before calling + * other methods. + */ + public readonly enabled: boolean; + + private readonly enabledProps?: { + readonly port: number; + readonly url: string; + readonly client: KbnClient; + readonly uuid?: string; + readonly supertest?: Supertest.SuperTest; + }; + + constructor(config: Config, log: ToolingLog) { + if (!config.get('kbnTestServer.useDedicatedTaskRunner')) { + this.enabled = false; + return; + } + + this.enabled = true; + + const port = DedicatedTaskRunner.getPort(config.get('servers.kibana.port')); + const url = Url.format({ + ...config.get('servers.kibana'), + port, + }); + const client = new KbnClient({ + log, + url, + certificateAuthorities: config.get('servers.kibana.certificateAuthorities'), + uiSettingDefaults: config.get('uiSettings.defaults'), + }); + + const mainUuid = getKibanaCliArg(config.get('kbnTestServer.serverArgs'), 'server.uuid'); + const uuid = typeof mainUuid === 'string' ? DedicatedTaskRunner.getUuid(mainUuid) : undefined; + + this.enabledProps = { port, url, client, uuid }; + } + + private getEnabledProps() { + if (!this.enabledProps) { + throw new Error( + `DedicatedTaskRunner is not enabled, check the "enabled" property before calling getters assuming it is enabled.` + ); + } + + return this.enabledProps; + } + + /** + * The port number that the dedicated task runner is running on + */ + getPort() { + return this.getEnabledProps().port; + } + + /** + * The full URL for the dedicated task runner process + */ + getUrl() { + return this.getEnabledProps().url; + } + + /** + * Returns true if the `--server.uuid` setting was passed to the Kibana server, allowing the UUID to + * be deterministic and ensuring that `dedicatedTaskRunner.getUuid()` won't throw. + */ + hasUuid() { + return !!this.getEnabledProps().uuid; + } + + /** + * If `--server.uuid` is passed to Kibana in the FTR config file then the dedicated task runner will + * use a UUID derived from that and it will be synchronously available to users via this function. + * Otherwise this function will through. + */ + getUuid() { + const uuid = this.getEnabledProps().uuid; + if (!uuid) { + throw new Error( + 'Pass `--server.uuid` the the Kibana server in your FTR config in order to make the UUID of the dedicated task runner deterministic.' + ); + } + + return uuid; + } + + /** + * @returns a `KbnClient` instance that is configured to talk directly to the dedicated task runner. Not really sure how useful this is. + */ + getClient() { + return this.getEnabledProps().client; + } + + /** + * @returns a Supertest instance that will send requests to the dedicated task runner. + * + * @example + * const supertest = dedicatedTaskRunner.getSupertest(); + * const response = await supertest.get('/status'); + */ + getSupertest() { + return Supertest(this.getUrl()); + } +} diff --git a/packages/kbn-test/src/functional_test_runner/lib/index.ts b/packages/kbn-test/src/functional_test_runner/lib/index.ts index b269e34178851..983a185dee682 100644 --- a/packages/kbn-test/src/functional_test_runner/lib/index.ts +++ b/packages/kbn-test/src/functional_test_runner/lib/index.ts @@ -14,6 +14,7 @@ export * from './providers'; export { runTests, setupMocha } from './mocha'; export * from './docker_servers'; export { SuiteTracker } from './suite_tracker'; +export { DedicatedTaskRunner } from './dedicated_task_runner'; export type { Provider } from './providers'; export * from './es_version'; diff --git a/packages/kbn-test/src/functional_test_runner/public_types.ts b/packages/kbn-test/src/functional_test_runner/public_types.ts index 67adceaf22323..3faa19de73ce1 100644 --- a/packages/kbn-test/src/functional_test_runner/public_types.ts +++ b/packages/kbn-test/src/functional_test_runner/public_types.ts @@ -8,7 +8,13 @@ import type { ToolingLog } from '@kbn/tooling-log'; -import type { Config, Lifecycle, DockerServersService, EsVersion } from './lib'; +import type { + Config, + Lifecycle, + DockerServersService, + EsVersion, + DedicatedTaskRunner, +} from './lib'; import type { Test, Suite } from './fake_mocha_types'; export { Lifecycle, Config }; @@ -56,7 +62,15 @@ export interface GenericFtrProviderContext< * Determine if a service is avaliable * @param serviceName */ - hasService(serviceName: 'config' | 'log' | 'lifecycle' | 'dockerServers' | 'esVersion'): true; + hasService( + serviceName: + | 'config' + | 'log' + | 'lifecycle' + | 'dockerServers' + | 'esVersion' + | 'dedicatedTaskRunner' + ): true; hasService(serviceName: K): serviceName is K; hasService(serviceName: string): serviceName is Extract; @@ -70,6 +84,7 @@ export interface GenericFtrProviderContext< getService(serviceName: 'lifecycle'): Lifecycle; getService(serviceName: 'dockerServers'): DockerServersService; getService(serviceName: 'esVersion'): EsVersion; + getService(serviceName: 'dedicatedTaskRunner'): DedicatedTaskRunner; getService(serviceName: T): ServiceMap[T]; /** diff --git a/packages/kbn-test/src/functional_tests/lib/index.ts b/packages/kbn-test/src/functional_tests/lib/index.ts index 2726192328bda..8844a2ee59a19 100644 --- a/packages/kbn-test/src/functional_tests/lib/index.ts +++ b/packages/kbn-test/src/functional_tests/lib/index.ts @@ -10,5 +10,4 @@ export { runKibanaServer } from './run_kibana_server'; export { runElasticsearch } from './run_elasticsearch'; export type { CreateFtrOptions, CreateFtrParams } from './run_ftr'; export { runFtr, hasTests, assertNoneExcluded } from './run_ftr'; -export { KIBANA_ROOT, KIBANA_FTR_SCRIPT } from './paths'; export { runCli } from './run_cli'; diff --git a/packages/kbn-test/src/functional_tests/lib/paths.ts b/packages/kbn-test/src/functional_tests/lib/paths.ts deleted file mode 100644 index 76357d447dc2a..0000000000000 --- a/packages/kbn-test/src/functional_tests/lib/paths.ts +++ /dev/null @@ -1,21 +0,0 @@ -/* - * 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 { REPO_ROOT } from '@kbn/utils'; -import { resolve, relative } from 'path'; - -// resolve() treats relative paths as relative to process.cwd(), -// so to return a relative path we use relative() -function resolveRelative(path: string) { - return relative(process.cwd(), resolve(path)); -} - -export const KIBANA_EXEC = 'node'; -export const KIBANA_SCRIPT_PATH = resolveRelative('scripts/kibana'); -export const KIBANA_ROOT = REPO_ROOT; -export const KIBANA_FTR_SCRIPT = resolve(KIBANA_ROOT, 'scripts/functional_test_runner'); diff --git a/packages/kbn-test/src/functional_tests/lib/run_elasticsearch.ts b/packages/kbn-test/src/functional_tests/lib/run_elasticsearch.ts index 2ee9de4053fef..5dcee56e765e0 100644 --- a/packages/kbn-test/src/functional_tests/lib/run_elasticsearch.ts +++ b/packages/kbn-test/src/functional_tests/lib/run_elasticsearch.ts @@ -9,7 +9,7 @@ import { resolve } from 'path'; import type { ToolingLog } from '@kbn/tooling-log'; import getPort from 'get-port'; -import { KIBANA_ROOT } from './paths'; +import { REPO_ROOT } from '@kbn/utils'; import type { Config } from '../../functional_test_runner'; import { createTestEsCluster } from '../../es'; @@ -106,7 +106,7 @@ async function startEsNode( port: config.port, ssl: config.ssl, log, - basePath: resolve(KIBANA_ROOT, '.es'), + basePath: resolve(REPO_ROOT, '.es'), nodes: [ { name, diff --git a/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts b/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts index 7b6d6d5cd1a3e..76346f3618a51 100644 --- a/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts +++ b/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts @@ -7,12 +7,15 @@ */ import Path from 'path'; +import Os from 'os'; +import Uuid from 'uuid'; import type { ProcRunner } from '@kbn/dev-proc-runner'; +import { REPO_ROOT } from '@kbn/utils'; -import { KIBANA_ROOT, KIBANA_EXEC, KIBANA_SCRIPT_PATH } from './paths'; import type { Config } from '../../functional_test_runner'; -import { parseRawFlags } from './kibana_cli_args'; +import { DedicatedTaskRunner } from '../../functional_test_runner/lib'; +import { parseRawFlags, getArgValue } from './kibana_cli_args'; function extendNodeOptions(installDir?: string) { if (!installDir) { @@ -44,13 +47,35 @@ export async function runKibanaServer({ }) { const runOptions = config.get('kbnTestServer.runOptions'); const installDir = runOptions.alwaysUseSource ? undefined : options.installDir; - const extraArgs = options.extraKbnOpts ?? []; + const devMode = !installDir; + const useTaskRunner = config.get('kbnTestServer.useDedicatedTaskRunner'); + + const procRunnerOpts = { + cwd: installDir || REPO_ROOT, + cmd: installDir + ? process.platform.startsWith('win') + ? Path.resolve(installDir, 'bin/kibana.bat') + : Path.resolve(installDir, 'bin/kibana') + : process.execPath, + env: { + FORCE_COLOR: 1, + ...process.env, + ...config.get('kbnTestServer.env'), + ...extendNodeOptions(installDir), + }, + wait: runOptions.wait, + onEarlyExit, + }; + + const prefixArgs = devMode + ? [Path.relative(process.cwd(), Path.resolve(REPO_ROOT, 'scripts/kibana'))] + : []; const buildArgs: string[] = config.get('kbnTestServer.buildArgs') || []; const sourceArgs: string[] = config.get('kbnTestServer.sourceArgs') || []; const serverArgs: string[] = config.get('kbnTestServer.serverArgs') || []; - const args = parseRawFlags([ + const kbnFlags = parseRawFlags([ // When installDir is passed, we run from a built version of Kibana which uses different command line // arguments. If installDir is not passed, we run from source code. ...(installDir @@ -58,31 +83,51 @@ export async function runKibanaServer({ : [...sourceArgs, ...serverArgs]), // We also allow passing in extra Kibana server options, tack those on here so they always take precedence - ...extraArgs, + ...(options.extraKbnOpts ?? []), ]); - // main process - await procs.run('kibana', { - cmd: getKibanaCmd(installDir), - args: installDir ? args : [KIBANA_SCRIPT_PATH, ...args], - env: { - FORCE_COLOR: 1, - ...process.env, - ...config.get('kbnTestServer.env'), - ...extendNodeOptions(installDir), - }, - cwd: installDir || KIBANA_ROOT, - wait: runOptions.wait, - onEarlyExit, - }); -} + const promises = [ + // main process + procs.run(useTaskRunner ? 'kbn-ui' : 'kibana', { + ...procRunnerOpts, + args: [ + ...prefixArgs, + ...parseRawFlags([ + ...kbnFlags, + ...(!useTaskRunner + ? [] + : [ + '--node.roles=["ui"]', + `--path.data=${Path.resolve(Os.tmpdir(), `ftr-ui-${Uuid.v4()}`)}`, + ]), + ]), + ], + }), + ]; + + if (useTaskRunner) { + const mainUuid = getArgValue(kbnFlags, 'server.uuid'); -function getKibanaCmd(installDir?: string) { - if (installDir) { - return process.platform.startsWith('win') - ? Path.resolve(installDir, 'bin/kibana.bat') - : Path.resolve(installDir, 'bin/kibana'); + // dedicated task runner + promises.push( + procs.run('kbn-tasks', { + ...procRunnerOpts, + args: [ + ...prefixArgs, + ...parseRawFlags([ + ...kbnFlags, + `--server.port=${DedicatedTaskRunner.getPort(config.get('servers.kibana.port'))}`, + '--node.roles=["background_tasks"]', + `--path.data=${Path.resolve(Os.tmpdir(), `ftr-task-runner-${Uuid.v4()}`)}`, + ...(typeof mainUuid === 'string' && mainUuid + ? [`--server.uuid=${DedicatedTaskRunner.getUuid(mainUuid)}`] + : []), + ...(devMode ? ['--no-optimizer'] : []), + ]), + ], + }) + ); } - return KIBANA_EXEC; + await Promise.all(promises); } diff --git a/packages/kbn-test/src/functional_tests/tasks.ts b/packages/kbn-test/src/functional_tests/tasks.ts index 76cc4dde1f36b..9b5fb5424f3fe 100644 --- a/packages/kbn-test/src/functional_tests/tasks.ts +++ b/packages/kbn-test/src/functional_tests/tasks.ts @@ -6,9 +6,10 @@ * Side Public License, v 1. */ -import { relative } from 'path'; -import * as Rx from 'rxjs'; +import Path from 'path'; import { setTimeout } from 'timers/promises'; + +import * as Rx from 'rxjs'; import { startWith, switchMap, take } from 'rxjs/operators'; import { withProcRunner } from '@kbn/dev-proc-runner'; import { ToolingLog } from '@kbn/tooling-log'; @@ -16,17 +17,17 @@ import { getTimeReporter } from '@kbn/ci-stats-reporter'; import { REPO_ROOT } from '@kbn/utils'; import dedent from 'dedent'; +import { readConfigFile, EsVersion } from '../functional_test_runner/lib'; import { runElasticsearch, runKibanaServer, runFtr, assertNoneExcluded, hasTests, - KIBANA_FTR_SCRIPT, CreateFtrOptions, } from './lib'; -import { readConfigFile, EsVersion } from '../functional_test_runner/lib'; +const FTR_SCRIPT_PATH = Path.resolve(REPO_ROOT, 'scripts/functional_test_runner'); const makeSuccessMessage = (options: StartServerOptions) => { const installDirFlag = options.installDir ? ` --kibana-install-dir=${options.installDir}` : ''; @@ -34,7 +35,7 @@ const makeSuccessMessage = (options: StartServerOptions) => { const pathsMessage = options.useDefaultConfig ? '' : configPaths - .map((path) => relative(process.cwd(), path)) + .map((path) => Path.relative(process.cwd(), path)) .map((path) => ` --config ${path}`) .join(''); @@ -44,7 +45,7 @@ const makeSuccessMessage = (options: StartServerOptions) => { Elasticsearch and Kibana are ready for functional testing. Start the functional tests in another terminal session by running this command from this directory: - node ${relative(process.cwd(), KIBANA_FTR_SCRIPT)}${installDirFlag}${pathsMessage} + node ${Path.relative(process.cwd(), FTR_SCRIPT_PATH)}${installDirFlag}${pathsMessage} ` + '\n\n' ); @@ -96,7 +97,7 @@ export async function runTests(options: RunTestsParams) { await log.indent(0, async () => { if (options.configs.length > 1) { const progress = `${i + 1}/${options.configs.length}`; - log.write(`--- [${progress}] Running ${relative(REPO_ROOT, configPath)}`); + log.write(`--- [${progress}] Running ${Path.relative(REPO_ROOT, configPath)}`); } if (!(await hasTests({ configPath, options: { ...options, log } }))) { diff --git a/packages/kbn-test/src/index.ts b/packages/kbn-test/src/index.ts index 7770232011d21..6d67bbecc2093 100644 --- a/packages/kbn-test/src/index.ts +++ b/packages/kbn-test/src/index.ts @@ -24,9 +24,6 @@ export { runTestsCli, processRunTestsCliOptions, startServersCli, processStartSe // @internal export { runTests, startServers } from './functional_tests/tasks'; -// @internal -export { KIBANA_ROOT } from './functional_tests/lib/paths'; - export { getKibanaCliArg, getKibanaCliLoggers } from './functional_tests/lib/kibana_cli_args'; export type { diff --git a/test/examples/config.js b/test/examples/config.js index 25537a22e19ac..e2374d203d7c7 100644 --- a/test/examples/config.js +++ b/test/examples/config.js @@ -9,15 +9,15 @@ import { resolve } from 'path'; import { services } from '../plugin_functional/services'; import fs from 'fs'; -import { KIBANA_ROOT } from '@kbn/test'; +import { REPO_ROOT } from '@kbn/utils'; export default async function ({ readConfigFile }) { const functionalConfig = await readConfigFile(require.resolve('../functional/config.base.js')); // Find all folders in /examples and /x-pack/examples since we treat all them as plugin folder - const examplesFiles = fs.readdirSync(resolve(KIBANA_ROOT, 'examples')); + const examplesFiles = fs.readdirSync(resolve(REPO_ROOT, 'examples')); const examples = examplesFiles.filter((file) => - fs.statSync(resolve(KIBANA_ROOT, 'examples', file)).isDirectory() + fs.statSync(resolve(REPO_ROOT, 'examples', file)).isDirectory() ); return { @@ -63,7 +63,7 @@ export default async function ({ readConfigFile }) { '--env.name=development', '--telemetry.optIn=false', ...examples.map( - (exampleDir) => `--plugin-path=${resolve(KIBANA_ROOT, 'examples', exampleDir)}` + (exampleDir) => `--plugin-path=${resolve(REPO_ROOT, 'examples', exampleDir)}` ), ], }, diff --git a/x-pack/test/examples/config.ts b/x-pack/test/examples/config.ts index 16db620e76598..fe01c4ecf0e44 100644 --- a/x-pack/test/examples/config.ts +++ b/x-pack/test/examples/config.ts @@ -8,8 +8,7 @@ import { FtrConfigProviderContext } from '@kbn/test'; import { resolve } from 'path'; import fs from 'fs'; -// @ts-expect-error https://github.com/elastic/kibana/issues/95679 -import { KIBANA_ROOT } from '@kbn/test'; +import { REPO_ROOT as KIBANA_ROOT } from '@kbn/utils'; export default async function ({ readConfigFile }: FtrConfigProviderContext) { const xpackFunctionalConfig = await readConfigFile( diff --git a/x-pack/test/licensing_plugin/config.public.ts b/x-pack/test/licensing_plugin/config.public.ts index a9df9f6ad1e96..a962f499d566a 100644 --- a/x-pack/test/licensing_plugin/config.public.ts +++ b/x-pack/test/licensing_plugin/config.public.ts @@ -6,8 +6,7 @@ */ import path from 'path'; -// @ts-expect-error https://github.com/elastic/kibana/issues/95679 -import { KIBANA_ROOT } from '@kbn/test'; +import { REPO_ROOT as KIBANA_ROOT } from '@kbn/utils'; import { FtrConfigProviderContext } from '@kbn/test'; export default async function ({ readConfigFile }: FtrConfigProviderContext) { diff --git a/x-pack/test/plugin_functional/config.ts b/x-pack/test/plugin_functional/config.ts index a21b8f406e506..361318c0992a3 100644 --- a/x-pack/test/plugin_functional/config.ts +++ b/x-pack/test/plugin_functional/config.ts @@ -7,8 +7,7 @@ import { resolve } from 'path'; import fs from 'fs'; -// @ts-expect-error https://github.com/elastic/kibana/issues/95679 -import { KIBANA_ROOT } from '@kbn/test'; +import { REPO_ROOT as KIBANA_ROOT } from '@kbn/utils'; import { FtrConfigProviderContext } from '@kbn/test'; import { services } from './services'; import { pageObjects } from './page_objects'; diff --git a/x-pack/test/security_solution_endpoint/services/endpoint_telemetry.ts b/x-pack/test/security_solution_endpoint/services/endpoint_telemetry.ts index d91a772ccafac..eb93b43e83bab 100644 --- a/x-pack/test/security_solution_endpoint/services/endpoint_telemetry.ts +++ b/x-pack/test/security_solution_endpoint/services/endpoint_telemetry.ts @@ -7,8 +7,7 @@ import fs from 'fs'; import Path from 'path'; -// @ts-expect-error https://github.com/elastic/kibana/issues/95679 -import { KIBANA_ROOT } from '@kbn/test'; +import { REPO_ROOT as KIBANA_ROOT } from '@kbn/utils'; import { FtrProviderContext } from '../ftr_provider_context'; const TELEMETRY_API_ROOT = '/api/stats?extended=true'; From 318530ef549c6706d05c8417b9869612ac3c73e3 Mon Sep 17 00:00:00 2001 From: "Christiane (Tina) Heiligers" Date: Wed, 13 Jul 2022 15:58:41 -0700 Subject: [PATCH 004/111] Migrates core's client-side deprecations service to packages (#136164) * Creates packages for shared types: core-deprecations-common and core-deprecations-common-internal, moves types accordingly, updates src/core/public|server imports * Moves more internal types to package * Changes widely used internal deprecations-related types to public types, moves these to publically accessible packages * Updates import, updates bazel build file * Creates package core-deprecations-browser-internal and moves implementation and tests into package * Updates imports of public deprecations implementations * Creates package core-deprecations-browser-mocks, moves mock and deletes core-deprecations-common-internal * Updates types in src/core * Updates README's and build bazel files for core's client-side deprecations service * Updates imports * exports shared DeprecationsDetails from core/server * Adds deprecations to i18n rc * replace targetted core packages with top level packages for core in i18nrc file, cleans up tsconfig and bazel build files, addresses prefered style in core --- .i18nrc.json | 3 +- package.json | 8 ++ packages/BUILD.bazel | 8 ++ .../BUILD.bazel | 114 ++++++++++++++++++ .../README.md | 3 + .../jest.config.js | 13 ++ .../package.json | 8 ++ .../src}/deprecations_client.test.ts | 2 +- .../src}/deprecations_client.ts | 9 +- .../src/deprecations_service.ts | 29 +++++ .../src}/index.ts | 2 - .../tsconfig.json | 18 +++ .../BUILD.bazel | 110 +++++++++++++++++ .../core-deprecations-browser-mocks/README.md | 3 + .../jest.config.js | 13 ++ .../package.json | 8 ++ .../src}/deprecations_service.mock.ts | 4 +- .../src/index.ts | 9 ++ .../tsconfig.json | 18 +++ .../core-deprecations-browser/BUILD.bazel | 107 ++++++++++++++++ .../core-deprecations-browser/README.md | 3 + .../core-deprecations-browser/jest.config.js | 13 ++ .../core-deprecations-browser/package.json | 8 ++ .../src/contracts.ts | 24 +--- .../core-deprecations-browser/src/index.ts | 10 ++ .../core-deprecations-browser/src/types.ts | 13 ++ .../core-deprecations-browser/tsconfig.json | 18 +++ .../core-deprecations-common/BUILD.bazel | 106 ++++++++++++++++ .../core-deprecations-common/README.md | 3 + .../core-deprecations-common/jest.config.js | 13 ++ .../core-deprecations-common/package.json | 8 ++ .../core-deprecations-common/src/index.ts | 16 +++ .../core-deprecations-common/src/types.ts | 107 ++++++++++++++++ .../core-deprecations-common/tsconfig.json | 18 +++ src/core/public/core_system.ts | 2 +- src/core/public/index.ts | 9 +- src/core/public/mocks.ts | 4 +- .../public/plugins/plugins_service.test.ts | 2 +- .../deprecations/deprecations_factory.test.ts | 2 +- .../deprecations/deprecations_factory.ts | 7 +- .../deprecations/deprecations_registry.ts | 8 +- .../deprecations/deprecations_service.ts | 4 +- src/core/server/deprecations/index.ts | 10 +- src/core/server/deprecations/routes/get.ts | 2 +- src/core/server/deprecations/types.ts | 101 +--------------- src/core/server/index.ts | 6 +- .../deprecations/unknown_object_types.ts | 2 +- src/core/server/types.ts | 5 +- yarn.lock | 32 +++++ 49 files changed, 874 insertions(+), 171 deletions(-) create mode 100644 packages/core/deprecations/core-deprecations-browser-internal/BUILD.bazel create mode 100644 packages/core/deprecations/core-deprecations-browser-internal/README.md create mode 100644 packages/core/deprecations/core-deprecations-browser-internal/jest.config.js create mode 100644 packages/core/deprecations/core-deprecations-browser-internal/package.json rename {src/core/public/deprecations => packages/core/deprecations/core-deprecations-browser-internal/src}/deprecations_client.test.ts (98%) rename {src/core/public/deprecations => packages/core/deprecations/core-deprecations-browser-internal/src}/deprecations_client.ts (92%) create mode 100644 packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts rename {src/core/public/deprecations => packages/core/deprecations/core-deprecations-browser-internal/src}/index.ts (74%) create mode 100644 packages/core/deprecations/core-deprecations-browser-internal/tsconfig.json create mode 100644 packages/core/deprecations/core-deprecations-browser-mocks/BUILD.bazel create mode 100644 packages/core/deprecations/core-deprecations-browser-mocks/README.md create mode 100644 packages/core/deprecations/core-deprecations-browser-mocks/jest.config.js create mode 100644 packages/core/deprecations/core-deprecations-browser-mocks/package.json rename {src/core/public/deprecations => packages/core/deprecations/core-deprecations-browser-mocks/src}/deprecations_service.mock.ts (88%) create mode 100644 packages/core/deprecations/core-deprecations-browser-mocks/src/index.ts create mode 100644 packages/core/deprecations/core-deprecations-browser-mocks/tsconfig.json create mode 100644 packages/core/deprecations/core-deprecations-browser/BUILD.bazel create mode 100644 packages/core/deprecations/core-deprecations-browser/README.md create mode 100644 packages/core/deprecations/core-deprecations-browser/jest.config.js create mode 100644 packages/core/deprecations/core-deprecations-browser/package.json rename src/core/public/deprecations/deprecations_service.ts => packages/core/deprecations/core-deprecations-browser/src/contracts.ts (60%) create mode 100644 packages/core/deprecations/core-deprecations-browser/src/index.ts create mode 100644 packages/core/deprecations/core-deprecations-browser/src/types.ts create mode 100644 packages/core/deprecations/core-deprecations-browser/tsconfig.json create mode 100644 packages/core/deprecations/core-deprecations-common/BUILD.bazel create mode 100644 packages/core/deprecations/core-deprecations-common/README.md create mode 100644 packages/core/deprecations/core-deprecations-common/jest.config.js create mode 100644 packages/core/deprecations/core-deprecations-common/package.json create mode 100644 packages/core/deprecations/core-deprecations-common/src/index.ts create mode 100644 packages/core/deprecations/core-deprecations-common/src/types.ts create mode 100644 packages/core/deprecations/core-deprecations-common/tsconfig.json diff --git a/.i18nrc.json b/.i18nrc.json index 073a413fabf80..08f2ff151b4c2 100644 --- a/.i18nrc.json +++ b/.i18nrc.json @@ -9,8 +9,7 @@ "console": "src/plugins/console", "core": [ "src/core", - "packages/core/i18n/core-i18n-browser-internal", - "packages/core/fatal-errors/core-fatal-errors-browser-internal" + "packages/core" ], "customIntegrations": "src/plugins/custom_integrations", "dashboard": "src/plugins/dashboard", diff --git a/package.json b/package.json index addd2cde108fb..b56a4d1e803aa 100644 --- a/package.json +++ b/package.json @@ -158,6 +158,10 @@ "@kbn/core-base-server-mocks": "link:bazel-bin/packages/core/base/core-base-server-mocks", "@kbn/core-config-server-internal": "link:bazel-bin/packages/core/config/core-config-server-internal", "@kbn/core-config-server-mocks": "link:bazel-bin/packages/core/config/core-config-server-mocks", + "@kbn/core-deprecations-browser": "link:bazel-bin/packages/core/deprecations/core-deprecations-browser", + "@kbn/core-deprecations-browser-internal": "link:bazel-bin/packages/core/deprecations/core-deprecations-browser-internal", + "@kbn/core-deprecations-browser-mocks": "link:bazel-bin/packages/core/deprecations/core-deprecations-browser-mocks", + "@kbn/core-deprecations-common": "link:bazel-bin/packages/core/deprecations/core-deprecations-common", "@kbn/core-doc-links-browser": "link:bazel-bin/packages/core/doc-links/core-doc-links-browser", "@kbn/core-doc-links-browser-internal": "link:bazel-bin/packages/core/doc-links/core-doc-links-browser-internal", "@kbn/core-doc-links-browser-mocks": "link:bazel-bin/packages/core/doc-links/core-doc-links-browser-mocks", @@ -730,6 +734,10 @@ "@types/kbn__core-common-internal-base": "link:bazel-bin/packages/core/common/internal-base/npm_module_types", "@types/kbn__core-config-server-internal": "link:bazel-bin/packages/core/config/core-config-server-internal/npm_module_types", "@types/kbn__core-config-server-mocks": "link:bazel-bin/packages/core/config/core-config-server-mocks/npm_module_types", + "@types/kbn__core-deprecations-browser": "link:bazel-bin/packages/core/deprecations/core-deprecations-browser/npm_module_types", + "@types/kbn__core-deprecations-browser-internal": "link:bazel-bin/packages/core/deprecations/core-deprecations-browser-internal/npm_module_types", + "@types/kbn__core-deprecations-browser-mocks": "link:bazel-bin/packages/core/deprecations/core-deprecations-browser-mocks/npm_module_types", + "@types/kbn__core-deprecations-common": "link:bazel-bin/packages/core/deprecations/core-deprecations-common/npm_module_types", "@types/kbn__core-doc-links-browser": "link:bazel-bin/packages/core/doc-links/core-doc-links-browser/npm_module_types", "@types/kbn__core-doc-links-browser-internal": "link:bazel-bin/packages/core/doc-links/core-doc-links-browser-internal/npm_module_types", "@types/kbn__core-doc-links-browser-mocks": "link:bazel-bin/packages/core/doc-links/core-doc-links-browser-mocks/npm_module_types", diff --git a/packages/BUILD.bazel b/packages/BUILD.bazel index 8d39cf240970b..96786d77dd80f 100644 --- a/packages/BUILD.bazel +++ b/packages/BUILD.bazel @@ -27,6 +27,10 @@ filegroup( "//packages/core/base/core-base-server-internal:build", "//packages/core/base/core-base-server-mocks:build", "//packages/core/config/core-config-server-internal:build", + "//packages/core/deprecations/core-deprecations-browser-internal:build", + "//packages/core/deprecations/core-deprecations-browser-mocks:build", + "//packages/core/deprecations/core-deprecations-browser:build", + "//packages/core/deprecations/core-deprecations-common:build", "//packages/core/doc-links/core-doc-links-browser-internal:build", "//packages/core/doc-links/core-doc-links-browser-mocks:build", "//packages/core/doc-links/core-doc-links-browser:build", @@ -224,6 +228,10 @@ filegroup( "//packages/core/base/core-base-server-internal:build_types", "//packages/core/base/core-base-server-mocks:build_types", "//packages/core/config/core-config-server-internal:build_types", + "//packages/core/deprecations/core-deprecations-browser-internal:build_types", + "//packages/core/deprecations/core-deprecations-browser-mocks:build_types", + "//packages/core/deprecations/core-deprecations-browser:build_types", + "//packages/core/deprecations/core-deprecations-common:build_types", "//packages/core/doc-links/core-doc-links-browser-internal:build_types", "//packages/core/doc-links/core-doc-links-browser-mocks:build_types", "//packages/core/doc-links/core-doc-links-browser:build_types", diff --git a/packages/core/deprecations/core-deprecations-browser-internal/BUILD.bazel b/packages/core/deprecations/core-deprecations-browser-internal/BUILD.bazel new file mode 100644 index 0000000000000..c3f2e0f4c1a23 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-internal/BUILD.bazel @@ -0,0 +1,114 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-deprecations-browser-internal" +PKG_REQUIRE_NAME = "@kbn/core-deprecations-browser-internal" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ + "//packages/kbn-i18n", + "//packages/core/http/core-http-browser-mocks", +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "@npm//@types/react", + "//packages/kbn-i18n:npm_module_types", + "//packages/core/base/core-base-browser-internal:npm_module_types", + "//packages/core/http/core-http-browser:npm_module_types", + "//packages/core/http/core-http-browser-mocks:npm_module_types", + "//packages/core/deprecations/core-deprecations-common:npm_module_types", + "//packages/core/deprecations/core-deprecations-browser:npm_module_types" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/deprecations/core-deprecations-browser-internal/README.md b/packages/core/deprecations/core-deprecations-browser-internal/README.md new file mode 100644 index 0000000000000..8f7b2f147deaf --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-internal/README.md @@ -0,0 +1,3 @@ +# @kbn/core-deprecations-browser-internal + +Contains implementation and internal types for Core's client-side `deprecations` service diff --git a/packages/core/deprecations/core-deprecations-browser-internal/jest.config.js b/packages/core/deprecations/core-deprecations-browser-internal/jest.config.js new file mode 100644 index 0000000000000..c1baf6d1fdfc9 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-internal/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/deprecations/core-deprecations-browser-internal'], +}; diff --git a/packages/core/deprecations/core-deprecations-browser-internal/package.json b/packages/core/deprecations/core-deprecations-browser-internal/package.json new file mode 100644 index 0000000000000..1f4a5d5531ce9 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-internal/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-deprecations-browser-internal", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/src/core/public/deprecations/deprecations_client.test.ts b/packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_client.test.ts similarity index 98% rename from src/core/public/deprecations/deprecations_client.test.ts rename to packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_client.test.ts index 7bff04cccf323..49d9c0a23956a 100644 --- a/src/core/public/deprecations/deprecations_client.test.ts +++ b/packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_client.test.ts @@ -8,7 +8,7 @@ import { httpServiceMock } from '@kbn/core-http-browser-mocks'; import { DeprecationsClient } from './deprecations_client'; -import type { DomainDeprecationDetails } from '../../server/types'; +import type { DomainDeprecationDetails } from '@kbn/core-deprecations-common'; describe('DeprecationsClient', () => { const http = httpServiceMock.createSetupContract(); diff --git a/src/core/public/deprecations/deprecations_client.ts b/packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_client.ts similarity index 92% rename from src/core/public/deprecations/deprecations_client.ts rename to packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_client.ts index 80b1913fcfaf1..f3f2bd7f28e8a 100644 --- a/src/core/public/deprecations/deprecations_client.ts +++ b/packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_client.ts @@ -8,16 +8,17 @@ import { i18n } from '@kbn/i18n'; import type { HttpStart } from '@kbn/core-http-browser'; -import type { DomainDeprecationDetails, DeprecationsGetResponse } from '../../server/types'; +import type { + DomainDeprecationDetails, + DeprecationsGetResponse, +} from '@kbn/core-deprecations-common'; +import type { ResolveDeprecationResponse } from '@kbn/core-deprecations-browser'; /* @internal */ export interface DeprecationsClientDeps { http: Pick; } -/* @internal */ -export type ResolveDeprecationResponse = { status: 'ok' } | { status: 'fail'; reason: string }; - export class DeprecationsClient { private readonly http: Pick; constructor({ http }: DeprecationsClientDeps) { diff --git a/packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts b/packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts new file mode 100644 index 0000000000000..edaf5f7f27be0 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts @@ -0,0 +1,29 @@ +/* + * 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 type { CoreService } from '@kbn/core-base-browser-internal'; +import type { DeprecationsServiceStart } from '@kbn/core-deprecations-browser'; +import type { HttpStart } from '@kbn/core-http-browser'; +import { DeprecationsClient } from './deprecations_client'; + +export class DeprecationsService implements CoreService { + public setup(): void {} + + public start({ http }: { http: HttpStart }): DeprecationsServiceStart { + const deprecationsClient = new DeprecationsClient({ http }); + + return { + getAllDeprecations: deprecationsClient.getAllDeprecations, + getDeprecations: deprecationsClient.getDeprecations, + isDeprecationResolvable: deprecationsClient.isDeprecationResolvable, + resolveDeprecation: deprecationsClient.resolveDeprecation, + }; + } + + public stop(): void {} +} diff --git a/src/core/public/deprecations/index.ts b/packages/core/deprecations/core-deprecations-browser-internal/src/index.ts similarity index 74% rename from src/core/public/deprecations/index.ts rename to packages/core/deprecations/core-deprecations-browser-internal/src/index.ts index 092cbed613ac2..758a941ee3a04 100644 --- a/src/core/public/deprecations/index.ts +++ b/packages/core/deprecations/core-deprecations-browser-internal/src/index.ts @@ -7,5 +7,3 @@ */ export { DeprecationsService } from './deprecations_service'; -export type { DeprecationsServiceStart } from './deprecations_service'; -export type { ResolveDeprecationResponse } from './deprecations_client'; diff --git a/packages/core/deprecations/core-deprecations-browser-internal/tsconfig.json b/packages/core/deprecations/core-deprecations-browser-internal/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-internal/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/core/deprecations/core-deprecations-browser-mocks/BUILD.bazel b/packages/core/deprecations/core-deprecations-browser-mocks/BUILD.bazel new file mode 100644 index 0000000000000..8c840af011078 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-mocks/BUILD.bazel @@ -0,0 +1,110 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-deprecations-browser-mocks" +PKG_REQUIRE_NAME = "@kbn/core-deprecations-browser-mocks" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ + "//packages/core/deprecations/core-deprecations-browser-internal" +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "@npm//@types/react", + "//packages/kbn-utility-types:npm_module_types", + "//packages/core/deprecations/core-deprecations-browser:npm_module_types", + "//packages/core/deprecations/core-deprecations-browser-internal:npm_module_types" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/deprecations/core-deprecations-browser-mocks/README.md b/packages/core/deprecations/core-deprecations-browser-mocks/README.md new file mode 100644 index 0000000000000..a11bbcc144ebb --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-mocks/README.md @@ -0,0 +1,3 @@ +# @kbn/core-deprecations-browser-mocks + +Contains mocks for Core's client-side `deprecations` service diff --git a/packages/core/deprecations/core-deprecations-browser-mocks/jest.config.js b/packages/core/deprecations/core-deprecations-browser-mocks/jest.config.js new file mode 100644 index 0000000000000..4bfb844cf8fa3 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-mocks/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/deprecations/core-deprecations-browser-mocks'], +}; diff --git a/packages/core/deprecations/core-deprecations-browser-mocks/package.json b/packages/core/deprecations/core-deprecations-browser-mocks/package.json new file mode 100644 index 0000000000000..47b5aa1f0add2 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-mocks/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-deprecations-browser-mocks", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/src/core/public/deprecations/deprecations_service.mock.ts b/packages/core/deprecations/core-deprecations-browser-mocks/src/deprecations_service.mock.ts similarity index 88% rename from src/core/public/deprecations/deprecations_service.mock.ts rename to packages/core/deprecations/core-deprecations-browser-mocks/src/deprecations_service.mock.ts index 5bcd52982d513..f742f84036ea6 100644 --- a/src/core/public/deprecations/deprecations_service.mock.ts +++ b/packages/core/deprecations/core-deprecations-browser-mocks/src/deprecations_service.mock.ts @@ -7,8 +7,8 @@ */ import type { PublicMethodsOf } from '@kbn/utility-types'; -import { DeprecationsService } from './deprecations_service'; -import type { DeprecationsServiceStart } from './deprecations_service'; +import { DeprecationsService } from '@kbn/core-deprecations-browser-internal'; +import type { DeprecationsServiceStart } from '@kbn/core-deprecations-browser'; const createServiceMock = (): jest.Mocked => ({ getAllDeprecations: jest.fn().mockResolvedValue([]), diff --git a/packages/core/deprecations/core-deprecations-browser-mocks/src/index.ts b/packages/core/deprecations/core-deprecations-browser-mocks/src/index.ts new file mode 100644 index 0000000000000..1239090c387ad --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-mocks/src/index.ts @@ -0,0 +1,9 @@ +/* + * 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. + */ + +export { deprecationsServiceMock } from './deprecations_service.mock'; diff --git a/packages/core/deprecations/core-deprecations-browser-mocks/tsconfig.json b/packages/core/deprecations/core-deprecations-browser-mocks/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser-mocks/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/core/deprecations/core-deprecations-browser/BUILD.bazel b/packages/core/deprecations/core-deprecations-browser/BUILD.bazel new file mode 100644 index 0000000000000..85a9e6c411c21 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser/BUILD.bazel @@ -0,0 +1,107 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-deprecations-browser" +PKG_REQUIRE_NAME = "@kbn/core-deprecations-browser" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "@npm//@types/react", + "//packages/core/deprecations/core-deprecations-common:npm_module_types" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/deprecations/core-deprecations-browser/README.md b/packages/core/deprecations/core-deprecations-browser/README.md new file mode 100644 index 0000000000000..3c7bae6833733 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser/README.md @@ -0,0 +1,3 @@ +# @kbn/core-deprecations-browser + +Contains public types for Core's client-side `deprecations` service diff --git a/packages/core/deprecations/core-deprecations-browser/jest.config.js b/packages/core/deprecations/core-deprecations-browser/jest.config.js new file mode 100644 index 0000000000000..9f08c08e4fb41 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/deprecations/core-deprecations-browser'], +}; diff --git a/packages/core/deprecations/core-deprecations-browser/package.json b/packages/core/deprecations/core-deprecations-browser/package.json new file mode 100644 index 0000000000000..d4e5346ab80a8 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-deprecations-browser", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/src/core/public/deprecations/deprecations_service.ts b/packages/core/deprecations/core-deprecations-browser/src/contracts.ts similarity index 60% rename from src/core/public/deprecations/deprecations_service.ts rename to packages/core/deprecations/core-deprecations-browser/src/contracts.ts index bcc701cc634a0..c8e8d08e79848 100644 --- a/src/core/public/deprecations/deprecations_service.ts +++ b/packages/core/deprecations/core-deprecations-browser/src/contracts.ts @@ -5,11 +5,8 @@ * in compliance with, at your election, the Elastic License 2.0 or the Server * Side Public License, v 1. */ - -import type { CoreService } from '@kbn/core-base-browser-internal'; -import type { HttpStart } from '@kbn/core-http-browser'; -import { DeprecationsClient, ResolveDeprecationResponse } from './deprecations_client'; -import type { DomainDeprecationDetails } from '../../server/types'; +import type { DomainDeprecationDetails } from '@kbn/core-deprecations-common'; +import type { ResolveDeprecationResponse } from './types'; /** * DeprecationsService provides methods to fetch domain deprecation details from @@ -41,20 +38,3 @@ export interface DeprecationsServiceStart { */ resolveDeprecation: (details: DomainDeprecationDetails) => Promise; } - -export class DeprecationsService implements CoreService { - public setup(): void {} - - public start({ http }: { http: HttpStart }): DeprecationsServiceStart { - const deprecationsClient = new DeprecationsClient({ http }); - - return { - getAllDeprecations: deprecationsClient.getAllDeprecations, - getDeprecations: deprecationsClient.getDeprecations, - isDeprecationResolvable: deprecationsClient.isDeprecationResolvable, - resolveDeprecation: deprecationsClient.resolveDeprecation, - }; - } - - public stop(): void {} -} diff --git a/packages/core/deprecations/core-deprecations-browser/src/index.ts b/packages/core/deprecations/core-deprecations-browser/src/index.ts new file mode 100644 index 0000000000000..4ae415ba26f5e --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser/src/index.ts @@ -0,0 +1,10 @@ +/* + * 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. + */ + +export type { DeprecationsServiceStart } from './contracts'; +export type { ResolveDeprecationResponse } from './types'; diff --git a/packages/core/deprecations/core-deprecations-browser/src/types.ts b/packages/core/deprecations/core-deprecations-browser/src/types.ts new file mode 100644 index 0000000000000..a51174445edac --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser/src/types.ts @@ -0,0 +1,13 @@ +/* + * 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. + */ + +/** + * Response from correctiveActions.api call from automatically resolving the deprecation + * @public + */ +export type ResolveDeprecationResponse = { status: 'ok' } | { status: 'fail'; reason: string }; diff --git a/packages/core/deprecations/core-deprecations-browser/tsconfig.json b/packages/core/deprecations/core-deprecations-browser/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/deprecations/core-deprecations-browser/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/core/deprecations/core-deprecations-common/BUILD.bazel b/packages/core/deprecations/core-deprecations-common/BUILD.bazel new file mode 100644 index 0000000000000..7bddbc3cebaf7 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-common/BUILD.bazel @@ -0,0 +1,106 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-deprecations-common" +PKG_REQUIRE_NAME = "@kbn/core-deprecations-common" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "@npm//@types/react" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/deprecations/core-deprecations-common/README.md b/packages/core/deprecations/core-deprecations-common/README.md new file mode 100644 index 0000000000000..503006503c060 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-common/README.md @@ -0,0 +1,3 @@ +# @kbn/core-deprecations-common + +Contains public shared types for Core's `deprecations` service diff --git a/packages/core/deprecations/core-deprecations-common/jest.config.js b/packages/core/deprecations/core-deprecations-common/jest.config.js new file mode 100644 index 0000000000000..3a20374e4f7ad --- /dev/null +++ b/packages/core/deprecations/core-deprecations-common/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/deprecations/core-deprecations-common'], +}; diff --git a/packages/core/deprecations/core-deprecations-common/package.json b/packages/core/deprecations/core-deprecations-common/package.json new file mode 100644 index 0000000000000..66dd322302c60 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-common/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-deprecations-common", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/packages/core/deprecations/core-deprecations-common/src/index.ts b/packages/core/deprecations/core-deprecations-common/src/index.ts new file mode 100644 index 0000000000000..3013ad0f32281 --- /dev/null +++ b/packages/core/deprecations/core-deprecations-common/src/index.ts @@ -0,0 +1,16 @@ +/* + * 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. + */ + +export type { + BaseDeprecationDetails, + ConfigDeprecationDetails, + FeatureDeprecationDetails, + DeprecationsDetails, + DomainDeprecationDetails, + DeprecationsGetResponse, +} from './types'; diff --git a/packages/core/deprecations/core-deprecations-common/src/types.ts b/packages/core/deprecations/core-deprecations-common/src/types.ts new file mode 100644 index 0000000000000..8dc7a08923bad --- /dev/null +++ b/packages/core/deprecations/core-deprecations-common/src/types.ts @@ -0,0 +1,107 @@ +/* + * 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. + */ + +/** + * Base properties shared by all types of deprecations + * + * @public + */ +export interface BaseDeprecationDetails { + /** + * The title of the deprecation. + * Check the README for writing deprecations in `src/core/server/deprecations/README.mdx` + */ + title: string; + /** + * The description message to be displayed for the deprecation. + * Check the README for writing deprecations in `src/core/server/deprecations/README.mdx` + */ + message: string; + /** + * levels: + * - warning: will not break deployment upon upgrade + * - critical: needs to be addressed before upgrade. + * - fetch_error: Deprecations service failed to grab the deprecation details for the domain. + */ + level: 'warning' | 'critical' | 'fetch_error'; + /** + * (optional) Used to identify between different deprecation types. + * Example use case: in Upgrade Assistant, we may want to allow the user to sort by + * deprecation type or show each type in a separate tab. + * + * Feel free to add new types if necessary. + * Predefined types are necessary to reduce having similar definitions with different keywords + * across kibana deprecations. + */ + deprecationType?: 'config' | 'feature'; + /** (optional) link to the documentation for more details on the deprecation. */ + documentationUrl?: string; + /** (optional) specify the fix for this deprecation requires a full kibana restart. */ + requireRestart?: boolean; + /** corrective action needed to fix this deprecation. */ + correctiveActions: { + /** + * (optional) The api to be called to automatically fix the deprecation + * Each domain should implement a POST/PUT route for their plugin to + * handle their deprecations. + */ + api?: { + /** Kibana route path. Passing a query string is allowed */ + path: string; + /** Kibana route method: 'POST' or 'PUT'. */ + method: 'POST' | 'PUT'; + /** Additional details to be passed to the route. */ + body?: { + [key: string]: any; + }; + /* Allow to omit context in the request of the body */ + omitContextFromBody?: boolean; + }; + /** + * Specify a list of manual steps users need to follow to + * fix the deprecation before upgrade. Required even if an API + * corrective action is set in case the API fails. + * Check the README for writing deprecations in `src/core/server/deprecations/README.mdx` + */ + manualSteps: string[]; + }; +} + +/** + * @public + */ +export interface ConfigDeprecationDetails extends BaseDeprecationDetails { + configPath: string; + deprecationType: 'config'; +} + +/** + * @public + */ +export interface FeatureDeprecationDetails extends BaseDeprecationDetails { + deprecationType?: 'feature' | undefined; +} + +/** + * @public + */ +export type DeprecationsDetails = ConfigDeprecationDetails | FeatureDeprecationDetails; + +/** + * @public + */ +export type DomainDeprecationDetails = DeprecationsDetails & { + domainId: string; +}; + +/** + * @public + */ +export interface DeprecationsGetResponse { + deprecations: DomainDeprecationDetails[]; +} diff --git a/packages/core/deprecations/core-deprecations-common/tsconfig.json b/packages/core/deprecations/core-deprecations-common/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/deprecations/core-deprecations-common/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/src/core/public/core_system.ts b/src/core/public/core_system.ts index 636c44dd3a6e0..834927ae7f541 100644 --- a/src/core/public/core_system.ts +++ b/src/core/public/core_system.ts @@ -23,6 +23,7 @@ import { ExecutionContextService } from '@kbn/core-execution-context-browser-int import type { FatalErrorsSetup } from '@kbn/core-fatal-errors-browser'; import { FatalErrorsService } from '@kbn/core-fatal-errors-browser-internal'; import { HttpService } from '@kbn/core-http-browser-internal'; +import { DeprecationsService } from '@kbn/core-deprecations-browser-internal'; import { CoreSetup, CoreStart } from '.'; import { ChromeService } from './chrome'; import { NotificationsService } from './notifications'; @@ -33,7 +34,6 @@ import { ApplicationService } from './application'; import { RenderingService } from './rendering'; import { SavedObjectsService } from './saved_objects'; import { IntegrationsService } from './integrations'; -import { DeprecationsService } from './deprecations'; import { CoreApp } from './core_app'; import type { InternalApplicationSetup, InternalApplicationStart } from './application/types'; import { fetchOptionalMemoryInfo } from './fetch_optional_memory_info'; diff --git a/src/core/public/index.ts b/src/core/public/index.ts index 5e224c38a2dc4..b3ffc84a51f58 100644 --- a/src/core/public/index.ts +++ b/src/core/public/index.ts @@ -42,6 +42,7 @@ import type { FatalErrorsStart, FatalErrorInfo, } from '@kbn/core-fatal-errors-browser'; +import type { DeprecationsServiceStart } from '@kbn/core-deprecations-browser'; import type { ChromeBadge, ChromeBreadcrumb, @@ -75,10 +76,9 @@ import type { import type { UiSettingsState, IUiSettingsClient } from './ui_settings'; import type { ApplicationSetup, Capabilities, ApplicationStart } from './application'; import type { SavedObjectsStart } from './saved_objects'; -import type { DeprecationsServiceStart } from './deprecations'; export type { PackageInfo, EnvironmentMode } from '@kbn/config'; -export type { DomainDeprecationDetails } from '../server/types'; +export type { DomainDeprecationDetails } from '@kbn/core-deprecations-common'; export type { CoreContext } from '@kbn/core-base-browser-internal'; export type { CoreSystem } from './core_system'; export { DEFAULT_APP_CATEGORIES, APP_WRAPPER_CLASS } from '../utils'; @@ -210,7 +210,10 @@ export type { export type { ThemeServiceSetup, ThemeServiceStart, CoreTheme } from '@kbn/core-theme-browser'; -export type { DeprecationsServiceStart, ResolveDeprecationResponse } from './deprecations'; +export type { + DeprecationsServiceStart, + ResolveDeprecationResponse, +} from '@kbn/core-deprecations-browser'; export type { MountPoint, UnmountCallback, PublicUiSettingsParams } from './types'; diff --git a/src/core/public/mocks.ts b/src/core/public/mocks.ts index b3070d46feee8..97f3af9f33cca 100644 --- a/src/core/public/mocks.ts +++ b/src/core/public/mocks.ts @@ -17,6 +17,7 @@ import { executionContextServiceMock } from '@kbn/core-execution-context-browser import { i18nServiceMock } from '@kbn/core-i18n-browser-mocks'; import { fatalErrorsServiceMock } from '@kbn/core-fatal-errors-browser-mocks'; import { httpServiceMock } from '@kbn/core-http-browser-mocks'; +import { deprecationsServiceMock } from '@kbn/core-deprecations-browser-mocks'; import type { PluginInitializerContext, AppMountParameters } from '.'; // Import values from their individual modules instead. import { ScopedHistory } from './application'; @@ -26,7 +27,6 @@ import { notificationServiceMock } from './notifications/notifications_service.m import { overlayServiceMock } from './overlays/overlay_service.mock'; import { uiSettingsServiceMock } from './ui_settings/ui_settings_service.mock'; import { savedObjectsServiceMock } from './saved_objects/saved_objects_service.mock'; -import { deprecationsServiceMock } from './deprecations/deprecations_service.mock'; export { injectedMetadataServiceMock } from '@kbn/core-injected-metadata-browser-mocks'; export { docLinksServiceMock } from '@kbn/core-doc-links-browser-mocks'; @@ -43,7 +43,7 @@ export { uiSettingsServiceMock } from './ui_settings/ui_settings_service.mock'; export { savedObjectsServiceMock } from './saved_objects/saved_objects_service.mock'; export { scopedHistoryMock } from './application/scoped_history.mock'; export { applicationServiceMock } from './application/application_service.mock'; -export { deprecationsServiceMock } from './deprecations/deprecations_service.mock'; +export { deprecationsServiceMock } from '@kbn/core-deprecations-browser-mocks'; function createCoreSetupMock({ basePath = '', diff --git a/src/core/public/plugins/plugins_service.test.ts b/src/core/public/plugins/plugins_service.test.ts index d956b0e8599a3..d6b7810f44cd6 100644 --- a/src/core/public/plugins/plugins_service.test.ts +++ b/src/core/public/plugins/plugins_service.test.ts @@ -38,7 +38,7 @@ import { uiSettingsServiceMock } from '../ui_settings/ui_settings_service.mock'; import { httpServiceMock } from '@kbn/core-http-browser-mocks'; import type { CoreSetup, CoreStart, PluginInitializerContext } from '..'; import { savedObjectsServiceMock } from '../saved_objects/saved_objects_service.mock'; -import { deprecationsServiceMock } from '../deprecations/deprecations_service.mock'; +import { deprecationsServiceMock } from '@kbn/core-deprecations-browser-mocks'; export let mockPluginInitializers: Map; diff --git a/src/core/server/deprecations/deprecations_factory.test.ts b/src/core/server/deprecations/deprecations_factory.test.ts index b05a3ea3ce4dc..3ae83a1886e5c 100644 --- a/src/core/server/deprecations/deprecations_factory.test.ts +++ b/src/core/server/deprecations/deprecations_factory.test.ts @@ -9,7 +9,7 @@ import type { GetDeprecationsContext } from './types'; import { DeprecationsFactory, DeprecationsFactoryConfig } from './deprecations_factory'; import { loggerMock } from '@kbn/logging-mocks'; -import { DeprecationsDetails } from './types'; +import type { DeprecationsDetails } from '@kbn/core-deprecations-common'; describe('DeprecationsFactory', () => { let logger: ReturnType; diff --git a/src/core/server/deprecations/deprecations_factory.ts b/src/core/server/deprecations/deprecations_factory.ts index d36d61fa2eab2..514817ed1c12a 100644 --- a/src/core/server/deprecations/deprecations_factory.ts +++ b/src/core/server/deprecations/deprecations_factory.ts @@ -8,12 +8,9 @@ import { i18n } from '@kbn/i18n'; import type { Logger } from '@kbn/logging'; +import type { DomainDeprecationDetails, DeprecationsDetails } from '@kbn/core-deprecations-common'; import { DeprecationsRegistry } from './deprecations_registry'; -import type { - DomainDeprecationDetails, - DeprecationsDetails, - GetDeprecationsContext, -} from './types'; +import type { GetDeprecationsContext } from './types'; export interface DeprecationsFactoryDeps { logger: Logger; diff --git a/src/core/server/deprecations/deprecations_registry.ts b/src/core/server/deprecations/deprecations_registry.ts index e979bb94712e6..6e59504d0d1d7 100644 --- a/src/core/server/deprecations/deprecations_registry.ts +++ b/src/core/server/deprecations/deprecations_registry.ts @@ -7,12 +7,8 @@ */ import { withTimeout, isPromise } from '@kbn/std'; -import type { - DeprecationsDetails, - RegisterDeprecationsConfig, - GetDeprecationsContext, -} from './types'; - +import type { DeprecationsDetails } from '@kbn/core-deprecations-common'; +import type { RegisterDeprecationsConfig, GetDeprecationsContext } from './types'; const MsInSec = 1000; export class DeprecationsRegistry { diff --git a/src/core/server/deprecations/deprecations_service.ts b/src/core/server/deprecations/deprecations_service.ts index 6d8aef2ef84e8..7b07b4c1d10de 100644 --- a/src/core/server/deprecations/deprecations_service.ts +++ b/src/core/server/deprecations/deprecations_service.ts @@ -7,13 +7,13 @@ */ import { firstValueFrom } from 'rxjs'; - import type { Logger } from '@kbn/logging'; import type { IConfigService } from '@kbn/config'; import type { CoreContext, CoreService } from '@kbn/core-base-server-internal'; +import { DomainDeprecationDetails } from '@kbn/core-deprecations-common'; import type { InternalHttpServiceSetup } from '@kbn/core-http-server-internal'; import { DeprecationsFactory } from './deprecations_factory'; -import { DomainDeprecationDetails, RegisterDeprecationsConfig } from './types'; +import { RegisterDeprecationsConfig } from './types'; import { registerRoutes } from './routes'; import { config as deprecationConfig, DeprecationConfigType } from './deprecation_config'; import { IScopedClusterClient } from '../elasticsearch/client'; diff --git a/src/core/server/deprecations/index.ts b/src/core/server/deprecations/index.ts index 9245179d3099a..db6fe8193867d 100644 --- a/src/core/server/deprecations/index.ts +++ b/src/core/server/deprecations/index.ts @@ -6,15 +6,7 @@ * Side Public License, v 1. */ -export type { - BaseDeprecationDetails, - DeprecationsDetails, - ConfigDeprecationDetails, - FeatureDeprecationDetails, - GetDeprecationsContext, - RegisterDeprecationsConfig, - DeprecationsGetResponse, -} from './types'; +export type { GetDeprecationsContext, RegisterDeprecationsConfig } from './types'; export type { DeprecationsServiceSetup, diff --git a/src/core/server/deprecations/routes/get.ts b/src/core/server/deprecations/routes/get.ts index a3ea08f04d706..1ae70e47c2b62 100644 --- a/src/core/server/deprecations/routes/get.ts +++ b/src/core/server/deprecations/routes/get.ts @@ -6,7 +6,7 @@ * Side Public License, v 1. */ -import type { DeprecationsGetResponse } from '../types'; +import type { DeprecationsGetResponse } from '@kbn/core-deprecations-common'; import type { InternalDeprecationRouter } from '../internal_types'; export const registerGetRoute = (router: InternalDeprecationRouter) => { diff --git a/src/core/server/deprecations/types.ts b/src/core/server/deprecations/types.ts index 3990a76f7578e..16104c6f9cc57 100644 --- a/src/core/server/deprecations/types.ts +++ b/src/core/server/deprecations/types.ts @@ -7,102 +7,10 @@ */ import type { MaybePromise } from '@kbn/utility-types'; +import type { DeprecationsDetails } from '@kbn/core-deprecations-common'; import type { SavedObjectsClientContract } from '../saved_objects/types'; import type { IScopedClusterClient } from '../elasticsearch'; -/** - * Base properties shared by all types of deprecations - * - * @public - */ -export interface BaseDeprecationDetails { - /** - * The title of the deprecation. - * Check the README for writing deprecations in `src/core/server/deprecations/README.mdx` - */ - title: string; - /** - * The description message to be displayed for the deprecation. - * Check the README for writing deprecations in `src/core/server/deprecations/README.mdx` - */ - message: string; - /** - * levels: - * - warning: will not break deployment upon upgrade - * - critical: needs to be addressed before upgrade. - * - fetch_error: Deprecations service failed to grab the deprecation details for the domain. - */ - level: 'warning' | 'critical' | 'fetch_error'; - /** - * (optional) Used to identify between different deprecation types. - * Example use case: in Upgrade Assistant, we may want to allow the user to sort by - * deprecation type or show each type in a separate tab. - * - * Feel free to add new types if necessary. - * Predefined types are necessary to reduce having similar definitions with different keywords - * across kibana deprecations. - */ - deprecationType?: 'config' | 'feature'; - /** (optional) link to the documentation for more details on the deprecation. */ - documentationUrl?: string; - /** (optional) specify the fix for this deprecation requires a full kibana restart. */ - requireRestart?: boolean; - /** corrective action needed to fix this deprecation. */ - correctiveActions: { - /** - * (optional) The api to be called to automatically fix the deprecation - * Each domain should implement a POST/PUT route for their plugin to - * handle their deprecations. - */ - api?: { - /** Kibana route path. Passing a query string is allowed */ - path: string; - /** Kibana route method: 'POST' or 'PUT'. */ - method: 'POST' | 'PUT'; - /** Additional details to be passed to the route. */ - body?: { - [key: string]: any; - }; - /* Allow to omit context in the request of the body */ - omitContextFromBody?: boolean; - }; - /** - * Specify a list of manual steps users need to follow to - * fix the deprecation before upgrade. Required even if an API - * corrective action is set in case the API fails. - * Check the README for writing deprecations in `src/core/server/deprecations/README.mdx` - */ - manualSteps: string[]; - }; -} - -/** - * @public - */ -export interface ConfigDeprecationDetails extends BaseDeprecationDetails { - configPath: string; - deprecationType: 'config'; -} - -/** - * @public - */ -export interface FeatureDeprecationDetails extends BaseDeprecationDetails { - deprecationType?: 'feature' | undefined; -} - -/** - * @public - */ -export type DeprecationsDetails = ConfigDeprecationDetails | FeatureDeprecationDetails; - -/** - * @internal - */ -export type DomainDeprecationDetails = DeprecationsDetails & { - domainId: string; -}; - /** * @public */ @@ -117,10 +25,3 @@ export interface GetDeprecationsContext { esClient: IScopedClusterClient; savedObjectsClient: SavedObjectsClientContract; } - -/** - * @public - */ -export interface DeprecationsGetResponse { - deprecations: DomainDeprecationDetails[]; -} diff --git a/src/core/server/index.ts b/src/core/server/index.ts index 9dc6a88bacca5..82d98f875241e 100644 --- a/src/core/server/index.ts +++ b/src/core/server/index.ts @@ -405,17 +405,13 @@ export { EventLoopDelaysMonitor } from './metrics'; export type { I18nServiceSetup } from './i18n'; export type { - BaseDeprecationDetails, - DeprecationsDetails, - ConfigDeprecationDetails, - FeatureDeprecationDetails, RegisterDeprecationsConfig, GetDeprecationsContext, DeprecationsServiceSetup, DeprecationsClient, DeprecationsRequestHandlerContext, } from './deprecations'; - +export type { DeprecationsDetails } from '@kbn/core-deprecations-common'; export type { AppCategory } from '../types'; export { DEFAULT_APP_CATEGORIES, APP_WRAPPER_CLASS } from '../utils'; diff --git a/src/core/server/saved_objects/deprecations/unknown_object_types.ts b/src/core/server/saved_objects/deprecations/unknown_object_types.ts index 9e48c84860b48..d8762ebcfd1bd 100644 --- a/src/core/server/saved_objects/deprecations/unknown_object_types.ts +++ b/src/core/server/saved_objects/deprecations/unknown_object_types.ts @@ -7,7 +7,7 @@ */ import { i18n } from '@kbn/i18n'; -import type { DeprecationsDetails } from '../../deprecations'; +import type { DeprecationsDetails } from '@kbn/core-deprecations-common'; import { IScopedClusterClient } from '../../elasticsearch'; import { getAggregatedTypesDocuments } from '../migrations/actions/check_for_unknown_docs'; import { addExcludedTypesToBoolQuery } from '../migrations/model/helpers'; diff --git a/src/core/server/types.ts b/src/core/server/types.ts index 0e49ebbf851d6..1bcdd1ac09535 100644 --- a/src/core/server/types.ts +++ b/src/core/server/types.ts @@ -42,6 +42,9 @@ export type { SavedObjectReferenceWithContext, SavedObjectsCollectMultiNamespaceReferencesResponse, } from './saved_objects/service'; -export type { DomainDeprecationDetails, DeprecationsGetResponse } from './deprecations/types'; +export type { + DomainDeprecationDetails, + DeprecationsGetResponse, +} from '@kbn/core-deprecations-common'; export * from './ui_settings/types'; export type { ExternalUrlConfig } from '@kbn/core-http-server-internal'; diff --git a/yarn.lock b/yarn.lock index 645740bce7b48..47a0d08a5b1c7 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3104,6 +3104,22 @@ version "0.0.0" uid "" +"@kbn/core-deprecations-browser-internal@link:bazel-bin/packages/core/deprecations/core-deprecations-browser-internal": + version "0.0.0" + uid "" + +"@kbn/core-deprecations-browser-mocks@link:bazel-bin/packages/core/deprecations/core-deprecations-browser-mocks": + version "0.0.0" + uid "" + +"@kbn/core-deprecations-browser@link:bazel-bin/packages/core/deprecations/core-deprecations-browser": + version "0.0.0" + uid "" + +"@kbn/core-deprecations-common@link:bazel-bin/packages/core/deprecations/core-deprecations-common": + version "0.0.0" + uid "" + "@kbn/core-doc-links-browser-internal@link:bazel-bin/packages/core/doc-links/core-doc-links-browser-internal": version "0.0.0" uid "" @@ -6723,6 +6739,22 @@ version "0.0.0" uid "" +"@types/kbn__core-deprecations-browser-internal@link:bazel-bin/packages/core/deprecations/core-deprecations-browser-internal/npm_module_types": + version "0.0.0" + uid "" + +"@types/kbn__core-deprecations-browser-mocks@link:bazel-bin/packages/core/deprecations/core-deprecations-browser-mocks/npm_module_types": + version "0.0.0" + uid "" + +"@types/kbn__core-deprecations-browser@link:bazel-bin/packages/core/deprecations/core-deprecations-browser/npm_module_types": + version "0.0.0" + uid "" + +"@types/kbn__core-deprecations-common@link:bazel-bin/packages/core/deprecations/core-deprecations-common/npm_module_types": + version "0.0.0" + uid "" + "@types/kbn__core-doc-links-browser-internal@link:bazel-bin/packages/core/doc-links/core-doc-links-browser-internal/npm_module_types": version "0.0.0" uid "" From 5a09b74cef9ec7cc4db9f862814f21a875ae206a Mon Sep 17 00:00:00 2001 From: Nicolas Chaulet Date: Wed, 13 Jul 2022 19:02:41 -0400 Subject: [PATCH 005/111] [Fleet] Remove licence restrictions for bulk reassign and bulk unenroll (#136334) --- x-pack/plugins/fleet/server/routes/agent/handlers.ts | 8 -------- .../plugins/fleet/server/routes/agent/unenroll_handler.ts | 8 -------- 2 files changed, 16 deletions(-) diff --git a/x-pack/plugins/fleet/server/routes/agent/handlers.ts b/x-pack/plugins/fleet/server/routes/agent/handlers.ts index 8f5797d0d3cf3..7a10a50e2fb7b 100644 --- a/x-pack/plugins/fleet/server/routes/agent/handlers.ts +++ b/x-pack/plugins/fleet/server/routes/agent/handlers.ts @@ -29,7 +29,6 @@ import type { PostBulkUpdateAgentTagsRequestSchema, } from '../../types'; import { defaultIngestErrorHandler } from '../../errors'; -import { licenseService } from '../../services'; import * as AgentService from '../../services/agents'; export const getAgentHandler: RequestHandler< @@ -214,13 +213,6 @@ export const postBulkAgentsReassignHandler: RequestHandler< undefined, TypeOf > = async (context, request, response) => { - if (!licenseService.isGoldPlus()) { - return response.customError({ - statusCode: 403, - body: { message: 'Requires Gold license' }, - }); - } - const coreContext = await context.core; const soClient = coreContext.savedObjects.client; const esClient = coreContext.elasticsearch.client.asInternalUser; diff --git a/x-pack/plugins/fleet/server/routes/agent/unenroll_handler.ts b/x-pack/plugins/fleet/server/routes/agent/unenroll_handler.ts index 257112dc6872d..b6e398d269a6f 100644 --- a/x-pack/plugins/fleet/server/routes/agent/unenroll_handler.ts +++ b/x-pack/plugins/fleet/server/routes/agent/unenroll_handler.ts @@ -16,7 +16,6 @@ import type { PostAgentUnenrollRequestSchema, PostBulkAgentUnenrollRequestSchema, } from '../../types'; -import { licenseService } from '../../services'; import * as AgentService from '../../services/agents'; import { defaultIngestErrorHandler } from '../../errors'; @@ -46,13 +45,6 @@ export const postBulkAgentsUnenrollHandler: RequestHandler< undefined, TypeOf > = async (context, request, response) => { - if (!licenseService.isGoldPlus()) { - return response.customError({ - statusCode: 403, - body: { message: 'Requires Gold license' }, - }); - } - const coreContext = await context.core; const soClient = coreContext.savedObjects.client; const esClient = coreContext.elasticsearch.client.asInternalUser; From 65e307086fceceeac30e13142523abeedd6cdf6c Mon Sep 17 00:00:00 2001 From: Muhammad Ibragimov <53621505+mibragimov@users.noreply.github.com> Date: Thu, 14 Jul 2022 08:53:51 +0500 Subject: [PATCH 006/111] [Console] Handle encoded characters in API requests (#135441) * [Console] Handle encoded characters in API requests * Add a functional test for requests with query params Co-authored-by: Muhammad Ibragimov --- .../network_request_status_bar.tsx | 5 +- .../console/server/lib/proxy_request.test.ts | 113 ++++++++++-------- .../console/server/lib/proxy_request.ts | 27 ++--- .../server/lib/utils/encode_path.test.ts | 37 ++++++ .../console/server/lib/utils/encode_path.ts | 28 +++++ src/plugins/console/server/lib/utils/index.ts | 9 ++ .../api/console/proxy/create_handler.ts | 5 + test/functional/apps/console/_console.ts | 16 +++ test/functional/page_objects/console_page.ts | 6 + 9 files changed, 172 insertions(+), 74 deletions(-) create mode 100644 src/plugins/console/server/lib/utils/encode_path.test.ts create mode 100644 src/plugins/console/server/lib/utils/encode_path.ts create mode 100644 src/plugins/console/server/lib/utils/index.ts diff --git a/src/plugins/console/public/application/components/network_request_status_bar/network_request_status_bar.tsx b/src/plugins/console/public/application/components/network_request_status_bar/network_request_status_bar.tsx index d5d8d97a4712a..320b0bbfee473 100644 --- a/src/plugins/console/public/application/components/network_request_status_bar/network_request_status_bar.tsx +++ b/src/plugins/console/public/application/components/network_request_status_bar/network_request_status_bar.tsx @@ -80,7 +80,10 @@ export const NetworkRequestStatusBar: FunctionComponent = ({ }`} } > - + {/* Use   to ensure that no matter the width we don't allow line breaks */} {statusCode} - {statusText} diff --git a/src/plugins/console/server/lib/proxy_request.test.ts b/src/plugins/console/server/lib/proxy_request.test.ts index 98c63d9685c87..10f43e0a8f11b 100644 --- a/src/plugins/console/server/lib/proxy_request.test.ts +++ b/src/plugins/console/server/lib/proxy_request.test.ts @@ -6,7 +6,7 @@ * Side Public License, v 1. */ -import http, { ClientRequest } from 'http'; +import http, { ClientRequest, OutgoingHttpHeaders } from 'http'; import * as sinon from 'sinon'; import { proxyRequest } from './proxy_request'; import { URL } from 'url'; @@ -29,6 +29,28 @@ describe(`Console's send request`, () => { fakeRequest = null as any; }); + const sendProxyRequest = async ({ + headers = {}, + uri = new URL('http://noone.nowhere.none'), + timeout = 3000, + requestPath = '', + }: { + headers?: OutgoingHttpHeaders; + uri?: URL; + timeout?: number; + requestPath?: string; + }) => { + return await proxyRequest({ + agent: null as any, + headers, + method: 'get', + payload: null as any, + uri, + timeout, + requestPath, + }); + }; + it('correctly implements timeout and abort mechanism', async () => { fakeRequest = { destroy: sinon.stub(), @@ -36,14 +58,7 @@ describe(`Console's send request`, () => { once() {}, } as any; try { - await proxyRequest({ - agent: null as any, - headers: {}, - method: 'get', - payload: null as any, - timeout: 0, // immediately timeout - uri: new URL('http://noone.nowhere.none'), - }); + await sendProxyRequest({ timeout: 0 }); // immediately timeout fail('Should not reach here!'); } catch (e) { expect(e.message).toEqual('Client request timeout'); @@ -63,16 +78,9 @@ describe(`Console's send request`, () => { } as any; // Don't set a host header this time - const result1 = await proxyRequest({ - agent: null as any, - headers: {}, - method: 'get', - payload: null as any, - timeout: 30000, - uri: new URL('http://noone.nowhere.none'), - }); + const defaultResult = await sendProxyRequest({}); - expect(result1).toEqual('done'); + expect(defaultResult).toEqual('done'); const [httpRequestOptions1] = stub.firstCall.args; @@ -83,16 +91,9 @@ describe(`Console's send request`, () => { }); // Set a host header - const result2 = await proxyRequest({ - agent: null as any, - headers: { Host: 'myhost' }, - method: 'get', - payload: null as any, - timeout: 30000, - uri: new URL('http://noone.nowhere.none'), - }); + const resultWithHostHeader = await sendProxyRequest({ headers: { Host: 'myhost' } }); - expect(result2).toEqual('done'); + expect(resultWithHostHeader).toEqual('done'); const [httpRequestOptions2] = stub.secondCall.args; expect((httpRequestOptions2 as any).headers).toEqual({ @@ -102,7 +103,7 @@ describe(`Console's send request`, () => { }); }); - describe('with percent-encoded uri pathname', () => { + describe('with request path', () => { beforeEach(() => { fakeRequest = { abort: sinon.stub(), @@ -115,39 +116,45 @@ describe(`Console's send request`, () => { } as any; }); - it('should decode percent-encoded uri pathname and encode it correctly', async () => { - const uri = new URL( - `http://noone.nowhere.none/%{[@metadata][beat]}-%{[@metadata][version]}-2020.08.23` - ); - const result = await proxyRequest({ - agent: null as any, - headers: {}, - method: 'get', - payload: null as any, - timeout: 30000, + const verifyRequestPath = async ({ + initialPath, + expectedPath, + uri, + }: { + initialPath: string; + expectedPath: string; + uri?: URL; + }) => { + const result = await sendProxyRequest({ + requestPath: initialPath, uri, }); - expect(result).toEqual('done'); const [httpRequestOptions] = stub.firstCall.args; - expect((httpRequestOptions as any).path).toEqual( - '/%25%7B%5B%40metadata%5D%5Bbeat%5D%7D-%25%7B%5B%40metadata%5D%5Bversion%5D%7D-2020.08.23' - ); + expect((httpRequestOptions as any).path).toEqual(expectedPath); + }; + + it('should correctly encode invalid URL characters included in path', async () => { + await verifyRequestPath({ + initialPath: '%{[@metadata][beat]}-%{[@metadata][version]}-2020.08.23', + expectedPath: + '%25%7B%5B%40metadata%5D%5Bbeat%5D%7D-%25%7B%5B%40metadata%5D%5Bversion%5D%7D-2020.08.23', + }); }); - it('should issue request with date-math format', async () => { - const result = await proxyRequest({ - agent: null as any, - headers: {}, - method: 'get', - payload: null as any, - timeout: 30000, - uri: new URL(`http://noone.nowhere.none/%3Cmy-index-%7Bnow%2Fd%7D%3E`), + it('should not encode the path if it is encoded', async () => { + await verifyRequestPath({ + initialPath: '%3Cmy-index-%7Bnow%2Fd%7D%3E', + expectedPath: '%3Cmy-index-%7Bnow%2Fd%7D%3E', }); + }); - expect(result).toEqual('done'); - const [httpRequestOptions] = stub.firstCall.args; - expect((httpRequestOptions as any).path).toEqual('/%3Cmy-index-%7Bnow%2Fd%7D%3E'); + it('should correctly encode path with query params', async () => { + await verifyRequestPath({ + initialPath: '_index/.test', + uri: new URL('http://noone.nowhere.none/_index/.test?q=something&v=something'), + expectedPath: '_index/.test?q=something&v=something', + }); }); }); }); diff --git a/src/plugins/console/server/lib/proxy_request.ts b/src/plugins/console/server/lib/proxy_request.ts index 4a8839d1d8583..35452b4f99703 100644 --- a/src/plugins/console/server/lib/proxy_request.ts +++ b/src/plugins/console/server/lib/proxy_request.ts @@ -11,8 +11,9 @@ import https from 'https'; import net from 'net'; import stream from 'stream'; import Boom from '@hapi/boom'; -import { URL, URLSearchParams } from 'url'; -import { trimStart } from 'lodash'; +import { URL } from 'url'; + +import { encodePath } from './utils'; interface Args { method: 'get' | 'post' | 'put' | 'delete' | 'patch' | 'head'; @@ -22,6 +23,7 @@ interface Args { timeout: number; headers: http.OutgoingHttpHeaders; rejectUnauthorized?: boolean; + requestPath: string; } /** @@ -31,22 +33,6 @@ interface Args { const sanitizeHostname = (hostName: string): string => hostName.trim().replace(/^\[/, '').replace(/\]$/, ''); -/** - * Node URL percent-encodes any invalid characters in the pathname which results a 400 bad request error. - * We need to decode the percent-encoded pathname, and encode it correctly with encodeURIComponent - */ - -const encodePathname = (pathname: string) => { - const decodedPath = new URLSearchParams(`path=${pathname}`).get('path') ?? ''; - - // Skip if it is valid - if (pathname === decodedPath) { - return pathname; - } - - return `/${encodeURIComponent(trimStart(decodedPath, '/'))}`; -}; - // We use a modified version of Hapi's Wreck because Hapi, Axios, and Superagent don't support GET requests // with bodies, but ES APIs do. Similarly with DELETE requests with bodies. Another library, `request` // diverged too much from current behaviour. @@ -58,10 +44,11 @@ export const proxyRequest = ({ timeout, payload, rejectUnauthorized, + requestPath, }: Args) => { - const { hostname, port, protocol, pathname, search } = uri; + const { hostname, port, protocol, search } = uri; const client = uri.protocol === 'https:' ? https : http; - const encodedPath = encodePathname(pathname); + const encodedPath = encodePath(requestPath); let resolved = false; let resolve: (res: http.IncomingMessage) => void; diff --git a/src/plugins/console/server/lib/utils/encode_path.test.ts b/src/plugins/console/server/lib/utils/encode_path.test.ts new file mode 100644 index 0000000000000..07c7108e9d2cf --- /dev/null +++ b/src/plugins/console/server/lib/utils/encode_path.test.ts @@ -0,0 +1,37 @@ +/* + * 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 { encodePath } from './encode_path'; + +describe('encodePath', () => { + const tests = [ + { + description: 'encodes invalid URL characters', + source: '/%{[@metadata][beat]}-%{[@metadata][version]}-2020.08.23', + assert: + '/%25%7B%5B%40metadata%5D%5Bbeat%5D%7D-%25%7B%5B%40metadata%5D%5Bversion%5D%7D-2020.08.23', + }, + { + description: 'ignores encoded characters', + source: '/my-index/_doc/this%2Fis%2Fa%2Fdoc', + assert: '/my-index/_doc/this%2Fis%2Fa%2Fdoc', + }, + { + description: 'ignores slashes between', + source: '_index/test/.test', + assert: '_index/test/.test', + }, + ]; + + tests.forEach(({ description, source, assert }) => { + test(description, () => { + const result = encodePath(source); + expect(result).toEqual(assert); + }); + }); +}); diff --git a/src/plugins/console/server/lib/utils/encode_path.ts b/src/plugins/console/server/lib/utils/encode_path.ts new file mode 100644 index 0000000000000..273c60d3f66e4 --- /dev/null +++ b/src/plugins/console/server/lib/utils/encode_path.ts @@ -0,0 +1,28 @@ +/* + * 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 { URLSearchParams } from 'url'; +import { trimStart } from 'lodash'; + +export const encodePath = (path: string) => { + const decodedPath = new URLSearchParams(`path=${path}`).get('path') ?? ''; + // Take the initial path and compare it with the decoded path. + // If the result is not the same, the path is encoded. + const isEncoded = trimStart(path, '/') !== trimStart(decodedPath, '/'); + + // Return the initial path if it is already encoded + if (isEncoded) { + return path; + } + + // Encode every component except slashes + return path + .split('/') + .map((component) => encodeURIComponent(component)) + .join('/'); +}; diff --git a/src/plugins/console/server/lib/utils/index.ts b/src/plugins/console/server/lib/utils/index.ts new file mode 100644 index 0000000000000..19c35901570e6 --- /dev/null +++ b/src/plugins/console/server/lib/utils/index.ts @@ -0,0 +1,9 @@ +/* + * 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. + */ + +export { encodePath } from './encode_path'; diff --git a/src/plugins/console/server/routes/api/console/proxy/create_handler.ts b/src/plugins/console/server/routes/api/console/proxy/create_handler.ts index 1fc22ca685cc5..2e575c7723a64 100644 --- a/src/plugins/console/server/routes/api/console/proxy/create_handler.ts +++ b/src/plugins/console/server/routes/api/console/proxy/create_handler.ts @@ -145,6 +145,10 @@ export const createHandler = const host = hosts[idx]; try { const uri = toURL(host, path); + // Invalid URL characters included in uri pathname will be percent-encoded by Node URL method, and results in a faulty request in some cases. + // To fix this issue, we need to extract the original request path and supply it to proxyRequest function to encode it correctly with encodeURIComponent. + // We ignore the search params here, since we are extracting them from the uri constructed by Node URL method. + const [requestPath] = path.split('?'); // Because this can technically be provided by a settings-defined proxy config, we need to // preserve these property names to maintain BWC. @@ -174,6 +178,7 @@ export const createHandler = payload: body, rejectUnauthorized, agent, + requestPath, }); break; diff --git a/test/functional/apps/console/_console.ts b/test/functional/apps/console/_console.ts index de4ed241f4110..f22a46c838ae9 100644 --- a/test/functional/apps/console/_console.ts +++ b/test/functional/apps/console/_console.ts @@ -124,6 +124,22 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { }); }); + describe('with query params', () => { + it('should issue a successful request', async () => { + await PageObjects.console.clearTextArea(); + await PageObjects.console.enterRequest( + '\n GET _cat/aliases?format=json&v=true&pretty=true' + ); + await PageObjects.console.clickPlay(); + await PageObjects.header.waitUntilLoadingHasFinished(); + + await retry.try(async () => { + const status = await PageObjects.console.getResponseStatus(); + expect(status).to.eql(200); + }); + }); + }); + describe('multiple requests output', () => { const sendMultipleRequests = async (requests: string[]) => { await asyncForEach(requests, async (request) => { diff --git a/test/functional/page_objects/console_page.ts b/test/functional/page_objects/console_page.ts index 17ab4e1b170f7..3a5c8e3d84db4 100644 --- a/test/functional/page_objects/console_page.ts +++ b/test/functional/page_objects/console_page.ts @@ -221,4 +221,10 @@ export class ConsolePageObject extends FtrService { return false; } } + + public async getResponseStatus() { + const statusBadge = await this.testSubjects.find('consoleResponseStatusBadge'); + const text = await statusBadge.getVisibleText(); + return text.replace(/[^\d.]+/, ''); + } } From a1c2220566adac87a71e62cf5022fd8d7b5cad18 Mon Sep 17 00:00:00 2001 From: Spencer Date: Wed, 13 Jul 2022 23:37:39 -0500 Subject: [PATCH 007/111] [checks] disable spinners in CI to cut-down on log sizes (#136341) --- .../src/cli/run_telemetry_check.ts | 112 +++++++++--------- .../src/cli/run_telemetry_extract.ts | 39 +++--- src/dev/run_i18n_check.ts | 1 + src/dev/run_i18n_extract.ts | 55 +++++---- src/dev/run_i18n_integrate.ts | 57 +++++---- x-pack/plugins/apm/scripts/precommit.js | 6 +- 6 files changed, 148 insertions(+), 122 deletions(-) diff --git a/packages/kbn-telemetry-tools/src/cli/run_telemetry_check.ts b/packages/kbn-telemetry-tools/src/cli/run_telemetry_check.ts index 4518b3631a2a0..ed5a7ff8b8135 100644 --- a/packages/kbn-telemetry-tools/src/cli/run_telemetry_check.ts +++ b/packages/kbn-telemetry-tools/src/cli/run_telemetry_check.ts @@ -48,64 +48,70 @@ export function runTelemetryCheck() { ); } - const list = new Listr([ - { - title: 'Checking .telemetryrc.json files', - task: () => new Listr(parseConfigsTask(), { exitOnError: true }), - }, - { - title: 'Extracting Collectors', - task: (context) => new Listr(extractCollectorsTask(context, path), { exitOnError: true }), - }, - { - enabled: () => typeof path !== 'undefined', - title: 'Checking collectors in --path are not excluded', - task: ({ roots }: TaskContext) => { - const totalCollections = roots.reduce((acc, root) => { - return acc + (root.parsedCollections?.length || 0); - }, 0); - const collectorsInPath = Array.isArray(path) ? path.length : 1; + const list = new Listr( + [ + { + title: 'Checking .telemetryrc.json files', + task: () => new Listr(parseConfigsTask(), { exitOnError: true }), + }, + { + title: 'Extracting Collectors', + task: (context) => + new Listr(extractCollectorsTask(context, path), { exitOnError: true }), + }, + { + enabled: () => typeof path !== 'undefined', + title: 'Checking collectors in --path are not excluded', + task: ({ roots }: TaskContext) => { + const totalCollections = roots.reduce((acc, root) => { + return acc + (root.parsedCollections?.length || 0); + }, 0); + const collectorsInPath = Array.isArray(path) ? path.length : 1; - if (totalCollections !== collectorsInPath) { - throw new Error( - 'Collector specified in `path` is excluded; Check the telemetryrc.json files.' + if (totalCollections !== collectorsInPath) { + throw new Error( + 'Collector specified in `path` is excluded; Check the telemetryrc.json files.' + ); + } + }, + }, + { + title: 'Checking Compatible collector.schema with collector.fetch type', + task: (context) => new Listr(checkCompatibleTypesTask(context), { exitOnError: true }), + }, + { + enabled: (_) => fix || !ignoreStoredJson, + title: 'Checking Matching collector.schema against stored json files', + task: (context) => + new Listr(checkMatchingSchemasTask(context, !fix), { exitOnError: true }), + }, + { + enabled: (_) => fix, + skip: ({ roots }: TaskContext) => { + const noDiffs = roots.every( + ({ esMappingDiffs }) => !esMappingDiffs || !esMappingDiffs.length ); - } + return noDiffs && 'No changes needed.'; + }, + title: 'Generating new telemetry mappings', + task: (context) => new Listr(generateSchemasTask(context), { exitOnError: true }), }, - }, - { - title: 'Checking Compatible collector.schema with collector.fetch type', - task: (context) => new Listr(checkCompatibleTypesTask(context), { exitOnError: true }), - }, - { - enabled: (_) => fix || !ignoreStoredJson, - title: 'Checking Matching collector.schema against stored json files', - task: (context) => - new Listr(checkMatchingSchemasTask(context, !fix), { exitOnError: true }), - }, - { - enabled: (_) => fix, - skip: ({ roots }: TaskContext) => { - const noDiffs = roots.every( - ({ esMappingDiffs }) => !esMappingDiffs || !esMappingDiffs.length - ); - return noDiffs && 'No changes needed.'; + { + enabled: (_) => fix, + skip: ({ roots }: TaskContext) => { + const noDiffs = roots.every( + ({ esMappingDiffs }) => !esMappingDiffs || !esMappingDiffs.length + ); + return noDiffs && 'No changes needed.'; + }, + title: 'Updating telemetry mapping files', + task: (context) => new Listr(writeToFileTask(context), { exitOnError: true }), }, - title: 'Generating new telemetry mappings', - task: (context) => new Listr(generateSchemasTask(context), { exitOnError: true }), - }, + ], { - enabled: (_) => fix, - skip: ({ roots }: TaskContext) => { - const noDiffs = roots.every( - ({ esMappingDiffs }) => !esMappingDiffs || !esMappingDiffs.length - ); - return noDiffs && 'No changes needed.'; - }, - title: 'Updating telemetry mapping files', - task: (context) => new Listr(writeToFileTask(context), { exitOnError: true }), - }, - ]); + renderer: process.env.CI ? 'verbose' : 'default', + } + ); try { const context = createTaskContext(); diff --git a/packages/kbn-telemetry-tools/src/cli/run_telemetry_extract.ts b/packages/kbn-telemetry-tools/src/cli/run_telemetry_extract.ts index c998470ff0a9c..22790ab6a0578 100644 --- a/packages/kbn-telemetry-tools/src/cli/run_telemetry_extract.ts +++ b/packages/kbn-telemetry-tools/src/cli/run_telemetry_extract.ts @@ -21,24 +21,29 @@ import { export function runTelemetryExtract() { run( async ({ flags: {}, log }) => { - const list = new Listr([ + const list = new Listr( + [ + { + title: 'Parsing .telemetryrc.json files', + task: () => new Listr(parseConfigsTask(), { exitOnError: true }), + }, + { + title: 'Extracting Telemetry Collectors', + task: (context) => new Listr(extractCollectorsTask(context), { exitOnError: true }), + }, + { + title: 'Generating Schema files', + task: (context) => new Listr(generateSchemasTask(context), { exitOnError: true }), + }, + { + title: 'Writing to file', + task: (context) => new Listr(writeToFileTask(context), { exitOnError: true }), + }, + ], { - title: 'Parsing .telemetryrc.json files', - task: () => new Listr(parseConfigsTask(), { exitOnError: true }), - }, - { - title: 'Extracting Telemetry Collectors', - task: (context) => new Listr(extractCollectorsTask(context), { exitOnError: true }), - }, - { - title: 'Generating Schema files', - task: (context) => new Listr(generateSchemasTask(context), { exitOnError: true }), - }, - { - title: 'Writing to file', - task: (context) => new Listr(writeToFileTask(context), { exitOnError: true }), - }, - ]); + renderer: process.env.CI ? 'verbose' : 'default', + } + ); try { const context = createTaskContext(); diff --git a/src/dev/run_i18n_check.ts b/src/dev/run_i18n_check.ts index 2aa9f65f4d3db..220eef24f3808 100644 --- a/src/dev/run_i18n_check.ts +++ b/src/dev/run_i18n_check.ts @@ -120,6 +120,7 @@ run( { concurrent: false, exitOnError: true, + renderer: process.env.CI ? 'verbose' : 'default', } ); diff --git a/src/dev/run_i18n_extract.ts b/src/dev/run_i18n_extract.ts index 6ff9eb5164ad2..2c1f39e929a36 100644 --- a/src/dev/run_i18n_extract.ts +++ b/src/dev/run_i18n_extract.ts @@ -38,32 +38,37 @@ run( } const srcPaths = Array().concat(path || ['./src', './packages', './x-pack']); - const list = new Listr([ - { - title: 'Merging .i18nrc.json files', - task: () => new Listr(mergeConfigs(includeConfig), { exitOnError: true }), - }, - { - title: 'Extracting Default Messages', - task: ({ config }) => - new Listr(extractDefaultMessages(config, srcPaths), { exitOnError: true }), - }, - { - title: 'Writing to file', - enabled: (ctx) => outputDir && ctx.messages.size, - task: async (ctx) => { - const sortedMessages = [...ctx.messages].sort(([key1], [key2]) => - key1.localeCompare(key2) - ); - await writeFileAsync( - resolve(outputDir, 'en.json'), - outputFormat === 'json5' - ? serializeToJson5(sortedMessages) - : serializeToJson(sortedMessages) - ); + const list = new Listr( + [ + { + title: 'Merging .i18nrc.json files', + task: () => new Listr(mergeConfigs(includeConfig), { exitOnError: true }), + }, + { + title: 'Extracting Default Messages', + task: ({ config }) => + new Listr(extractDefaultMessages(config, srcPaths), { exitOnError: true }), }, - }, - ]); + { + title: 'Writing to file', + enabled: (ctx) => outputDir && ctx.messages.size, + task: async (ctx) => { + const sortedMessages = [...ctx.messages].sort(([key1], [key2]) => + key1.localeCompare(key2) + ); + await writeFileAsync( + resolve(outputDir, 'en.json'), + outputFormat === 'json5' + ? serializeToJson5(sortedMessages) + : serializeToJson(sortedMessages) + ); + }, + }, + ], + { + renderer: process.env.CI ? 'verbose' : 'default', + } + ); try { const reporter = new ErrorReporter(); diff --git a/src/dev/run_i18n_integrate.ts b/src/dev/run_i18n_integrate.ts index 29696ca5f9aa5..80e2f8cb1f33b 100644 --- a/src/dev/run_i18n_integrate.ts +++ b/src/dev/run_i18n_integrate.ts @@ -69,33 +69,38 @@ run( const srcPaths = Array().concat(path || ['./src', './packages', './x-pack']); - const list = new Listr([ - { - title: 'Merging .i18nrc.json files', - task: () => new Listr(mergeConfigs(includeConfig), { exitOnError: true }), - }, - { - title: 'Extracting Default Messages', - task: ({ config }) => - new Listr(extractDefaultMessages(config, srcPaths), { exitOnError: true }), - }, - { - title: 'Integrating Locale File', - task: async ({ messages, config }) => { - await integrateLocaleFiles(messages, { - sourceFileName: source, - targetFileName: target, - dryRun, - ignoreIncompatible, - ignoreUnused, - ignoreMissing, - ignoreMalformed, - config, - log, - }); + const list = new Listr( + [ + { + title: 'Merging .i18nrc.json files', + task: () => new Listr(mergeConfigs(includeConfig), { exitOnError: true }), + }, + { + title: 'Extracting Default Messages', + task: ({ config }) => + new Listr(extractDefaultMessages(config, srcPaths), { exitOnError: true }), }, - }, - ]); + { + title: 'Integrating Locale File', + task: async ({ messages, config }) => { + await integrateLocaleFiles(messages, { + sourceFileName: source, + targetFileName: target, + dryRun, + ignoreIncompatible, + ignoreUnused, + ignoreMissing, + ignoreMalformed, + config, + log, + }); + }, + }, + ], + { + renderer: process.env.CI ? 'verbose' : 'default', + } + ); try { const reporter = new ErrorReporter(); diff --git a/x-pack/plugins/apm/scripts/precommit.js b/x-pack/plugins/apm/scripts/precommit.js index ab19094c4e610..c1847432abcf7 100644 --- a/x-pack/plugins/apm/scripts/precommit.js +++ b/x-pack/plugins/apm/scripts/precommit.js @@ -80,7 +80,11 @@ const tasks = new Listr( ), }, ], - { exitOnError: true, concurrent: false } + { + exitOnError: true, + concurrent: false, + renderer: process.env.CI ? 'verbose' : 'default', + } ); tasks.run().catch((error) => { From ac2ce8971e035bfbc02f8a36776912240f940f5d Mon Sep 17 00:00:00 2001 From: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> Date: Thu, 14 Jul 2022 00:41:57 -0400 Subject: [PATCH 008/111] [api-docs] Daily api_docs build (#136361) --- api_docs/actions.mdx | 2 +- api_docs/advanced_settings.mdx | 2 +- api_docs/aiops.devdocs.json | 72 +- api_docs/aiops.mdx | 7 +- api_docs/alerting.mdx | 2 +- api_docs/apm.devdocs.json | 86 +- api_docs/apm.mdx | 2 +- api_docs/banners.mdx | 2 +- api_docs/bfetch.mdx | 2 +- api_docs/canvas.mdx | 2 +- api_docs/cases.mdx | 2 +- api_docs/charts.mdx | 2 +- api_docs/cloud.mdx | 2 +- api_docs/cloud_security_posture.mdx | 2 +- api_docs/console.mdx | 2 +- api_docs/controls.mdx | 2 +- api_docs/core.devdocs.json | 406 +++------ api_docs/core.mdx | 4 +- api_docs/core_application.mdx | 4 +- api_docs/core_chrome.mdx | 4 +- api_docs/core_http.devdocs.json | 218 ----- api_docs/core_http.mdx | 30 - api_docs/core_saved_objects.mdx | 4 +- api_docs/custom_integrations.mdx | 2 +- api_docs/dashboard.mdx | 2 +- api_docs/dashboard_enhanced.mdx | 2 +- api_docs/data.devdocs.json | 26 +- api_docs/data.mdx | 2 +- api_docs/data_query.mdx | 2 +- api_docs/data_search.devdocs.json | 163 +++- api_docs/data_search.mdx | 2 +- api_docs/data_view_editor.devdocs.json | 15 + api_docs/data_view_editor.mdx | 4 +- api_docs/data_view_field_editor.devdocs.json | 33 +- api_docs/data_view_field_editor.mdx | 4 +- api_docs/data_view_management.mdx | 2 +- api_docs/data_views.devdocs.json | 32 +- api_docs/data_views.mdx | 2 +- api_docs/data_visualizer.mdx | 2 +- api_docs/deprecations_by_api.mdx | 2 +- api_docs/deprecations_by_plugin.mdx | 4 +- api_docs/deprecations_by_team.mdx | 2 +- api_docs/dev_tools.mdx | 2 +- api_docs/discover.mdx | 2 +- api_docs/discover_enhanced.mdx | 2 +- api_docs/elastic_apm_synthtrace.mdx | 2 +- api_docs/embeddable.mdx | 2 +- api_docs/embeddable_enhanced.mdx | 2 +- api_docs/encrypted_saved_objects.mdx | 2 +- api_docs/enterprise_search.mdx | 2 +- api_docs/es_ui_shared.mdx | 2 +- api_docs/event_annotation.mdx | 2 +- api_docs/event_log.mdx | 2 +- api_docs/expression_error.mdx | 2 +- api_docs/expression_gauge.devdocs.json | 4 +- api_docs/expression_gauge.mdx | 2 +- api_docs/expression_heatmap.devdocs.json | 4 +- api_docs/expression_heatmap.mdx | 2 +- api_docs/expression_image.mdx | 2 +- api_docs/expression_legacy_metric_vis.mdx | 2 +- api_docs/expression_metric.mdx | 2 +- api_docs/expression_metric_vis.mdx | 2 +- .../expression_partition_vis.devdocs.json | 2 +- api_docs/expression_partition_vis.mdx | 2 +- api_docs/expression_repeat_image.mdx | 2 +- api_docs/expression_reveal_image.mdx | 2 +- api_docs/expression_shape.mdx | 2 +- api_docs/expression_tagcloud.mdx | 2 +- api_docs/expression_x_y.devdocs.json | 8 +- api_docs/expression_x_y.mdx | 2 +- api_docs/expressions.devdocs.json | 2 +- api_docs/expressions.mdx | 2 +- api_docs/features.mdx | 2 +- api_docs/field_formats.devdocs.json | 33 +- api_docs/field_formats.mdx | 2 +- api_docs/file_upload.mdx | 2 +- api_docs/fleet.devdocs.json | 47 +- api_docs/fleet.mdx | 4 +- api_docs/global_search.mdx | 2 +- api_docs/home.mdx | 2 +- api_docs/index_lifecycle_management.mdx | 2 +- api_docs/index_management.mdx | 2 +- api_docs/infra.mdx | 2 +- api_docs/inspector.mdx | 2 +- api_docs/interactive_setup.mdx | 2 +- api_docs/kbn_ace.mdx | 2 +- api_docs/kbn_aiops_components.mdx | 2 +- api_docs/kbn_aiops_utils.mdx | 2 +- api_docs/kbn_alerts.mdx | 2 +- api_docs/kbn_analytics.mdx | 2 +- api_docs/kbn_analytics_client.mdx | 2 +- ..._analytics_shippers_elastic_v3_browser.mdx | 2 +- ...n_analytics_shippers_elastic_v3_common.mdx | 2 +- ...n_analytics_shippers_elastic_v3_server.mdx | 2 +- api_docs/kbn_analytics_shippers_fullstory.mdx | 2 +- api_docs/kbn_apm_config_loader.mdx | 2 +- api_docs/kbn_apm_utils.mdx | 2 +- api_docs/kbn_axe_config.mdx | 2 +- api_docs/kbn_bazel_packages.mdx | 2 +- api_docs/kbn_bazel_runner.mdx | 2 +- api_docs/kbn_ci_stats_core.mdx | 2 +- api_docs/kbn_ci_stats_performance_metrics.mdx | 2 +- api_docs/kbn_ci_stats_reporter.mdx | 2 +- api_docs/kbn_cli_dev_mode.mdx | 2 +- api_docs/kbn_coloring.mdx | 2 +- api_docs/kbn_config.mdx | 2 +- api_docs/kbn_config_mocks.mdx | 2 +- api_docs/kbn_config_schema.mdx | 2 +- api_docs/kbn_core_analytics_browser.mdx | 2 +- .../kbn_core_analytics_browser_internal.mdx | 2 +- api_docs/kbn_core_analytics_browser_mocks.mdx | 2 +- api_docs/kbn_core_analytics_server.mdx | 2 +- .../kbn_core_analytics_server_internal.mdx | 2 +- api_docs/kbn_core_analytics_server_mocks.mdx | 2 +- api_docs/kbn_core_base_browser_mocks.mdx | 2 +- api_docs/kbn_core_base_common.mdx | 2 +- api_docs/kbn_core_base_server_internal.mdx | 2 +- api_docs/kbn_core_base_server_mocks.mdx | 2 +- api_docs/kbn_core_config_server_internal.mdx | 2 +- ...kbn_core_deprecations_browser.devdocs.json | 189 ++++ api_docs/kbn_core_deprecations_browser.mdx | 30 + ...deprecations_browser_internal.devdocs.json | 129 +++ ...kbn_core_deprecations_browser_internal.mdx | 27 + ...re_deprecations_browser_mocks.devdocs.json | 92 ++ .../kbn_core_deprecations_browser_mocks.mdx | 27 + .../kbn_core_deprecations_common.devdocs.json | 321 +++++++ api_docs/kbn_core_deprecations_common.mdx | 30 + api_docs/kbn_core_doc_links_browser.mdx | 2 +- api_docs/kbn_core_doc_links_browser_mocks.mdx | 2 +- api_docs/kbn_core_doc_links_server.mdx | 2 +- api_docs/kbn_core_doc_links_server_mocks.mdx | 2 +- .../kbn_core_environment_server_internal.mdx | 2 +- .../kbn_core_environment_server_mocks.mdx | 2 +- .../kbn_core_execution_context_browser.mdx | 2 +- ...ore_execution_context_browser_internal.mdx | 2 +- ...n_core_execution_context_browser_mocks.mdx | 2 +- .../kbn_core_execution_context_common.mdx | 2 +- .../kbn_core_execution_context_server.mdx | 2 +- ...core_execution_context_server_internal.mdx | 2 +- ...bn_core_execution_context_server_mocks.mdx | 2 +- api_docs/kbn_core_fatal_errors_browser.mdx | 2 +- .../kbn_core_fatal_errors_browser_mocks.mdx | 2 +- api_docs/kbn_core_http_browser.mdx | 2 +- api_docs/kbn_core_http_browser_internal.mdx | 2 +- api_docs/kbn_core_http_browser_mocks.mdx | 2 +- api_docs/kbn_core_http_common.mdx | 2 +- ...ore_http_context_server_mocks.devdocs.json | 201 +++++ .../kbn_core_http_context_server_mocks.mdx | 30 + ...e_http_router_server_internal.devdocs.json | 414 +++++++++ .../kbn_core_http_router_server_internal.mdx | 33 + ...core_http_router_server_mocks.devdocs.json | 193 ++++ .../kbn_core_http_router_server_mocks.mdx | 30 + api_docs/kbn_core_http_server.mdx | 2 +- ...kbn_core_http_server_internal.devdocs.json | 845 ++++++++++++++++++ api_docs/kbn_core_http_server_internal.mdx | 36 + .../kbn_core_http_server_mocks.devdocs.json | 830 +++++++++++++++++ api_docs/kbn_core_http_server_mocks.mdx | 33 + api_docs/kbn_core_i18n_browser.mdx | 2 +- api_docs/kbn_core_i18n_browser_mocks.mdx | 2 +- .../kbn_core_injected_metadata_browser.mdx | 2 +- ...n_core_injected_metadata_browser_mocks.mdx | 2 +- api_docs/kbn_core_logging_server.mdx | 2 +- api_docs/kbn_core_logging_server_internal.mdx | 2 +- api_docs/kbn_core_logging_server_mocks.mdx | 2 +- api_docs/kbn_core_node_server.mdx | 2 +- ...kbn_core_node_server_internal.devdocs.json | 2 +- api_docs/kbn_core_node_server_internal.mdx | 2 +- api_docs/kbn_core_node_server_mocks.mdx | 2 +- api_docs/kbn_core_preboot_server.mdx | 2 +- api_docs/kbn_core_preboot_server_mocks.mdx | 2 +- api_docs/kbn_core_theme_browser.mdx | 2 +- api_docs/kbn_core_theme_browser_internal.mdx | 2 +- api_docs/kbn_core_theme_browser_mocks.mdx | 2 +- api_docs/kbn_crypto.mdx | 2 +- api_docs/kbn_crypto_browser.mdx | 2 +- api_docs/kbn_datemath.mdx | 2 +- api_docs/kbn_dev_cli_errors.mdx | 2 +- api_docs/kbn_dev_cli_runner.mdx | 2 +- api_docs/kbn_dev_proc_runner.mdx | 2 +- api_docs/kbn_dev_utils.mdx | 2 +- api_docs/kbn_doc_links.mdx | 2 +- api_docs/kbn_docs_utils.mdx | 2 +- api_docs/kbn_es_archiver.mdx | 2 +- api_docs/kbn_es_errors.mdx | 2 +- api_docs/kbn_es_query.mdx | 2 +- api_docs/kbn_eslint_plugin_imports.mdx | 2 +- api_docs/kbn_field_types.mdx | 2 +- api_docs/kbn_find_used_node_modules.mdx | 2 +- api_docs/kbn_generate.mdx | 2 +- api_docs/kbn_handlebars.mdx | 2 +- api_docs/kbn_hapi_mocks.mdx | 2 +- api_docs/kbn_home_sample_data_cards.mdx | 2 +- api_docs/kbn_i18n.mdx | 2 +- api_docs/kbn_import_resolver.mdx | 2 +- api_docs/kbn_interpreter.mdx | 2 +- api_docs/kbn_io_ts_utils.mdx | 2 +- api_docs/kbn_jest_serializers.mdx | 2 +- api_docs/kbn_kibana_json_schema.mdx | 2 +- api_docs/kbn_logging.mdx | 2 +- api_docs/kbn_logging_mocks.mdx | 2 +- api_docs/kbn_mapbox_gl.mdx | 2 +- api_docs/kbn_ml_agg_utils.mdx | 2 +- api_docs/kbn_ml_is_populated_object.mdx | 2 +- api_docs/kbn_ml_string_hash.mdx | 2 +- api_docs/kbn_monaco.mdx | 2 +- api_docs/kbn_optimizer.mdx | 2 +- api_docs/kbn_optimizer_webpack_helpers.mdx | 2 +- ..._performance_testing_dataset_extractor.mdx | 2 +- api_docs/kbn_plugin_discovery.mdx | 2 +- api_docs/kbn_plugin_generator.mdx | 2 +- api_docs/kbn_plugin_helpers.mdx | 2 +- api_docs/kbn_pm.mdx | 2 +- api_docs/kbn_react_field.mdx | 2 +- api_docs/kbn_rule_data_utils.mdx | 2 +- .../kbn_scalability_simulation_generator.mdx | 2 +- .../kbn_securitysolution_autocomplete.mdx | 2 +- api_docs/kbn_securitysolution_es_utils.mdx | 2 +- api_docs/kbn_securitysolution_hook_utils.mdx | 2 +- ..._securitysolution_io_ts_alerting_types.mdx | 2 +- .../kbn_securitysolution_io_ts_list_types.mdx | 2 +- api_docs/kbn_securitysolution_io_ts_types.mdx | 2 +- api_docs/kbn_securitysolution_io_ts_utils.mdx | 2 +- api_docs/kbn_securitysolution_list_api.mdx | 2 +- .../kbn_securitysolution_list_constants.mdx | 2 +- api_docs/kbn_securitysolution_list_hooks.mdx | 2 +- api_docs/kbn_securitysolution_list_utils.mdx | 2 +- api_docs/kbn_securitysolution_rules.mdx | 2 +- api_docs/kbn_securitysolution_t_grid.mdx | 2 +- api_docs/kbn_securitysolution_utils.mdx | 2 +- api_docs/kbn_server_http_tools.mdx | 2 +- api_docs/kbn_server_route_repository.mdx | 2 +- api_docs/kbn_shared_ux_button_toolbar.mdx | 2 +- api_docs/kbn_shared_ux_card_no_data.mdx | 2 +- api_docs/kbn_shared_ux_components.mdx | 2 +- .../kbn_shared_ux_page_analytics_no_data.mdx | 2 +- .../kbn_shared_ux_page_kibana_no_data.mdx | 2 +- api_docs/kbn_shared_ux_page_solution_nav.mdx | 2 +- .../kbn_shared_ux_prompt_no_data_views.mdx | 2 +- api_docs/kbn_shared_ux_services.mdx | 2 +- api_docs/kbn_shared_ux_storybook.mdx | 2 +- api_docs/kbn_shared_ux_utility.mdx | 2 +- api_docs/kbn_sort_package_json.mdx | 2 +- api_docs/kbn_std.mdx | 2 +- api_docs/kbn_stdio_dev_helpers.mdx | 2 +- api_docs/kbn_storybook.mdx | 2 +- api_docs/kbn_telemetry_tools.mdx | 2 +- api_docs/kbn_test.devdocs.json | 97 +- api_docs/kbn_test.mdx | 4 +- api_docs/kbn_test_jest_helpers.mdx | 2 +- api_docs/kbn_tooling_log.mdx | 2 +- api_docs/kbn_type_summarizer.mdx | 2 +- api_docs/kbn_type_summarizer_core.mdx | 2 +- api_docs/kbn_typed_react_router_config.mdx | 2 +- api_docs/kbn_ui_theme.mdx | 2 +- api_docs/kbn_utility_types.mdx | 2 +- api_docs/kbn_utility_types_jest.mdx | 2 +- api_docs/kbn_utils.mdx | 2 +- api_docs/kibana_overview.mdx | 2 +- api_docs/kibana_react.devdocs.json | 26 +- api_docs/kibana_react.mdx | 2 +- api_docs/kibana_utils.mdx | 2 +- api_docs/kubernetes_security.mdx | 2 +- api_docs/lens.devdocs.json | 16 +- api_docs/lens.mdx | 2 +- api_docs/license_api_guard.mdx | 2 +- api_docs/license_management.mdx | 2 +- api_docs/licensing.mdx | 2 +- api_docs/lists.mdx | 2 +- api_docs/management.mdx | 2 +- api_docs/maps.devdocs.json | 29 +- api_docs/maps.mdx | 4 +- api_docs/maps_ems.mdx | 2 +- api_docs/ml.mdx | 2 +- api_docs/monitoring.mdx | 2 +- api_docs/monitoring_collection.mdx | 2 +- api_docs/navigation.mdx | 2 +- api_docs/newsfeed.mdx | 2 +- api_docs/observability.devdocs.json | 95 +- api_docs/observability.mdx | 2 +- api_docs/osquery.mdx | 2 +- api_docs/plugin_directory.mdx | 31 +- api_docs/presentation_util.mdx | 2 +- api_docs/remote_clusters.mdx | 2 +- api_docs/reporting.mdx | 2 +- api_docs/rollup.mdx | 2 +- api_docs/rule_registry.mdx | 2 +- api_docs/runtime_fields.mdx | 2 +- api_docs/saved_objects.mdx | 2 +- api_docs/saved_objects_management.mdx | 2 +- api_docs/saved_objects_tagging.mdx | 2 +- api_docs/saved_objects_tagging_oss.mdx | 2 +- api_docs/screenshot_mode.mdx | 2 +- api_docs/screenshotting.mdx | 2 +- api_docs/security.devdocs.json | 8 +- api_docs/security.mdx | 2 +- api_docs/security_solution.mdx | 2 +- api_docs/session_view.mdx | 2 +- api_docs/share.mdx | 2 +- api_docs/shared_u_x.mdx | 2 +- api_docs/snapshot_restore.mdx | 2 +- api_docs/spaces.mdx | 2 +- api_docs/stack_alerts.mdx | 2 +- api_docs/task_manager.mdx | 2 +- api_docs/telemetry.mdx | 2 +- api_docs/telemetry_collection_manager.mdx | 2 +- api_docs/telemetry_collection_xpack.mdx | 2 +- api_docs/telemetry_management_section.mdx | 2 +- api_docs/timelines.mdx | 2 +- api_docs/transform.mdx | 2 +- api_docs/triggers_actions_ui.devdocs.json | 172 +--- api_docs/triggers_actions_ui.mdx | 4 +- api_docs/ui_actions.mdx | 2 +- api_docs/ui_actions_enhanced.mdx | 2 +- api_docs/unified_search.mdx | 2 +- api_docs/unified_search_autocomplete.mdx | 2 +- api_docs/url_forwarding.mdx | 2 +- api_docs/usage_collection.mdx | 2 +- api_docs/ux.mdx | 2 +- api_docs/vis_default_editor.mdx | 2 +- api_docs/vis_type_gauge.mdx | 2 +- api_docs/vis_type_heatmap.mdx | 2 +- api_docs/vis_type_pie.devdocs.json | 2 +- api_docs/vis_type_pie.mdx | 2 +- api_docs/vis_type_table.mdx | 2 +- api_docs/vis_type_timelion.mdx | 2 +- api_docs/vis_type_timeseries.mdx | 2 +- api_docs/vis_type_vega.mdx | 2 +- api_docs/vis_type_vislib.mdx | 2 +- api_docs/vis_type_xy.mdx | 2 +- api_docs/visualizations.devdocs.json | 10 +- api_docs/visualizations.mdx | 2 +- 331 files changed, 4457 insertions(+), 1299 deletions(-) delete mode 100644 api_docs/core_http.devdocs.json delete mode 100644 api_docs/core_http.mdx create mode 100644 api_docs/kbn_core_deprecations_browser.devdocs.json create mode 100644 api_docs/kbn_core_deprecations_browser.mdx create mode 100644 api_docs/kbn_core_deprecations_browser_internal.devdocs.json create mode 100644 api_docs/kbn_core_deprecations_browser_internal.mdx create mode 100644 api_docs/kbn_core_deprecations_browser_mocks.devdocs.json create mode 100644 api_docs/kbn_core_deprecations_browser_mocks.mdx create mode 100644 api_docs/kbn_core_deprecations_common.devdocs.json create mode 100644 api_docs/kbn_core_deprecations_common.mdx create mode 100644 api_docs/kbn_core_http_context_server_mocks.devdocs.json create mode 100644 api_docs/kbn_core_http_context_server_mocks.mdx create mode 100644 api_docs/kbn_core_http_router_server_internal.devdocs.json create mode 100644 api_docs/kbn_core_http_router_server_internal.mdx create mode 100644 api_docs/kbn_core_http_router_server_mocks.devdocs.json create mode 100644 api_docs/kbn_core_http_router_server_mocks.mdx create mode 100644 api_docs/kbn_core_http_server_internal.devdocs.json create mode 100644 api_docs/kbn_core_http_server_internal.mdx create mode 100644 api_docs/kbn_core_http_server_mocks.devdocs.json create mode 100644 api_docs/kbn_core_http_server_mocks.mdx diff --git a/api_docs/actions.mdx b/api_docs/actions.mdx index b37fe3df21ad2..266c9e3101296 100644 --- a/api_docs/actions.mdx +++ b/api_docs/actions.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/actions title: "actions" image: https://source.unsplash.com/400x175/?github summary: API docs for the actions plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'actions'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/advanced_settings.mdx b/api_docs/advanced_settings.mdx index d7284bf2ba87a..8b8ac8261c081 100644 --- a/api_docs/advanced_settings.mdx +++ b/api_docs/advanced_settings.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/advancedSettings title: "advancedSettings" image: https://source.unsplash.com/400x175/?github summary: API docs for the advancedSettings plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'advancedSettings'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/aiops.devdocs.json b/api_docs/aiops.devdocs.json index a9675003d2e1f..e351d2c17883e 100644 --- a/api_docs/aiops.devdocs.json +++ b/api_docs/aiops.devdocs.json @@ -10,17 +10,11 @@ "tags": [], "label": "ExplainLogRateSpikes", "description": [ - "\nLazy-wrapped ExplainLogRateSpikes React component" + "\nLazy-wrapped ExplainLogRateSpikesWrapper React component" ], "signature": [ "(props: React.PropsWithChildren<", - { - "pluginId": "aiops", - "scope": "public", - "docId": "kibAiopsPluginApi", - "section": "def-public.ExplainLogRateSpikesProps", - "text": "ExplainLogRateSpikesProps" - }, + "ExplainLogRateSpikesWrapperProps", ">) => JSX.Element" ], "path": "x-pack/plugins/aiops/public/shared_lazy_components.tsx", @@ -37,13 +31,7 @@ ], "signature": [ "React.PropsWithChildren<", - { - "pluginId": "aiops", - "scope": "public", - "docId": "kibAiopsPluginApi", - "section": "def-public.ExplainLogRateSpikesProps", - "text": "ExplainLogRateSpikesProps" - }, + "ExplainLogRateSpikesWrapperProps", ">" ], "path": "x-pack/plugins/aiops/public/shared_lazy_components.tsx", @@ -55,59 +43,7 @@ "initialIsOpen": false } ], - "interfaces": [ - { - "parentPluginId": "aiops", - "id": "def-public.ExplainLogRateSpikesProps", - "type": "Interface", - "tags": [], - "label": "ExplainLogRateSpikesProps", - "description": [ - "\nExplainLogRateSpikes props require a data view." - ], - "path": "x-pack/plugins/aiops/public/components/explain_log_rate_spikes/explain_log_rate_spikes.tsx", - "deprecated": false, - "children": [ - { - "parentPluginId": "aiops", - "id": "def-public.ExplainLogRateSpikesProps.dataView", - "type": "Object", - "tags": [], - "label": "dataView", - "description": [ - "The data view to analyze." - ], - "signature": [ - { - "pluginId": "dataViews", - "scope": "common", - "docId": "kibDataViewsPluginApi", - "section": "def-common.DataView", - "text": "DataView" - } - ], - "path": "x-pack/plugins/aiops/public/components/explain_log_rate_spikes/explain_log_rate_spikes.tsx", - "deprecated": false - }, - { - "parentPluginId": "aiops", - "id": "def-public.ExplainLogRateSpikesProps.windowParameters", - "type": "Object", - "tags": [], - "label": "windowParameters", - "description": [ - "Window parameters for the analysis" - ], - "signature": [ - "WindowParameters" - ], - "path": "x-pack/plugins/aiops/public/components/explain_log_rate_spikes/explain_log_rate_spikes.tsx", - "deprecated": false - } - ], - "initialIsOpen": false - } - ], + "interfaces": [], "enums": [], "misc": [], "objects": [], diff --git a/api_docs/aiops.mdx b/api_docs/aiops.mdx index 618ea5e1eb78d..d99384c4f3db0 100644 --- a/api_docs/aiops.mdx +++ b/api_docs/aiops.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/aiops title: "aiops" image: https://source.unsplash.com/400x175/?github summary: API docs for the aiops plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'aiops'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) for q | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 12 | 0 | 0 | 0 | +| 9 | 0 | 0 | 1 | ## Client @@ -28,9 +28,6 @@ Contact [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) for q ### Functions -### Interfaces - - ## Server ### Setup diff --git a/api_docs/alerting.mdx b/api_docs/alerting.mdx index 7b86f41380cf8..2db29e53cf015 100644 --- a/api_docs/alerting.mdx +++ b/api_docs/alerting.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/alerting title: "alerting" image: https://source.unsplash.com/400x175/?github summary: API docs for the alerting plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'alerting'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/apm.devdocs.json b/api_docs/apm.devdocs.json index 06c67d2dc2974..97812e861a663 100644 --- a/api_docs/apm.devdocs.json +++ b/api_docs/apm.devdocs.json @@ -772,7 +772,7 @@ "label": "APIEndpoint", "description": [], "signature": [ - "\"POST /internal/apm/data_view/static\" | \"GET /internal/apm/data_view/dynamic\" | \"GET /internal/apm/environments\" | \"GET /internal/apm/services/{serviceName}/errors/groups/main_statistics\" | \"POST /internal/apm/services/{serviceName}/errors/groups/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/errors/{groupId}\" | \"GET /internal/apm/services/{serviceName}/errors/distribution\" | \"POST /internal/apm/latency/overall_distribution/transactions\" | \"GET /internal/apm/services/{serviceName}/metrics/charts\" | \"GET /internal/apm/observability_overview\" | \"GET /internal/apm/observability_overview/has_data\" | \"GET /internal/apm/ux/page-load-distribution\" | \"GET /internal/apm/ux/page-load-distribution/breakdown\" | \"GET /internal/apm/service-map\" | \"GET /internal/apm/service-map/service/{serviceName}\" | \"GET /internal/apm/service-map/backend\" | \"GET /internal/apm/services/{serviceName}/serviceNodes\" | \"GET /internal/apm/services\" | \"POST /internal/apm/services/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/metadata/details\" | \"GET /internal/apm/services/{serviceName}/metadata/icons\" | \"GET /internal/apm/services/{serviceName}/agent\" | \"GET /internal/apm/services/{serviceName}/transaction_types\" | \"GET /internal/apm/services/{serviceName}/node/{serviceNodeName}/metadata\" | \"GET /api/apm/services/{serviceName}/annotation/search\" | \"POST /api/apm/services/{serviceName}/annotation\" | \"GET /internal/apm/services/{serviceName}/service_overview_instances/details/{serviceNodeName}\" | \"GET /internal/apm/services/{serviceName}/throughput\" | \"GET /internal/apm/services/{serviceName}/service_overview_instances/main_statistics\" | \"GET /internal/apm/services/{serviceName}/service_overview_instances/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/dependencies\" | \"GET /internal/apm/services/{serviceName}/dependencies/breakdown\" | \"GET /internal/apm/services/{serviceName}/profiling/timeline\" | \"GET /internal/apm/services/{serviceName}/profiling/statistics\" | \"GET /internal/apm/services/{serviceName}/anomaly_charts\" | \"GET /internal/apm/sorted_and_filtered_services\" | \"GET /internal/apm/service-groups\" | \"GET /internal/apm/service-group\" | \"POST /internal/apm/service-group\" | \"DELETE /internal/apm/service-group\" | \"GET /internal/apm/service-group/services\" | \"GET /internal/apm/suggestions\" | \"GET /internal/apm/traces/{traceId}\" | \"GET /internal/apm/traces\" | \"GET /internal/apm/traces/{traceId}/root_transaction\" | \"GET /internal/apm/transactions/{transactionId}\" | \"GET /internal/apm/traces/find\" | \"GET /internal/apm/services/{serviceName}/transactions/groups/main_statistics\" | \"GET /internal/apm/services/{serviceName}/transactions/groups/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/latency\" | \"GET /internal/apm/services/{serviceName}/transactions/traces/samples\" | \"GET /internal/apm/services/{serviceName}/transaction/charts/breakdown\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/error_rate\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/coldstart_rate\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/coldstart_rate_by_transaction_name\" | \"GET /internal/apm/alerts/chart_preview/transaction_error_rate\" | \"GET /internal/apm/alerts/chart_preview/transaction_duration\" | \"GET /internal/apm/alerts/chart_preview/transaction_error_count\" | \"GET /api/apm/settings/agent-configuration\" | \"GET /api/apm/settings/agent-configuration/view\" | \"DELETE /api/apm/settings/agent-configuration\" | \"PUT /api/apm/settings/agent-configuration\" | \"POST /api/apm/settings/agent-configuration/search\" | \"GET /api/apm/settings/agent-configuration/environments\" | \"GET /api/apm/settings/agent-configuration/agent_name\" | \"GET /internal/apm/settings/anomaly-detection/jobs\" | \"POST /internal/apm/settings/anomaly-detection/jobs\" | \"GET /internal/apm/settings/anomaly-detection/environments\" | \"POST /internal/apm/settings/anomaly-detection/update_to_v3\" | \"GET /internal/apm/settings/apm-index-settings\" | \"GET /internal/apm/settings/apm-indices\" | \"POST /internal/apm/settings/apm-indices/save\" | \"GET /internal/apm/settings/custom_links/transaction\" | \"GET /internal/apm/settings/custom_links\" | \"POST /internal/apm/settings/custom_links\" | \"PUT /internal/apm/settings/custom_links/{id}\" | \"DELETE /internal/apm/settings/custom_links/{id}\" | \"GET /api/apm/sourcemaps\" | \"POST /api/apm/sourcemaps\" | \"DELETE /api/apm/sourcemaps/{id}\" | \"GET /internal/apm/fleet/has_apm_policies\" | \"GET /internal/apm/fleet/agents\" | \"POST /api/apm/fleet/apm_server_schema\" | \"GET /internal/apm/fleet/apm_server_schema/unsupported\" | \"GET /internal/apm/fleet/migration_check\" | \"POST /internal/apm/fleet/cloud_apm_package_policy\" | \"GET /internal/apm/fleet/java_agent_versions\" | \"GET /internal/apm/backends/top_backends\" | \"GET /internal/apm/backends/upstream_services\" | \"GET /internal/apm/backends/metadata\" | \"GET /internal/apm/backends/charts/latency\" | \"GET /internal/apm/backends/charts/throughput\" | \"GET /internal/apm/backends/charts/error_rate\" | \"GET /internal/apm/backends/operations\" | \"GET /internal/apm/backends/charts/distribution\" | \"GET /internal/apm/backends/operations/spans\" | \"GET /internal/apm/correlations/field_candidates/transactions\" | \"POST /internal/apm/correlations/field_stats/transactions\" | \"GET /internal/apm/correlations/field_value_stats/transactions\" | \"POST /internal/apm/correlations/field_value_pairs/transactions\" | \"POST /internal/apm/correlations/significant_correlations/transactions\" | \"POST /internal/apm/correlations/p_values/transactions\" | \"GET /internal/apm/fallback_to_transactions\" | \"GET /internal/apm/has_data\" | \"GET /internal/apm/event_metadata/{processorEvent}/{id}\" | \"GET /internal/apm/agent_keys\" | \"GET /internal/apm/agent_keys/privileges\" | \"POST /internal/apm/api_key/invalidate\" | \"POST /api/apm/agent_keys\" | \"GET /internal/apm/traces/{traceId}/span_links/{spanId}/parents\" | \"GET /internal/apm/traces/{traceId}/span_links/{spanId}/children\" | \"GET /internal/apm/services/{serviceName}/infrastructure_attributes\" | \"GET /internal/apm/debug-telemetry\" | \"GET /internal/apm/time_range_metadata\"" + "\"POST /internal/apm/data_view/static\" | \"GET /internal/apm/data_view/dynamic\" | \"GET /internal/apm/environments\" | \"GET /internal/apm/services/{serviceName}/errors/groups/main_statistics\" | \"POST /internal/apm/services/{serviceName}/errors/groups/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/errors/{groupId}\" | \"GET /internal/apm/services/{serviceName}/errors/distribution\" | \"POST /internal/apm/latency/overall_distribution/transactions\" | \"GET /internal/apm/services/{serviceName}/metrics/charts\" | \"GET /internal/apm/observability_overview\" | \"GET /internal/apm/observability_overview/has_data\" | \"GET /internal/apm/service-map\" | \"GET /internal/apm/service-map/service/{serviceName}\" | \"GET /internal/apm/service-map/backend\" | \"GET /internal/apm/services/{serviceName}/serviceNodes\" | \"GET /internal/apm/services\" | \"POST /internal/apm/services/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/metadata/details\" | \"GET /internal/apm/services/{serviceName}/metadata/icons\" | \"GET /internal/apm/services/{serviceName}/agent\" | \"GET /internal/apm/services/{serviceName}/transaction_types\" | \"GET /internal/apm/services/{serviceName}/node/{serviceNodeName}/metadata\" | \"GET /api/apm/services/{serviceName}/annotation/search\" | \"POST /api/apm/services/{serviceName}/annotation\" | \"GET /internal/apm/services/{serviceName}/service_overview_instances/details/{serviceNodeName}\" | \"GET /internal/apm/services/{serviceName}/throughput\" | \"GET /internal/apm/services/{serviceName}/service_overview_instances/main_statistics\" | \"GET /internal/apm/services/{serviceName}/service_overview_instances/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/dependencies\" | \"GET /internal/apm/services/{serviceName}/dependencies/breakdown\" | \"GET /internal/apm/services/{serviceName}/profiling/timeline\" | \"GET /internal/apm/services/{serviceName}/profiling/statistics\" | \"GET /internal/apm/services/{serviceName}/anomaly_charts\" | \"GET /internal/apm/sorted_and_filtered_services\" | \"GET /internal/apm/service-groups\" | \"GET /internal/apm/service-group\" | \"POST /internal/apm/service-group\" | \"DELETE /internal/apm/service-group\" | \"GET /internal/apm/service-group/services\" | \"GET /internal/apm/suggestions\" | \"GET /internal/apm/traces/{traceId}\" | \"GET /internal/apm/traces\" | \"GET /internal/apm/traces/{traceId}/root_transaction\" | \"GET /internal/apm/transactions/{transactionId}\" | \"GET /internal/apm/traces/find\" | \"GET /internal/apm/services/{serviceName}/transactions/groups/main_statistics\" | \"GET /internal/apm/services/{serviceName}/transactions/groups/detailed_statistics\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/latency\" | \"GET /internal/apm/services/{serviceName}/transactions/traces/samples\" | \"GET /internal/apm/services/{serviceName}/transaction/charts/breakdown\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/error_rate\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/coldstart_rate\" | \"GET /internal/apm/services/{serviceName}/transactions/charts/coldstart_rate_by_transaction_name\" | \"GET /internal/apm/alerts/chart_preview/transaction_error_rate\" | \"GET /internal/apm/alerts/chart_preview/transaction_duration\" | \"GET /internal/apm/alerts/chart_preview/transaction_error_count\" | \"GET /api/apm/settings/agent-configuration\" | \"GET /api/apm/settings/agent-configuration/view\" | \"DELETE /api/apm/settings/agent-configuration\" | \"PUT /api/apm/settings/agent-configuration\" | \"POST /api/apm/settings/agent-configuration/search\" | \"GET /api/apm/settings/agent-configuration/environments\" | \"GET /api/apm/settings/agent-configuration/agent_name\" | \"GET /internal/apm/settings/anomaly-detection/jobs\" | \"POST /internal/apm/settings/anomaly-detection/jobs\" | \"GET /internal/apm/settings/anomaly-detection/environments\" | \"POST /internal/apm/settings/anomaly-detection/update_to_v3\" | \"GET /internal/apm/settings/apm-index-settings\" | \"GET /internal/apm/settings/apm-indices\" | \"POST /internal/apm/settings/apm-indices/save\" | \"GET /internal/apm/settings/custom_links/transaction\" | \"GET /internal/apm/settings/custom_links\" | \"POST /internal/apm/settings/custom_links\" | \"PUT /internal/apm/settings/custom_links/{id}\" | \"DELETE /internal/apm/settings/custom_links/{id}\" | \"GET /api/apm/sourcemaps\" | \"POST /api/apm/sourcemaps\" | \"DELETE /api/apm/sourcemaps/{id}\" | \"GET /internal/apm/fleet/has_apm_policies\" | \"GET /internal/apm/fleet/agents\" | \"POST /api/apm/fleet/apm_server_schema\" | \"GET /internal/apm/fleet/apm_server_schema/unsupported\" | \"GET /internal/apm/fleet/migration_check\" | \"POST /internal/apm/fleet/cloud_apm_package_policy\" | \"GET /internal/apm/fleet/java_agent_versions\" | \"GET /internal/apm/backends/top_backends\" | \"GET /internal/apm/backends/upstream_services\" | \"GET /internal/apm/backends/metadata\" | \"GET /internal/apm/backends/charts/latency\" | \"GET /internal/apm/backends/charts/throughput\" | \"GET /internal/apm/backends/charts/error_rate\" | \"GET /internal/apm/backends/operations\" | \"GET /internal/apm/backends/charts/distribution\" | \"GET /internal/apm/backends/operations/spans\" | \"GET /internal/apm/correlations/field_candidates/transactions\" | \"POST /internal/apm/correlations/field_stats/transactions\" | \"GET /internal/apm/correlations/field_value_stats/transactions\" | \"POST /internal/apm/correlations/field_value_pairs/transactions\" | \"POST /internal/apm/correlations/significant_correlations/transactions\" | \"POST /internal/apm/correlations/p_values/transactions\" | \"GET /internal/apm/fallback_to_transactions\" | \"GET /internal/apm/has_data\" | \"GET /internal/apm/event_metadata/{processorEvent}/{id}\" | \"GET /internal/apm/agent_keys\" | \"GET /internal/apm/agent_keys/privileges\" | \"POST /internal/apm/api_key/invalidate\" | \"POST /api/apm/agent_keys\" | \"GET /internal/apm/traces/{traceId}/span_links/{spanId}/parents\" | \"GET /internal/apm/traces/{traceId}/span_links/{spanId}/children\" | \"GET /internal/apm/services/{serviceName}/infrastructure_attributes\" | \"GET /internal/apm/debug-telemetry\" | \"GET /internal/apm/time_range_metadata\"" ], "path": "x-pack/plugins/apm/server/routes/apm_routes/get_global_apm_server_route_repository.ts", "deprecated": false, @@ -4740,90 +4740,6 @@ "ServiceAnomalyStats", " | undefined; label: string | undefined; id?: string | undefined; parent?: string | undefined; position?: cytoscape.Position | undefined; } | { 'span.destination.service.resource': string; 'span.type': string; 'span.subtype': string; label: string | undefined; id?: string | undefined; parent?: string | undefined; position?: cytoscape.Position | undefined; } | { id: string; source: string | undefined; target: string | undefined; label: string | undefined; bidirectional?: boolean | undefined; isInverseEdge?: boolean | undefined; } | undefined)[]; }; } | { data: { id: string; source: string; target: string; }; })[]; }, ", "APMRouteCreateOptions", - ">; \"GET /internal/apm/ux/page-load-distribution/breakdown\": ", - "ServerRoute", - "<\"GET /internal/apm/ux/page-load-distribution/breakdown\", ", - "TypeC", - "<{ query: ", - "IntersectionC", - "<[", - "IntersectionC", - "<[", - "TypeC", - "<{ uiFilters: ", - "StringC", - "; }>, ", - "TypeC", - "<{ start: ", - "Type", - "; end: ", - "Type", - "; }>, ", - "PartialC", - "<{ urlQuery: ", - "StringC", - "; percentile: ", - "StringC", - "; }>]>, ", - "PartialC", - "<{ minPercentile: ", - "StringC", - "; maxPercentile: ", - "StringC", - "; }>, ", - "TypeC", - "<{ breakdown: ", - "StringC", - "; }>]>; }>, ", - { - "pluginId": "apm", - "scope": "server", - "docId": "kibApmPluginApi", - "section": "def-server.APMRouteHandlerResources", - "text": "APMRouteHandlerResources" - }, - ", { pageLoadDistBreakdown: { name: string; data: { x: number; y: number; }[]; }[] | undefined; }, ", - "APMRouteCreateOptions", - ">; \"GET /internal/apm/ux/page-load-distribution\": ", - "ServerRoute", - "<\"GET /internal/apm/ux/page-load-distribution\", ", - "TypeC", - "<{ query: ", - "IntersectionC", - "<[", - "IntersectionC", - "<[", - "TypeC", - "<{ uiFilters: ", - "StringC", - "; }>, ", - "TypeC", - "<{ start: ", - "Type", - "; end: ", - "Type", - "; }>, ", - "PartialC", - "<{ urlQuery: ", - "StringC", - "; percentile: ", - "StringC", - "; }>]>, ", - "PartialC", - "<{ minPercentile: ", - "StringC", - "; maxPercentile: ", - "StringC", - "; }>]>; }>, ", - { - "pluginId": "apm", - "scope": "server", - "docId": "kibApmPluginApi", - "section": "def-server.APMRouteHandlerResources", - "text": "APMRouteHandlerResources" - }, - ", { pageLoadDistribution: { pageLoadDistribution: { x: number; y: number; }[]; percentiles: Record | undefined; minDuration: number; maxDuration: number; } | null; }, ", - "APMRouteCreateOptions", ">; \"GET /internal/apm/observability_overview/has_data\": ", "ServerRoute", "<\"GET /internal/apm/observability_overview/has_data\", undefined, ", diff --git a/api_docs/apm.mdx b/api_docs/apm.mdx index 1e52586d92225..3050858419771 100644 --- a/api_docs/apm.mdx +++ b/api_docs/apm.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/apm title: "apm" image: https://source.unsplash.com/400x175/?github summary: API docs for the apm plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'apm'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/banners.mdx b/api_docs/banners.mdx index 60a50ae742061..0611e689c3760 100644 --- a/api_docs/banners.mdx +++ b/api_docs/banners.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/banners title: "banners" image: https://source.unsplash.com/400x175/?github summary: API docs for the banners plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'banners'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/bfetch.mdx b/api_docs/bfetch.mdx index d11bfb0ab67a5..80f63cf0a3fbf 100644 --- a/api_docs/bfetch.mdx +++ b/api_docs/bfetch.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/bfetch title: "bfetch" image: https://source.unsplash.com/400x175/?github summary: API docs for the bfetch plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'bfetch'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/canvas.mdx b/api_docs/canvas.mdx index e647d472c91f9..434e0a37bb096 100644 --- a/api_docs/canvas.mdx +++ b/api_docs/canvas.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/canvas title: "canvas" image: https://source.unsplash.com/400x175/?github summary: API docs for the canvas plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'canvas'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/cases.mdx b/api_docs/cases.mdx index 2aa643e48d15b..f155adf764c83 100644 --- a/api_docs/cases.mdx +++ b/api_docs/cases.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/cases title: "cases" image: https://source.unsplash.com/400x175/?github summary: API docs for the cases plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'cases'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/charts.mdx b/api_docs/charts.mdx index 9671ccbe8af2f..b29658891ad61 100644 --- a/api_docs/charts.mdx +++ b/api_docs/charts.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/charts title: "charts" image: https://source.unsplash.com/400x175/?github summary: API docs for the charts plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'charts'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/cloud.mdx b/api_docs/cloud.mdx index 01ec58337accf..892f3c9871d8c 100644 --- a/api_docs/cloud.mdx +++ b/api_docs/cloud.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/cloud title: "cloud" image: https://source.unsplash.com/400x175/?github summary: API docs for the cloud plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'cloud'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/cloud_security_posture.mdx b/api_docs/cloud_security_posture.mdx index 21e18763c07cc..221935685c3aa 100644 --- a/api_docs/cloud_security_posture.mdx +++ b/api_docs/cloud_security_posture.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/cloudSecurityPosture title: "cloudSecurityPosture" image: https://source.unsplash.com/400x175/?github summary: API docs for the cloudSecurityPosture plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'cloudSecurityPosture'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/console.mdx b/api_docs/console.mdx index bf2db61245112..46fcb6547e8f0 100644 --- a/api_docs/console.mdx +++ b/api_docs/console.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/console title: "console" image: https://source.unsplash.com/400x175/?github summary: API docs for the console plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'console'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/controls.mdx b/api_docs/controls.mdx index fc1869da56022..78f2941afcacd 100644 --- a/api_docs/controls.mdx +++ b/api_docs/controls.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/controls title: "controls" image: https://source.unsplash.com/400x175/?github summary: API docs for the controls plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'controls'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/core.devdocs.json b/api_docs/core.devdocs.json index 04ccf7434c847..696d751b5a6ed 100644 --- a/api_docs/core.devdocs.json +++ b/api_docs/core.devdocs.json @@ -1646,13 +1646,7 @@ "{@link DeprecationsServiceStart}" ], "signature": [ - { - "pluginId": "core", - "scope": "public", - "docId": "kibCorePluginApi", - "section": "def-public.DeprecationsServiceStart", - "text": "DeprecationsServiceStart" - } + "DeprecationsServiceStart" ], "path": "src/core/public/index.ts", "deprecated": false @@ -1726,7 +1720,7 @@ "description": [ "\nDeprecationsService provides methods to fetch domain deprecation details from\nthe Kibana server.\n" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "children": [ { @@ -1743,7 +1737,7 @@ "DomainDeprecationDetails", "[]>" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "children": [], "returnComment": [] @@ -1762,7 +1756,7 @@ "DomainDeprecationDetails", "[]>" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "children": [ { @@ -1775,7 +1769,7 @@ "signature": [ "string" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "isRequired": true } @@ -1796,7 +1790,7 @@ "DomainDeprecationDetails", ") => boolean" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "children": [ { @@ -1809,7 +1803,7 @@ "signature": [ "DomainDeprecationDetails" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "isRequired": true } @@ -1829,16 +1823,10 @@ "(details: ", "DomainDeprecationDetails", ") => Promise<", - { - "pluginId": "core", - "scope": "public", - "docId": "kibCorePluginApi", - "section": "def-public.ResolveDeprecationResponse", - "text": "ResolveDeprecationResponse" - }, + "ResolveDeprecationResponse", ">" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "children": [ { @@ -1851,7 +1839,7 @@ "signature": [ "DomainDeprecationDetails" ], - "path": "src/core/public/deprecations/deprecations_service.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "isRequired": true } @@ -9180,6 +9168,21 @@ "deprecated": false, "initialIsOpen": false }, + { + "parentPluginId": "core", + "id": "def-public.DomainDeprecationDetails", + "type": "Type", + "tags": [], + "label": "DomainDeprecationDetails", + "description": [], + "signature": [ + "DeprecationsDetails", + " & { domainId: string; }" + ], + "path": "node_modules/@types/kbn__core-deprecations-common/index.d.ts", + "deprecated": false, + "initialIsOpen": false + }, { "parentPluginId": "core", "id": "def-public.EventType", @@ -9560,11 +9563,13 @@ "type": "Type", "tags": [], "label": "ResolveDeprecationResponse", - "description": [], + "description": [ + "\nResponse from correctiveActions.api call from automatically resolving the deprecation" + ], "signature": [ "{ status: \"ok\"; } | { status: \"fail\"; reason: string; }" ], - "path": "src/core/public/deprecations/deprecations_client.ts", + "path": "node_modules/@types/kbn__core-deprecations-browser/index.d.ts", "deprecated": false, "initialIsOpen": false }, @@ -10161,6 +10166,92 @@ }, "server": { "classes": [ + { + "parentPluginId": "core", + "id": "def-server.CspConfig", + "type": "Class", + "tags": [], + "label": "CspConfig", + "description": [ + "\nCSP configuration for use in Kibana." + ], + "signature": [ + "CspConfig", + " implements ", + "ICspConfig" + ], + "path": "node_modules/@types/kbn__core-http-server-internal/index.d.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "core", + "id": "def-server.CspConfig.private", + "type": "Any", + "tags": [], + "label": "#private", + "description": [], + "signature": [ + "any" + ], + "path": "node_modules/@types/kbn__core-http-server-internal/index.d.ts", + "deprecated": false + }, + { + "parentPluginId": "core", + "id": "def-server.CspConfig.DEFAULT", + "type": "Object", + "tags": [], + "label": "DEFAULT", + "description": [], + "signature": [ + "CspConfig" + ], + "path": "node_modules/@types/kbn__core-http-server-internal/index.d.ts", + "deprecated": false + }, + { + "parentPluginId": "core", + "id": "def-server.CspConfig.strict", + "type": "boolean", + "tags": [], + "label": "strict", + "description": [], + "path": "node_modules/@types/kbn__core-http-server-internal/index.d.ts", + "deprecated": false + }, + { + "parentPluginId": "core", + "id": "def-server.CspConfig.warnLegacyBrowsers", + "type": "boolean", + "tags": [], + "label": "warnLegacyBrowsers", + "description": [], + "path": "node_modules/@types/kbn__core-http-server-internal/index.d.ts", + "deprecated": false + }, + { + "parentPluginId": "core", + "id": "def-server.CspConfig.disableEmbedding", + "type": "boolean", + "tags": [], + "label": "disableEmbedding", + "description": [], + "path": "node_modules/@types/kbn__core-http-server-internal/index.d.ts", + "deprecated": false + }, + { + "parentPluginId": "core", + "id": "def-server.CspConfig.header", + "type": "string", + "tags": [], + "label": "header", + "description": [], + "path": "node_modules/@types/kbn__core-http-server-internal/index.d.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, { "parentPluginId": "core", "id": "def-server.ElasticsearchConfig", @@ -11519,120 +11610,6 @@ ], "initialIsOpen": false }, - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails", - "type": "Interface", - "tags": [], - "label": "BaseDeprecationDetails", - "description": [ - "\nBase properties shared by all types of deprecations\n" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false, - "children": [ - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails.title", - "type": "string", - "tags": [], - "label": "title", - "description": [ - "\nThe title of the deprecation.\nCheck the README for writing deprecations in `src/core/server/deprecations/README.mdx`" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails.message", - "type": "string", - "tags": [], - "label": "message", - "description": [ - "\nThe description message to be displayed for the deprecation.\nCheck the README for writing deprecations in `src/core/server/deprecations/README.mdx`" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails.level", - "type": "CompoundType", - "tags": [], - "label": "level", - "description": [ - "\nlevels:\n- warning: will not break deployment upon upgrade\n- critical: needs to be addressed before upgrade.\n- fetch_error: Deprecations service failed to grab the deprecation details for the domain." - ], - "signature": [ - "\"warning\" | \"critical\" | \"fetch_error\"" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails.deprecationType", - "type": "CompoundType", - "tags": [], - "label": "deprecationType", - "description": [ - "\n(optional) Used to identify between different deprecation types.\nExample use case: in Upgrade Assistant, we may want to allow the user to sort by\ndeprecation type or show each type in a separate tab.\n\nFeel free to add new types if necessary.\nPredefined types are necessary to reduce having similar definitions with different keywords\nacross kibana deprecations." - ], - "signature": [ - "\"config\" | \"feature\" | undefined" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails.documentationUrl", - "type": "string", - "tags": [], - "label": "documentationUrl", - "description": [ - "(optional) link to the documentation for more details on the deprecation." - ], - "signature": [ - "string | undefined" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails.requireRestart", - "type": "CompoundType", - "tags": [], - "label": "requireRestart", - "description": [ - "(optional) specify the fix for this deprecation requires a full kibana restart." - ], - "signature": [ - "boolean | undefined" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.BaseDeprecationDetails.correctiveActions", - "type": "Object", - "tags": [], - "label": "correctiveActions", - "description": [ - "corrective action needed to fix this deprecation." - ], - "signature": [ - "{ api?: { path: string; method: \"POST\" | \"PUT\"; body?: { [key: string]: any; } | undefined; omitContextFromBody?: boolean | undefined; } | undefined; manualSteps: string[]; }" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - } - ], - "initialIsOpen": false - }, { "parentPluginId": "core", "id": "def-server.Capabilities", @@ -11950,59 +11927,6 @@ ], "initialIsOpen": false }, - { - "parentPluginId": "core", - "id": "def-server.ConfigDeprecationDetails", - "type": "Interface", - "tags": [], - "label": "ConfigDeprecationDetails", - "description": [], - "signature": [ - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.ConfigDeprecationDetails", - "text": "ConfigDeprecationDetails" - }, - " extends ", - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.BaseDeprecationDetails", - "text": "BaseDeprecationDetails" - } - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false, - "children": [ - { - "parentPluginId": "core", - "id": "def-server.ConfigDeprecationDetails.configPath", - "type": "string", - "tags": [], - "label": "configPath", - "description": [], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.ConfigDeprecationDetails.deprecationType", - "type": "string", - "tags": [], - "label": "deprecationType", - "description": [], - "signature": [ - "\"config\"" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - } - ], - "initialIsOpen": false - }, { "parentPluginId": "core", "id": "def-server.ConfigDeprecationFactory", @@ -14528,49 +14452,6 @@ ], "initialIsOpen": false }, - { - "parentPluginId": "core", - "id": "def-server.FeatureDeprecationDetails", - "type": "Interface", - "tags": [], - "label": "FeatureDeprecationDetails", - "description": [], - "signature": [ - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.FeatureDeprecationDetails", - "text": "FeatureDeprecationDetails" - }, - " extends ", - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.BaseDeprecationDetails", - "text": "BaseDeprecationDetails" - } - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false, - "children": [ - { - "parentPluginId": "core", - "id": "def-server.FeatureDeprecationDetails.deprecationType", - "type": "string", - "tags": [], - "label": "deprecationType", - "description": [], - "signature": [ - "\"feature\" | undefined" - ], - "path": "src/core/server/deprecations/types.ts", - "deprecated": false - } - ], - "initialIsOpen": false - }, { "parentPluginId": "core", "id": "def-server.GetDeprecationsContext", @@ -25796,13 +25677,7 @@ ") => ", "MaybePromise", "<", - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.DeprecationsDetails", - "text": "DeprecationsDetails" - }, + "DeprecationsDetails", "[]>" ], "path": "src/core/server/deprecations/types.ts", @@ -28565,23 +28440,11 @@ "label": "DeprecationsDetails", "description": [], "signature": [ - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.ConfigDeprecationDetails", - "text": "ConfigDeprecationDetails" - }, + "ConfigDeprecationDetails", " | ", - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.FeatureDeprecationDetails", - "text": "FeatureDeprecationDetails" - } + "FeatureDeprecationDetails" ], - "path": "src/core/server/deprecations/types.ts", + "path": "node_modules/@types/kbn__core-deprecations-common/index.d.ts", "deprecated": false, "initialIsOpen": false }, @@ -30480,6 +30343,33 @@ "deprecated": false, "initialIsOpen": false }, + { + "parentPluginId": "core", + "id": "def-server.kibanaResponseFactory", + "type": "CompoundType", + "tags": [], + "label": "kibanaResponseFactory", + "description": [], + "signature": [ + "KibanaSuccessResponseFactory", + " & ", + "KibanaRedirectionResponseFactory", + " & ", + "KibanaErrorResponseFactory", + " & { custom | Error | ", + "Stream", + " | Buffer | { message: string | Error; attributes?: ", + "ResponseErrorAttributes", + " | undefined; } | undefined>(options: ", + "CustomHttpResponseOptions", + "): ", + "IKibanaResponse", + "; }" + ], + "path": "node_modules/@types/kbn__core-http-router-server-internal/index.d.ts", + "deprecated": false, + "initialIsOpen": false + }, { "parentPluginId": "core", "id": "def-server.KibanaResponseFactory", @@ -31461,9 +31351,9 @@ "\nThe set of common HTTP methods supported by Kibana routing." ], "signature": [ - "SafeRouteMethod", + "DestructiveRouteMethod", " | ", - "DestructiveRouteMethod" + "SafeRouteMethod" ], "path": "node_modules/@types/kbn__core-http-server/index.d.ts", "deprecated": false, diff --git a/api_docs/core.mdx b/api_docs/core.mdx index 1ca2a7bd7646b..f1a1c1b2e0dc0 100644 --- a/api_docs/core.mdx +++ b/api_docs/core.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/core title: "core" image: https://source.unsplash.com/400x175/?github summary: API docs for the core plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'core'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) for que | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 2489 | 9 | 746 | 25 | +| 2472 | 6 | 724 | 22 | ## Client diff --git a/api_docs/core_application.mdx b/api_docs/core_application.mdx index 73e1cc4df37c8..b9d2d257b7d28 100644 --- a/api_docs/core_application.mdx +++ b/api_docs/core_application.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/core-application title: "core.application" image: https://source.unsplash.com/400x175/?github summary: API docs for the core.application plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'core.application'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) for que | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 2489 | 9 | 746 | 25 | +| 2472 | 6 | 724 | 22 | ## Client diff --git a/api_docs/core_chrome.mdx b/api_docs/core_chrome.mdx index 38935d4adbf2c..7dfaeefb9d685 100644 --- a/api_docs/core_chrome.mdx +++ b/api_docs/core_chrome.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/core-chrome title: "core.chrome" image: https://source.unsplash.com/400x175/?github summary: API docs for the core.chrome plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'core.chrome'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) for que | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 2489 | 9 | 746 | 25 | +| 2472 | 6 | 724 | 22 | ## Client diff --git a/api_docs/core_http.devdocs.json b/api_docs/core_http.devdocs.json deleted file mode 100644 index 3aea850ad213e..0000000000000 --- a/api_docs/core_http.devdocs.json +++ /dev/null @@ -1,218 +0,0 @@ -{ - "id": "core.http", - "client": { - "classes": [], - "functions": [], - "interfaces": [], - "enums": [], - "misc": [], - "objects": [] - }, - "server": { - "classes": [ - { - "parentPluginId": "core", - "id": "def-server.CspConfig", - "type": "Class", - "tags": [], - "label": "CspConfig", - "description": [ - "\nCSP configuration for use in Kibana." - ], - "signature": [ - { - "pluginId": "core", - "scope": "server", - "docId": "kibCoreHttpPluginApi", - "section": "def-server.CspConfig", - "text": "CspConfig" - }, - " implements ", - "ICspConfig" - ], - "path": "src/core/server/http/csp/csp_config.ts", - "deprecated": false, - "children": [ - { - "parentPluginId": "core", - "id": "def-server.CspConfig.DEFAULT", - "type": "Object", - "tags": [], - "label": "DEFAULT", - "description": [], - "signature": [ - { - "pluginId": "core", - "scope": "server", - "docId": "kibCoreHttpPluginApi", - "section": "def-server.CspConfig", - "text": "CspConfig" - } - ], - "path": "src/core/server/http/csp/csp_config.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.CspConfig.directives", - "type": "Object", - "tags": [], - "label": "#directives", - "description": [], - "signature": [ - "CspDirectives" - ], - "path": "src/core/server/http/csp/csp_config.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.CspConfig.strict", - "type": "boolean", - "tags": [], - "label": "strict", - "description": [], - "path": "src/core/server/http/csp/csp_config.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.CspConfig.warnLegacyBrowsers", - "type": "boolean", - "tags": [], - "label": "warnLegacyBrowsers", - "description": [], - "path": "src/core/server/http/csp/csp_config.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.CspConfig.disableEmbedding", - "type": "boolean", - "tags": [], - "label": "disableEmbedding", - "description": [], - "path": "src/core/server/http/csp/csp_config.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.CspConfig.header", - "type": "string", - "tags": [], - "label": "header", - "description": [], - "path": "src/core/server/http/csp/csp_config.ts", - "deprecated": false - } - ], - "initialIsOpen": false - } - ], - "functions": [], - "interfaces": [], - "enums": [], - "misc": [], - "objects": [ - { - "parentPluginId": "core", - "id": "def-server.kibanaResponseFactory", - "type": "Object", - "tags": [], - "label": "kibanaResponseFactory", - "description": [], - "path": "src/core/server/http/router/response.ts", - "deprecated": false, - "children": [ - { - "parentPluginId": "core", - "id": "def-server.kibanaResponseFactory.Unnamed", - "type": "Any", - "tags": [], - "label": "Unnamed", - "description": [], - "signature": [ - "any" - ], - "path": "src/core/server/http/router/response.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.kibanaResponseFactory.Unnamed", - "type": "Any", - "tags": [], - "label": "Unnamed", - "description": [], - "signature": [ - "any" - ], - "path": "src/core/server/http/router/response.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.kibanaResponseFactory.Unnamed", - "type": "Any", - "tags": [], - "label": "Unnamed", - "description": [], - "signature": [ - "any" - ], - "path": "src/core/server/http/router/response.ts", - "deprecated": false - }, - { - "parentPluginId": "core", - "id": "def-server.kibanaResponseFactory.custom", - "type": "Function", - "tags": [], - "label": "custom", - "description": [], - "signature": [ - " | Error | ", - "Stream", - " | Buffer | { message: string | Error; attributes?: ", - "ResponseErrorAttributes", - " | undefined; } | undefined>(options: ", - "CustomHttpResponseOptions", - ") => ", - "KibanaResponse", - "" - ], - "path": "src/core/server/http/router/response.ts", - "deprecated": false, - "children": [ - { - "parentPluginId": "core", - "id": "def-server.kibanaResponseFactory.custom.$1", - "type": "Object", - "tags": [], - "label": "options", - "description": [], - "signature": [ - "CustomHttpResponseOptions", - "" - ], - "path": "src/core/server/http/router/response.ts", - "deprecated": false, - "isRequired": true - } - ], - "returnComment": [] - } - ], - "initialIsOpen": false - } - ] - }, - "common": { - "classes": [], - "functions": [], - "interfaces": [], - "enums": [], - "misc": [], - "objects": [] - } -} \ No newline at end of file diff --git a/api_docs/core_http.mdx b/api_docs/core_http.mdx deleted file mode 100644 index 3dca29910f474..0000000000000 --- a/api_docs/core_http.mdx +++ /dev/null @@ -1,30 +0,0 @@ ---- -id: kibCoreHttpPluginApi -slug: /kibana-dev-docs/api/core-http -title: "core.http" -image: https://source.unsplash.com/400x175/?github -summary: API docs for the core.http plugin -date: 2022-07-13 -tags: ['contributor', 'dev', 'apidocs', 'kibana', 'core.http'] -warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. ---- -import coreHttpObj from './core_http.devdocs.json'; - - - -Contact [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) for questions regarding this plugin. - -**Code health stats** - -| Public API count | Any count | Items lacking comments | Missing exports | -|-------------------|-----------|------------------------|-----------------| -| 2489 | 9 | 746 | 25 | - -## Server - -### Objects - - -### Classes - - diff --git a/api_docs/core_saved_objects.mdx b/api_docs/core_saved_objects.mdx index ef05af39d188d..c6536a2b385fb 100644 --- a/api_docs/core_saved_objects.mdx +++ b/api_docs/core_saved_objects.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/core-savedObjects title: "core.savedObjects" image: https://source.unsplash.com/400x175/?github summary: API docs for the core.savedObjects plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'core.savedObjects'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) for que | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 2489 | 9 | 746 | 25 | +| 2472 | 6 | 724 | 22 | ## Client diff --git a/api_docs/custom_integrations.mdx b/api_docs/custom_integrations.mdx index ee0b3ef00b9be..92901a3bcc233 100644 --- a/api_docs/custom_integrations.mdx +++ b/api_docs/custom_integrations.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/customIntegrations title: "customIntegrations" image: https://source.unsplash.com/400x175/?github summary: API docs for the customIntegrations plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'customIntegrations'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/dashboard.mdx b/api_docs/dashboard.mdx index 17a5f089230cd..6d6f8231dae94 100644 --- a/api_docs/dashboard.mdx +++ b/api_docs/dashboard.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/dashboard title: "dashboard" image: https://source.unsplash.com/400x175/?github summary: API docs for the dashboard plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'dashboard'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/dashboard_enhanced.mdx b/api_docs/dashboard_enhanced.mdx index cb8a65c67c0e3..9c8b86bab716f 100644 --- a/api_docs/dashboard_enhanced.mdx +++ b/api_docs/dashboard_enhanced.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/dashboardEnhanced title: "dashboardEnhanced" image: https://source.unsplash.com/400x175/?github summary: API docs for the dashboardEnhanced plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'dashboardEnhanced'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/data.devdocs.json b/api_docs/data.devdocs.json index cc89249f62a1b..128560ead897f 100644 --- a/api_docs/data.devdocs.json +++ b/api_docs/data.devdocs.json @@ -645,7 +645,15 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "" + ">" ], "path": "src/plugins/data/common/search/aggs/agg_config.ts", "deprecated": false, @@ -12955,7 +12963,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">) => void" ], @@ -12995,7 +13003,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">" ], @@ -19389,7 +19397,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">) => void" ], @@ -19429,7 +19437,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">" ], @@ -19517,7 +19525,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; esTypes?: string[] | undefined; searchable: boolean; aggregatable: boolean; readFromDocValues?: boolean | undefined; indexed?: boolean | undefined; customLabel?: string | undefined; runtimeField?: ", { @@ -22619,7 +22627,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">> | undefined; runtimeFieldMap?: Record> | undefined; runtimeFieldMap?: Record | undefined; esTypes?: string[] | undefined; searchable: boolean; aggregatable: boolean; readFromDocValues?: boolean | undefined; indexed?: boolean | undefined; customLabel?: string | undefined; runtimeField?: ", { diff --git a/api_docs/data.mdx b/api_docs/data.mdx index f6c01d22f9c87..3822a516eaafb 100644 --- a/api_docs/data.mdx +++ b/api_docs/data.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/data title: "data" image: https://source.unsplash.com/400x175/?github summary: API docs for the data plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'data'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/data_query.mdx b/api_docs/data_query.mdx index 50c49ba0251eb..d5c579e9428a5 100644 --- a/api_docs/data_query.mdx +++ b/api_docs/data_query.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/data-query title: "data.query" image: https://source.unsplash.com/400x175/?github summary: API docs for the data.query plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'data.query'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/data_search.devdocs.json b/api_docs/data_search.devdocs.json index a406c0bcb8d3f..65cfc70b670cd 100644 --- a/api_docs/data_search.devdocs.json +++ b/api_docs/data_search.devdocs.json @@ -1465,16 +1465,7 @@ "docId": "kibDataSearchPluginApi", "section": "def-server.ISearchSessionService", "text": "ISearchSessionService" - }, - "<", - { - "pluginId": "data", - "scope": "common", - "docId": "kibDataSearchPluginApi", - "section": "def-common.SearchSessionSavedObjectAttributes", - "text": "SearchSessionSavedObjectAttributes" - }, - ">" + } ], "path": "src/plugins/data/server/search/session/session_service.ts", "deprecated": false, @@ -2718,9 +2709,25 @@ "label": "saveSession", "description": [], "signature": [ - "(sessionId: string, attributes: Partial) => Promise<", + "(sessionId: string, attributes: Partial<", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionSavedObjectAttributes", + "text": "SearchSessionSavedObjectAttributes" + }, + ">) => Promise<", "SavedObject", - " | undefined>" + "<", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionSavedObjectAttributes", + "text": "SearchSessionSavedObjectAttributes" + }, + "> | undefined>" ], "path": "src/plugins/data/server/search/types.ts", "deprecated": false, @@ -2744,7 +2751,27 @@ "label": "attributes", "description": [], "signature": [ - "{ [P in keyof T]?: T[P] | undefined; }" + "{ sessionId?: string | undefined; name?: string | undefined; appId?: string | undefined; created?: string | undefined; touched?: string | undefined; expires?: string | undefined; completed?: string | null | undefined; status?: ", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionStatus", + "text": "SearchSessionStatus" + }, + " | undefined; locatorId?: string | undefined; initialState?: ", + "SerializableRecord", + " | undefined; restoreState?: ", + "SerializableRecord", + " | undefined; idMapping?: Record | undefined; persisted?: boolean | undefined; realmType?: string | undefined; realmName?: string | undefined; username?: string | undefined; version?: string | undefined; }" ], "path": "src/plugins/data/server/search/session/types.ts", "deprecated": false @@ -2761,7 +2788,15 @@ "signature": [ "(sessionId: string) => Promise<", "SavedObject", - ">" + "<", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionSavedObjectAttributes", + "text": "SearchSessionSavedObjectAttributes" + }, + ">>" ], "path": "src/plugins/data/server/search/types.ts", "deprecated": false, @@ -2803,7 +2838,15 @@ "section": "def-server.SavedObjectsFindResponse", "text": "SavedObjectsFindResponse" }, - ">" + "<", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionSavedObjectAttributes", + "text": "SearchSessionSavedObjectAttributes" + }, + ", unknown>>" ], "path": "src/plugins/data/server/search/types.ts", "deprecated": false, @@ -2860,7 +2903,15 @@ "label": "updateSession", "description": [], "signature": [ - "(sessionId: string, attributes: Partial) => Promise<", + "(sessionId: string, attributes: Partial<", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionSavedObjectAttributes", + "text": "SearchSessionSavedObjectAttributes" + }, + ">) => Promise<", { "pluginId": "core", "scope": "server", @@ -2868,7 +2919,15 @@ "section": "def-server.SavedObjectsUpdateResponse", "text": "SavedObjectsUpdateResponse" }, - ">" + "<", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionSavedObjectAttributes", + "text": "SearchSessionSavedObjectAttributes" + }, + ">>" ], "path": "src/plugins/data/server/search/types.ts", "deprecated": false, @@ -2892,7 +2951,27 @@ "label": "attributes", "description": [], "signature": [ - "{ [P in keyof T]?: T[P] | undefined; }" + "{ sessionId?: string | undefined; name?: string | undefined; appId?: string | undefined; created?: string | undefined; touched?: string | undefined; expires?: string | undefined; completed?: string | null | undefined; status?: ", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionStatus", + "text": "SearchSessionStatus" + }, + " | undefined; locatorId?: string | undefined; initialState?: ", + "SerializableRecord", + " | undefined; restoreState?: ", + "SerializableRecord", + " | undefined; idMapping?: Record | undefined; persisted?: boolean | undefined; realmType?: string | undefined; realmName?: string | undefined; username?: string | undefined; version?: string | undefined; }" ], "path": "src/plugins/data/server/search/session/types.ts", "deprecated": false @@ -2967,7 +3046,15 @@ "section": "def-server.SavedObjectsUpdateResponse", "text": "SavedObjectsUpdateResponse" }, - ">" + "<", + { + "pluginId": "data", + "scope": "common", + "docId": "kibDataSearchPluginApi", + "section": "def-common.SearchSessionSavedObjectAttributes", + "text": "SearchSessionSavedObjectAttributes" + }, + ">>" ], "path": "src/plugins/data/server/search/types.ts", "deprecated": false, @@ -3008,16 +3095,6 @@ "tags": [], "label": "ISearchSessionService", "description": [], - "signature": [ - { - "pluginId": "data", - "scope": "server", - "docId": "kibDataSearchPluginApi", - "section": "def-server.ISearchSessionService", - "text": "ISearchSessionService" - }, - "" - ], "path": "src/plugins/data/server/search/session/types.ts", "deprecated": false, "children": [ @@ -3040,8 +3117,7 @@ ") => (request: ", "KibanaRequest", ") => ", - "IScopedSearchSessionsClient", - "" + "IScopedSearchSessionsClient" ], "path": "src/plugins/data/server/search/session/types.ts", "deprecated": false, @@ -3758,8 +3834,7 @@ "label": "searchSessionsClient", "description": [], "signature": [ - "IScopedSearchSessionsClient", - "" + "IScopedSearchSessionsClient" ], "path": "src/plugins/data/server/search/types.ts", "deprecated": false @@ -4481,7 +4556,15 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "" + ">" ], "path": "src/plugins/data/common/search/aggs/agg_config.ts", "deprecated": false, @@ -7126,7 +7209,15 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "" + ">" ], "path": "src/plugins/data/common/search/aggs/agg_type.ts", "deprecated": false, @@ -21671,7 +21762,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">) | undefined" ], diff --git a/api_docs/data_search.mdx b/api_docs/data_search.mdx index b141bc3f7fa82..606b543770e9b 100644 --- a/api_docs/data_search.mdx +++ b/api_docs/data_search.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/data-search title: "data.search" image: https://source.unsplash.com/400x175/?github summary: API docs for the data.search plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'data.search'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/data_view_editor.devdocs.json b/api_docs/data_view_editor.devdocs.json index edcf82634ea28..a03f5a4289435 100644 --- a/api_docs/data_view_editor.devdocs.json +++ b/api_docs/data_view_editor.devdocs.json @@ -128,6 +128,21 @@ ], "path": "src/plugins/data_view_editor/public/types.ts", "deprecated": false + }, + { + "parentPluginId": "dataViewEditor", + "id": "def-public.DataViewEditorProps.allowAdHocDataView", + "type": "CompoundType", + "tags": [], + "label": "allowAdHocDataView", + "description": [ + "\nif set to true user is presented with an option to create ad-hoc dataview without a saved object." + ], + "signature": [ + "boolean | undefined" + ], + "path": "src/plugins/data_view_editor/public/types.ts", + "deprecated": false } ], "initialIsOpen": false diff --git a/api_docs/data_view_editor.mdx b/api_docs/data_view_editor.mdx index a0dfcb172f2c8..242a4f5e76579 100644 --- a/api_docs/data_view_editor.mdx +++ b/api_docs/data_view_editor.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/dataViewEditor title: "dataViewEditor" image: https://source.unsplash.com/400x175/?github summary: API docs for the dataViewEditor plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'dataViewEditor'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [App Services](https://github.com/orgs/elastic/teams/kibana-app-services | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 14 | 0 | 7 | 0 | +| 15 | 0 | 7 | 0 | ## Client diff --git a/api_docs/data_view_field_editor.devdocs.json b/api_docs/data_view_field_editor.devdocs.json index 8b3e28b5fd93a..7f38835b2639d 100644 --- a/api_docs/data_view_field_editor.devdocs.json +++ b/api_docs/data_view_field_editor.devdocs.json @@ -127,7 +127,7 @@ "label": "onChange", "description": [], "signature": [ - "(newParams?: {}) => void" + "(newParams?: Partial<{ type?: string | undefined; } & P>) => void" ], "path": "src/plugins/data_view_field_editor/public/components/field_format_editor/editors/default/default.tsx", "deprecated": false, @@ -140,7 +140,7 @@ "label": "newParams", "description": [], "signature": [ - "{}" + "Partial<{ type?: string | undefined; } & P>" ], "path": "src/plugins/data_view_field_editor/public/components/field_format_editor/editors/default/default.tsx", "deprecated": false, @@ -242,7 +242,9 @@ "label": "onChange", "description": [], "signature": [ - "(newParams: { [key: string]: any; }) => void" + "(newParams: ", + "SerializableRecord", + ") => void" ], "path": "src/plugins/data_view_field_editor/public/components/field_format_editor/editors/types.ts", "deprecated": false, @@ -254,23 +256,12 @@ "tags": [], "label": "newParams", "description": [], + "signature": [ + "SerializableRecord" + ], "path": "src/plugins/data_view_field_editor/public/components/field_format_editor/editors/types.ts", "deprecated": false, - "children": [ - { - "parentPluginId": "dataViewFieldEditor", - "id": "def-public.FormatEditorProps.onChange.$1.Unnamed", - "type": "IndexSignature", - "tags": [], - "label": "[key: string]: any", - "description": [], - "signature": [ - "[key: string]: any" - ], - "path": "src/plugins/data_view_field_editor/public/components/field_format_editor/editors/types.ts", - "deprecated": false - } - ] + "isRequired": true } ], "returnComment": [] @@ -556,7 +547,7 @@ "section": "def-public.FieldFormatEditorFactory", "text": "FieldFormatEditorFactory" }, - ") => void; }" + "<{}>) => void; }" ], "path": "src/plugins/data_view_field_editor/public/types.ts", "deprecated": false @@ -679,7 +670,7 @@ "section": "def-public.FieldFormatEditorFactory", "text": "FieldFormatEditorFactory" }, - "[]; getById: (id: string) => ", + "<{}>[]; getById:

(id: string) => ", { "pluginId": "dataViewFieldEditor", "scope": "public", @@ -687,7 +678,7 @@ "section": "def-public.FieldFormatEditorFactory", "text": "FieldFormatEditorFactory" }, - " | undefined; }" + "

| undefined; }" ], "path": "src/plugins/data_view_field_editor/public/types.ts", "deprecated": false diff --git a/api_docs/data_view_field_editor.mdx b/api_docs/data_view_field_editor.mdx index 59bf59eefe9bd..64b7f890a340d 100644 --- a/api_docs/data_view_field_editor.mdx +++ b/api_docs/data_view_field_editor.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/dataViewFieldEditor title: "dataViewFieldEditor" image: https://source.unsplash.com/400x175/?github summary: API docs for the dataViewFieldEditor plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'dataViewFieldEditor'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [App Services](https://github.com/orgs/elastic/teams/kibana-app-services | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 42 | 0 | 37 | 3 | +| 41 | 0 | 36 | 3 | ## Client diff --git a/api_docs/data_view_management.mdx b/api_docs/data_view_management.mdx index d1f57d8a709de..f6c1c816c3463 100644 --- a/api_docs/data_view_management.mdx +++ b/api_docs/data_view_management.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/dataViewManagement title: "dataViewManagement" image: https://source.unsplash.com/400x175/?github summary: API docs for the dataViewManagement plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'dataViewManagement'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/data_views.devdocs.json b/api_docs/data_views.devdocs.json index 1182fdba14c4d..69caa706b7227 100644 --- a/api_docs/data_views.devdocs.json +++ b/api_docs/data_views.devdocs.json @@ -1451,7 +1451,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">) => void" ], @@ -1491,7 +1491,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">" ], @@ -1579,7 +1579,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; esTypes?: string[] | undefined; searchable: boolean; aggregatable: boolean; readFromDocValues?: boolean | undefined; indexed?: boolean | undefined; customLabel?: string | undefined; runtimeField?: ", { @@ -5902,7 +5902,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">> | undefined; runtimeFieldMap?: Record | undefined; esTypes?: string[] | undefined; searchable: boolean; aggregatable: boolean; readFromDocValues?: boolean | undefined; indexed?: boolean | undefined; customLabel?: string | undefined; runtimeField?: ", { @@ -7555,7 +7555,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">) => void" ], @@ -7595,7 +7595,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">" ], @@ -10240,7 +10240,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; esTypes?: string[] | undefined; searchable: boolean; aggregatable: boolean; readFromDocValues?: boolean | undefined; indexed?: boolean | undefined; customLabel?: string | undefined; runtimeField?: ", { @@ -13560,7 +13560,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">) => void" ], @@ -13600,7 +13600,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">" ], @@ -13688,7 +13688,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; esTypes?: string[] | undefined; searchable: boolean; aggregatable: boolean; readFromDocValues?: boolean | undefined; indexed?: boolean | undefined; customLabel?: string | undefined; runtimeField?: ", { @@ -17765,7 +17765,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | null | undefined" ], @@ -18532,7 +18532,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">> | undefined; runtimeFieldMap?: Record> | undefined; runtimeFieldMap?: Record; }" ], @@ -19966,7 +19966,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; esTypes?: string[] | undefined; searchable: boolean; aggregatable: boolean; readFromDocValues?: boolean | undefined; indexed?: boolean | undefined; customLabel?: string | undefined; runtimeField?: ", { diff --git a/api_docs/data_views.mdx b/api_docs/data_views.mdx index affa6f0e564e2..f5ad4f7c782d3 100644 --- a/api_docs/data_views.mdx +++ b/api_docs/data_views.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/dataViews title: "dataViews" image: https://source.unsplash.com/400x175/?github summary: API docs for the dataViews plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'dataViews'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/data_visualizer.mdx b/api_docs/data_visualizer.mdx index 7c3260f17f381..ca0383f02bd8c 100644 --- a/api_docs/data_visualizer.mdx +++ b/api_docs/data_visualizer.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/dataVisualizer title: "dataVisualizer" image: https://source.unsplash.com/400x175/?github summary: API docs for the dataVisualizer plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'dataVisualizer'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/deprecations_by_api.mdx b/api_docs/deprecations_by_api.mdx index 671d479bbccc2..2b8ef4377da72 100644 --- a/api_docs/deprecations_by_api.mdx +++ b/api_docs/deprecations_by_api.mdx @@ -3,7 +3,7 @@ id: kibDevDocsDeprecationsByApi slug: /kibana-dev-docs/api-meta/deprecated-api-list-by-api title: Deprecated API usage by API summary: A list of deprecated APIs, which plugins are still referencing them, and when they need to be removed by. -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. --- diff --git a/api_docs/deprecations_by_plugin.mdx b/api_docs/deprecations_by_plugin.mdx index fab0384a628df..1c116f6874be7 100644 --- a/api_docs/deprecations_by_plugin.mdx +++ b/api_docs/deprecations_by_plugin.mdx @@ -3,7 +3,7 @@ id: kibDevDocsDeprecationsByPlugin slug: /kibana-dev-docs/api-meta/deprecated-api-list-by-plugin title: Deprecated API usage by plugin summary: A list of deprecated APIs, which plugins are still referencing them, and when they need to be removed by. -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. --- @@ -217,7 +217,7 @@ so TS and code-reference navigation might not highlight them. | | Deprecated API | Reference location(s) | Remove By | | ---------------|-----------|-----------| | | [page_template.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx#:~:text=KibanaPageTemplateProps), [page_template.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx#:~:text=KibanaPageTemplateProps) | - | -| | [version_mismatch_page.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/version_mismatch/version_mismatch_page.tsx#:~:text=KibanaPageTemplate), [version_mismatch_page.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/version_mismatch/version_mismatch_page.tsx#:~:text=KibanaPageTemplate), [version_mismatch_page.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/version_mismatch/version_mismatch_page.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate), [product_selector.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/product_selector/product_selector.tsx#:~:text=KibanaPageTemplate), [product_selector.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/product_selector/product_selector.tsx#:~:text=KibanaPageTemplate), [product_selector.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/product_selector/product_selector.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate)+ 11 more | - | +| | [version_mismatch_page.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/version_mismatch/version_mismatch_page.tsx#:~:text=KibanaPageTemplate), [version_mismatch_page.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/version_mismatch/version_mismatch_page.tsx#:~:text=KibanaPageTemplate), [version_mismatch_page.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/version_mismatch/version_mismatch_page.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate), [page_template.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx#:~:text=KibanaPageTemplate), [page_template.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx#:~:text=KibanaPageTemplate), [page_template.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx#:~:text=KibanaPageTemplate), [error_connecting.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/error_connecting/error_connecting.tsx#:~:text=KibanaPageTemplate)+ 8 more | - | | | [account_settings.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/workplace_search/views/account_settings/account_settings.tsx#:~:text=uiApi), [account_settings.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/workplace_search/views/account_settings/account_settings.tsx#:~:text=uiApi), [account_settings.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/workplace_search/views/account_settings/account_settings.tsx#:~:text=uiApi), [account_settings.tsx](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/public/applications/workplace_search/views/account_settings/account_settings.tsx#:~:text=uiApi) | - | | | [check_access.ts](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/server/lib/check_access.ts#:~:text=authz), [check_access.ts](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/server/lib/check_access.ts#:~:text=authz), [check_access.ts](https://github.com/elastic/kibana/tree/master/x-pack/plugins/enterprise_search/server/lib/check_access.ts#:~:text=authz) | - | diff --git a/api_docs/deprecations_by_team.mdx b/api_docs/deprecations_by_team.mdx index 8d5fe5e1eae5d..ec25b9ed7e4d5 100644 --- a/api_docs/deprecations_by_team.mdx +++ b/api_docs/deprecations_by_team.mdx @@ -3,7 +3,7 @@ id: kibDevDocsDeprecationsDueByTeam slug: /kibana-dev-docs/api-meta/deprecations-due-by-team title: Deprecated APIs due to be removed, by team summary: Lists the teams that are referencing deprecated APIs with a remove by date. -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. --- diff --git a/api_docs/dev_tools.mdx b/api_docs/dev_tools.mdx index aa54cbe4f050e..3bbded301146a 100644 --- a/api_docs/dev_tools.mdx +++ b/api_docs/dev_tools.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/devTools title: "devTools" image: https://source.unsplash.com/400x175/?github summary: API docs for the devTools plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'devTools'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/discover.mdx b/api_docs/discover.mdx index f65c671bed195..9ee768d6ccff2 100644 --- a/api_docs/discover.mdx +++ b/api_docs/discover.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/discover title: "discover" image: https://source.unsplash.com/400x175/?github summary: API docs for the discover plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'discover'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/discover_enhanced.mdx b/api_docs/discover_enhanced.mdx index 0e9c5ec48c255..942b1a2791147 100644 --- a/api_docs/discover_enhanced.mdx +++ b/api_docs/discover_enhanced.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/discoverEnhanced title: "discoverEnhanced" image: https://source.unsplash.com/400x175/?github summary: API docs for the discoverEnhanced plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'discoverEnhanced'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/elastic_apm_synthtrace.mdx b/api_docs/elastic_apm_synthtrace.mdx index 5ca22a26a6e36..652bcb829b36d 100644 --- a/api_docs/elastic_apm_synthtrace.mdx +++ b/api_docs/elastic_apm_synthtrace.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/elastic-apm-synthtrace title: "@elastic/apm-synthtrace" image: https://source.unsplash.com/400x175/?github summary: API docs for the @elastic/apm-synthtrace plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@elastic/apm-synthtrace'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/embeddable.mdx b/api_docs/embeddable.mdx index e4131ab27841b..4a53f6c3bc704 100644 --- a/api_docs/embeddable.mdx +++ b/api_docs/embeddable.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/embeddable title: "embeddable" image: https://source.unsplash.com/400x175/?github summary: API docs for the embeddable plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'embeddable'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/embeddable_enhanced.mdx b/api_docs/embeddable_enhanced.mdx index 57a314069ec80..722821b64b8b9 100644 --- a/api_docs/embeddable_enhanced.mdx +++ b/api_docs/embeddable_enhanced.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/embeddableEnhanced title: "embeddableEnhanced" image: https://source.unsplash.com/400x175/?github summary: API docs for the embeddableEnhanced plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'embeddableEnhanced'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/encrypted_saved_objects.mdx b/api_docs/encrypted_saved_objects.mdx index 6d81ac8710d6d..25760de133fcd 100644 --- a/api_docs/encrypted_saved_objects.mdx +++ b/api_docs/encrypted_saved_objects.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/encryptedSavedObjects title: "encryptedSavedObjects" image: https://source.unsplash.com/400x175/?github summary: API docs for the encryptedSavedObjects plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'encryptedSavedObjects'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/enterprise_search.mdx b/api_docs/enterprise_search.mdx index e63cd6c903d56..ca000e0cbdda2 100644 --- a/api_docs/enterprise_search.mdx +++ b/api_docs/enterprise_search.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/enterpriseSearch title: "enterpriseSearch" image: https://source.unsplash.com/400x175/?github summary: API docs for the enterpriseSearch plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'enterpriseSearch'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/es_ui_shared.mdx b/api_docs/es_ui_shared.mdx index 9af8efc8273f8..744edc9147194 100644 --- a/api_docs/es_ui_shared.mdx +++ b/api_docs/es_ui_shared.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/esUiShared title: "esUiShared" image: https://source.unsplash.com/400x175/?github summary: API docs for the esUiShared plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'esUiShared'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/event_annotation.mdx b/api_docs/event_annotation.mdx index ef1af364265bd..0cb6faf9f7921 100644 --- a/api_docs/event_annotation.mdx +++ b/api_docs/event_annotation.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/eventAnnotation title: "eventAnnotation" image: https://source.unsplash.com/400x175/?github summary: API docs for the eventAnnotation plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'eventAnnotation'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/event_log.mdx b/api_docs/event_log.mdx index 8f4e382d5481b..bf8a6079f2f48 100644 --- a/api_docs/event_log.mdx +++ b/api_docs/event_log.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/eventLog title: "eventLog" image: https://source.unsplash.com/400x175/?github summary: API docs for the eventLog plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'eventLog'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_error.mdx b/api_docs/expression_error.mdx index 51094be114475..fdb9f22e90e41 100644 --- a/api_docs/expression_error.mdx +++ b/api_docs/expression_error.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionError title: "expressionError" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionError plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionError'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_gauge.devdocs.json b/api_docs/expression_gauge.devdocs.json index c3acd6e8b013f..89a17fbf23fa0 100644 --- a/api_docs/expression_gauge.devdocs.json +++ b/api_docs/expression_gauge.devdocs.json @@ -898,7 +898,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined) => ", { @@ -928,7 +928,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined" ], diff --git a/api_docs/expression_gauge.mdx b/api_docs/expression_gauge.mdx index e50484b266e4c..bfe26a9810ee1 100644 --- a/api_docs/expression_gauge.mdx +++ b/api_docs/expression_gauge.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionGauge title: "expressionGauge" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionGauge plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionGauge'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_heatmap.devdocs.json b/api_docs/expression_heatmap.devdocs.json index 0a8c0f54bc641..6cc1961115e4e 100644 --- a/api_docs/expression_heatmap.devdocs.json +++ b/api_docs/expression_heatmap.devdocs.json @@ -485,7 +485,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined) => ", { @@ -515,7 +515,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined" ], diff --git a/api_docs/expression_heatmap.mdx b/api_docs/expression_heatmap.mdx index 685f99a7ba9e0..ba8d4bde0ea74 100644 --- a/api_docs/expression_heatmap.mdx +++ b/api_docs/expression_heatmap.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionHeatmap title: "expressionHeatmap" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionHeatmap plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionHeatmap'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_image.mdx b/api_docs/expression_image.mdx index 2e1f71c8bdd5c..5090c83da7a37 100644 --- a/api_docs/expression_image.mdx +++ b/api_docs/expression_image.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionImage title: "expressionImage" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionImage plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionImage'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_legacy_metric_vis.mdx b/api_docs/expression_legacy_metric_vis.mdx index 9e6300966a37f..c60be92df439d 100644 --- a/api_docs/expression_legacy_metric_vis.mdx +++ b/api_docs/expression_legacy_metric_vis.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionLegacyMetricVis title: "expressionLegacyMetricVis" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionLegacyMetricVis plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionLegacyMetricVis'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_metric.mdx b/api_docs/expression_metric.mdx index e8985aa1d6ed7..448a10c15c0a0 100644 --- a/api_docs/expression_metric.mdx +++ b/api_docs/expression_metric.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionMetric title: "expressionMetric" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionMetric plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionMetric'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_metric_vis.mdx b/api_docs/expression_metric_vis.mdx index ed1d2c1b8385d..a8fbfe9dccf90 100644 --- a/api_docs/expression_metric_vis.mdx +++ b/api_docs/expression_metric_vis.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionMetricVis title: "expressionMetricVis" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionMetricVis plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionMetricVis'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_partition_vis.devdocs.json b/api_docs/expression_partition_vis.devdocs.json index 215825a71615f..2f6134f683007 100644 --- a/api_docs/expression_partition_vis.devdocs.json +++ b/api_docs/expression_partition_vis.devdocs.json @@ -253,7 +253,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; }" ], diff --git a/api_docs/expression_partition_vis.mdx b/api_docs/expression_partition_vis.mdx index 0dc3ea7c83883..0b3d3ec2cb487 100644 --- a/api_docs/expression_partition_vis.mdx +++ b/api_docs/expression_partition_vis.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionPartitionVis title: "expressionPartitionVis" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionPartitionVis plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionPartitionVis'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_repeat_image.mdx b/api_docs/expression_repeat_image.mdx index fff23cee1715b..2ef5c54bd07e5 100644 --- a/api_docs/expression_repeat_image.mdx +++ b/api_docs/expression_repeat_image.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionRepeatImage title: "expressionRepeatImage" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionRepeatImage plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionRepeatImage'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_reveal_image.mdx b/api_docs/expression_reveal_image.mdx index 03329e37a283c..39653b4b02bc8 100644 --- a/api_docs/expression_reveal_image.mdx +++ b/api_docs/expression_reveal_image.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionRevealImage title: "expressionRevealImage" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionRevealImage plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionRevealImage'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_shape.mdx b/api_docs/expression_shape.mdx index e9b3fd2668ae8..62d44a3f287a4 100644 --- a/api_docs/expression_shape.mdx +++ b/api_docs/expression_shape.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionShape title: "expressionShape" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionShape plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionShape'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_tagcloud.mdx b/api_docs/expression_tagcloud.mdx index 1cf371bedce39..58c5ff7542301 100644 --- a/api_docs/expression_tagcloud.mdx +++ b/api_docs/expression_tagcloud.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionTagcloud title: "expressionTagcloud" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionTagcloud plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionTagcloud'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expression_x_y.devdocs.json b/api_docs/expression_x_y.devdocs.json index 8e4323a0f0114..4f47ae934bf4d 100644 --- a/api_docs/expression_x_y.devdocs.json +++ b/api_docs/expression_x_y.devdocs.json @@ -96,10 +96,10 @@ }, { "parentPluginId": "expressionXY", - "id": "def-common.AnnotationLayerArgs.hide", + "id": "def-common.AnnotationLayerArgs.simpleView", "type": "CompoundType", "tags": [], - "label": "hide", + "label": "simpleView", "description": [], "signature": [ "boolean | undefined" @@ -582,10 +582,10 @@ }, { "parentPluginId": "expressionXY", - "id": "def-common.DataLayerArgs.hide", + "id": "def-common.DataLayerArgs.simpleView", "type": "CompoundType", "tags": [], - "label": "hide", + "label": "simpleView", "description": [], "signature": [ "boolean | undefined" diff --git a/api_docs/expression_x_y.mdx b/api_docs/expression_x_y.mdx index 07590478a7e0e..3e646cc1d4144 100644 --- a/api_docs/expression_x_y.mdx +++ b/api_docs/expression_x_y.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressionXY title: "expressionXY" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressionXY plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressionXY'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/expressions.devdocs.json b/api_docs/expressions.devdocs.json index bea645fca66b1..dd9b0e90dcf4c 100644 --- a/api_docs/expressions.devdocs.json +++ b/api_docs/expressions.devdocs.json @@ -27942,7 +27942,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined" ], diff --git a/api_docs/expressions.mdx b/api_docs/expressions.mdx index f8c304a1aeab4..239e15f230145 100644 --- a/api_docs/expressions.mdx +++ b/api_docs/expressions.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/expressions title: "expressions" image: https://source.unsplash.com/400x175/?github summary: API docs for the expressions plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'expressions'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/features.mdx b/api_docs/features.mdx index d6353777ae421..b2e2cb8636e8f 100644 --- a/api_docs/features.mdx +++ b/api_docs/features.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/features title: "features" image: https://source.unsplash.com/400x175/?github summary: API docs for the features plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'features'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/field_formats.devdocs.json b/api_docs/field_formats.devdocs.json index 1fbc728768522..6ee4a0284f9f5 100644 --- a/api_docs/field_formats.devdocs.json +++ b/api_docs/field_formats.devdocs.json @@ -2116,7 +2116,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined) => ", { @@ -2145,7 +2145,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined" ], @@ -4878,7 +4878,8 @@ "\nParams provided when creating a formatter.\nParams are vary per formatter\n\nTODO: support strict typing for params depending on format type\nhttps://github.com/elastic/kibana/issues/108158" ], "signature": [ - "SerializableRecord" + "SerializableRecord", + " & P" ], "path": "src/plugins/field_formats/common/types.ts", "deprecated": false, @@ -5082,7 +5083,7 @@ "label": "FormatFactory", "description": [], "signature": [ - "(mapping?: ", + "

(mapping?: ", { "pluginId": "fieldFormats", "scope": "common", @@ -5090,9 +5091,15 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", - "SerializableRecord", - "> | undefined) => ", + "> | undefined) => ", { "pluginId": "fieldFormats", "scope": "common", @@ -5120,9 +5127,15 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", - "SerializableRecord", - "> | undefined" + "> | undefined" ], "path": "src/plugins/field_formats/common/types.ts", "deprecated": false diff --git a/api_docs/field_formats.mdx b/api_docs/field_formats.mdx index 3f308b1e45891..be83fc50e1a71 100644 --- a/api_docs/field_formats.mdx +++ b/api_docs/field_formats.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/fieldFormats title: "fieldFormats" image: https://source.unsplash.com/400x175/?github summary: API docs for the fieldFormats plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'fieldFormats'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/file_upload.mdx b/api_docs/file_upload.mdx index 0a0984a7c1b61..483619e1e4180 100644 --- a/api_docs/file_upload.mdx +++ b/api_docs/file_upload.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/fileUpload title: "fileUpload" image: https://source.unsplash.com/400x175/?github summary: API docs for the fileUpload plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'fileUpload'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/fleet.devdocs.json b/api_docs/fleet.devdocs.json index 0e8db05a8eb7a..aec385e2eab76 100644 --- a/api_docs/fleet.devdocs.json +++ b/api_docs/fleet.devdocs.json @@ -564,6 +564,19 @@ "path": "x-pack/plugins/fleet/common/types/models/package_policy.ts", "deprecated": false }, + { + "parentPluginId": "fleet", + "id": "def-public.NewPackagePolicy.is_managed", + "type": "CompoundType", + "tags": [], + "label": "is_managed", + "description": [], + "signature": [ + "boolean | undefined" + ], + "path": "x-pack/plugins/fleet/common/types/models/package_policy.ts", + "deprecated": false + }, { "parentPluginId": "fleet", "id": "def-public.NewPackagePolicy.policy_id", @@ -1342,7 +1355,7 @@ "The updated Integration Policy to be merged back and included in the API call" ], "signature": [ - "{ id?: string | number | undefined; name?: string | undefined; description?: string | undefined; namespace?: string | undefined; enabled?: boolean | undefined; policy_id?: string | undefined; output_id?: string | undefined; package?: ", + "{ id?: string | number | undefined; name?: string | undefined; description?: string | undefined; namespace?: string | undefined; enabled?: boolean | undefined; is_managed?: boolean | undefined; policy_id?: string | undefined; output_id?: string | undefined; package?: ", { "pluginId": "fleet", "scope": "common", @@ -10545,6 +10558,19 @@ "description": [], "path": "x-pack/plugins/fleet/common/types/models/agent_policy.ts", "deprecated": false + }, + { + "parentPluginId": "fleet", + "id": "def-common.AgentPolicy.agents", + "type": "number", + "tags": [], + "label": "agents", + "description": [], + "signature": [ + "number | undefined" + ], + "path": "x-pack/plugins/fleet/common/types/models/agent_policy.ts", + "deprecated": false } ], "initialIsOpen": false @@ -16436,6 +16462,19 @@ "path": "x-pack/plugins/fleet/common/types/models/package_policy.ts", "deprecated": false }, + { + "parentPluginId": "fleet", + "id": "def-common.NewPackagePolicy.is_managed", + "type": "CompoundType", + "tags": [], + "label": "is_managed", + "description": [], + "signature": [ + "boolean | undefined" + ], + "path": "x-pack/plugins/fleet/common/types/models/package_policy.ts", + "deprecated": false + }, { "parentPluginId": "fleet", "id": "def-common.NewPackagePolicy.policy_id", @@ -20222,7 +20261,7 @@ "section": "def-common.ValueOf", "text": "ValueOf" }, - "<{ readonly Active: \"active\"; readonly Inactive: \"inactive\"; }>; description?: string | undefined; name: string; updated_at: string; namespace: string; updated_by: string; is_default?: boolean | undefined; is_default_fleet_server?: boolean | undefined; has_fleet_server?: boolean | undefined; is_managed: boolean; monitoring_enabled?: (\"metrics\" | \"logs\")[] | undefined; unenroll_timeout?: number | undefined; is_preconfigured?: boolean | undefined; data_output_id?: string | null | undefined; monitoring_output_id?: string | null | undefined; download_source_id?: string | null | undefined; package_policies: string[] | ", + "<{ readonly Active: \"active\"; readonly Inactive: \"inactive\"; }>; description?: string | undefined; name: string; updated_at: string; namespace: string; updated_by: string; is_managed: boolean; is_default?: boolean | undefined; is_default_fleet_server?: boolean | undefined; has_fleet_server?: boolean | undefined; monitoring_enabled?: (\"metrics\" | \"logs\")[] | undefined; unenroll_timeout?: number | undefined; is_preconfigured?: boolean | undefined; data_output_id?: string | null | undefined; monitoring_output_id?: string | null | undefined; download_source_id?: string | null | undefined; package_policies: string[] | ", { "pluginId": "fleet", "scope": "common", @@ -20230,7 +20269,7 @@ "section": "def-common.PackagePolicy", "text": "PackagePolicy" }, - "[]; revision: number; }" + "[]; revision: number; agents?: number | undefined; }" ], "path": "x-pack/plugins/fleet/common/types/models/agent_policy.ts", "deprecated": false, @@ -22293,7 +22332,7 @@ "section": "def-common.PackagePolicyInput", "text": "PackagePolicyInput" }, - "[]; policy_id: string; output_id: string; revision: number; }" + "[]; is_managed?: boolean | undefined; policy_id: string; output_id: string; revision: number; }" ], "path": "x-pack/plugins/fleet/common/types/models/package_policy.ts", "deprecated": false, diff --git a/api_docs/fleet.mdx b/api_docs/fleet.mdx index 9e4d8abbf4299..0c6b50fdcbaba 100644 --- a/api_docs/fleet.mdx +++ b/api_docs/fleet.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/fleet title: "fleet" image: https://source.unsplash.com/400x175/?github summary: API docs for the fleet plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'fleet'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [Fleet](https://github.com/orgs/elastic/teams/fleet) for questions regar | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 1522 | 8 | 1390 | 10 | +| 1525 | 8 | 1393 | 10 | ## Client diff --git a/api_docs/global_search.mdx b/api_docs/global_search.mdx index dd60d001c83c5..2723d4f6e8c65 100644 --- a/api_docs/global_search.mdx +++ b/api_docs/global_search.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/globalSearch title: "globalSearch" image: https://source.unsplash.com/400x175/?github summary: API docs for the globalSearch plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'globalSearch'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/home.mdx b/api_docs/home.mdx index dcf20af6a1d11..f854b50ca3c46 100644 --- a/api_docs/home.mdx +++ b/api_docs/home.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/home title: "home" image: https://source.unsplash.com/400x175/?github summary: API docs for the home plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'home'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/index_lifecycle_management.mdx b/api_docs/index_lifecycle_management.mdx index c806e66c7e64b..4fc5d960a2148 100644 --- a/api_docs/index_lifecycle_management.mdx +++ b/api_docs/index_lifecycle_management.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/indexLifecycleManagement title: "indexLifecycleManagement" image: https://source.unsplash.com/400x175/?github summary: API docs for the indexLifecycleManagement plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'indexLifecycleManagement'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/index_management.mdx b/api_docs/index_management.mdx index 05e767cf2fc4c..8dd28aa8de103 100644 --- a/api_docs/index_management.mdx +++ b/api_docs/index_management.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/indexManagement title: "indexManagement" image: https://source.unsplash.com/400x175/?github summary: API docs for the indexManagement plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'indexManagement'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/infra.mdx b/api_docs/infra.mdx index d2c9347b374b5..cc46935d05be2 100644 --- a/api_docs/infra.mdx +++ b/api_docs/infra.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/infra title: "infra" image: https://source.unsplash.com/400x175/?github summary: API docs for the infra plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'infra'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/inspector.mdx b/api_docs/inspector.mdx index db6eb55ddad01..94489a03e5334 100644 --- a/api_docs/inspector.mdx +++ b/api_docs/inspector.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/inspector title: "inspector" image: https://source.unsplash.com/400x175/?github summary: API docs for the inspector plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'inspector'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/interactive_setup.mdx b/api_docs/interactive_setup.mdx index 632870059bc83..bc5f5239b9121 100644 --- a/api_docs/interactive_setup.mdx +++ b/api_docs/interactive_setup.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/interactiveSetup title: "interactiveSetup" image: https://source.unsplash.com/400x175/?github summary: API docs for the interactiveSetup plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'interactiveSetup'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ace.mdx b/api_docs/kbn_ace.mdx index d33da0ffedfeb..3a0fb68f7e276 100644 --- a/api_docs/kbn_ace.mdx +++ b/api_docs/kbn_ace.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ace title: "@kbn/ace" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ace plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ace'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_aiops_components.mdx b/api_docs/kbn_aiops_components.mdx index 67908b73aaf91..f892382e2d980 100644 --- a/api_docs/kbn_aiops_components.mdx +++ b/api_docs/kbn_aiops_components.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-aiops-components title: "@kbn/aiops-components" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/aiops-components plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/aiops-components'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_aiops_utils.mdx b/api_docs/kbn_aiops_utils.mdx index 16b93b3725319..3c4a88c4ece35 100644 --- a/api_docs/kbn_aiops_utils.mdx +++ b/api_docs/kbn_aiops_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-aiops-utils title: "@kbn/aiops-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/aiops-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/aiops-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_alerts.mdx b/api_docs/kbn_alerts.mdx index 50b568cc1982a..7576954a8e867 100644 --- a/api_docs/kbn_alerts.mdx +++ b/api_docs/kbn_alerts.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-alerts title: "@kbn/alerts" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/alerts plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/alerts'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_analytics.mdx b/api_docs/kbn_analytics.mdx index 13aa2734bd079..58d40c7854834 100644 --- a/api_docs/kbn_analytics.mdx +++ b/api_docs/kbn_analytics.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-analytics title: "@kbn/analytics" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/analytics plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/analytics'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_analytics_client.mdx b/api_docs/kbn_analytics_client.mdx index 276c72a842dfc..0f99bb0d50192 100644 --- a/api_docs/kbn_analytics_client.mdx +++ b/api_docs/kbn_analytics_client.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-analytics-client title: "@kbn/analytics-client" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/analytics-client plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/analytics-client'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_analytics_shippers_elastic_v3_browser.mdx b/api_docs/kbn_analytics_shippers_elastic_v3_browser.mdx index 4b9a8759b2b1b..89df1534b5024 100644 --- a/api_docs/kbn_analytics_shippers_elastic_v3_browser.mdx +++ b/api_docs/kbn_analytics_shippers_elastic_v3_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-analytics-shippers-elastic-v3-browser title: "@kbn/analytics-shippers-elastic-v3-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/analytics-shippers-elastic-v3-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/analytics-shippers-elastic-v3-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_analytics_shippers_elastic_v3_common.mdx b/api_docs/kbn_analytics_shippers_elastic_v3_common.mdx index 7e0390fc7d255..042d33148c7ab 100644 --- a/api_docs/kbn_analytics_shippers_elastic_v3_common.mdx +++ b/api_docs/kbn_analytics_shippers_elastic_v3_common.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-analytics-shippers-elastic-v3-common title: "@kbn/analytics-shippers-elastic-v3-common" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/analytics-shippers-elastic-v3-common plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/analytics-shippers-elastic-v3-common'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_analytics_shippers_elastic_v3_server.mdx b/api_docs/kbn_analytics_shippers_elastic_v3_server.mdx index 8e9c1a191211b..6eab6975ace2a 100644 --- a/api_docs/kbn_analytics_shippers_elastic_v3_server.mdx +++ b/api_docs/kbn_analytics_shippers_elastic_v3_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-analytics-shippers-elastic-v3-server title: "@kbn/analytics-shippers-elastic-v3-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/analytics-shippers-elastic-v3-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/analytics-shippers-elastic-v3-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_analytics_shippers_fullstory.mdx b/api_docs/kbn_analytics_shippers_fullstory.mdx index 17813d56492b2..1a6c6a6c29a8c 100644 --- a/api_docs/kbn_analytics_shippers_fullstory.mdx +++ b/api_docs/kbn_analytics_shippers_fullstory.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-analytics-shippers-fullstory title: "@kbn/analytics-shippers-fullstory" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/analytics-shippers-fullstory plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/analytics-shippers-fullstory'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_apm_config_loader.mdx b/api_docs/kbn_apm_config_loader.mdx index 5c00309bd8842..24b69f7e51081 100644 --- a/api_docs/kbn_apm_config_loader.mdx +++ b/api_docs/kbn_apm_config_loader.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-apm-config-loader title: "@kbn/apm-config-loader" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/apm-config-loader plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/apm-config-loader'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_apm_utils.mdx b/api_docs/kbn_apm_utils.mdx index 5203af444072a..1e5722fe7e8cc 100644 --- a/api_docs/kbn_apm_utils.mdx +++ b/api_docs/kbn_apm_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-apm-utils title: "@kbn/apm-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/apm-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/apm-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_axe_config.mdx b/api_docs/kbn_axe_config.mdx index c94abfadcbe05..a8f7220cc05ad 100644 --- a/api_docs/kbn_axe_config.mdx +++ b/api_docs/kbn_axe_config.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-axe-config title: "@kbn/axe-config" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/axe-config plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/axe-config'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_bazel_packages.mdx b/api_docs/kbn_bazel_packages.mdx index 99c31ede3a39d..7aeda72838515 100644 --- a/api_docs/kbn_bazel_packages.mdx +++ b/api_docs/kbn_bazel_packages.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-bazel-packages title: "@kbn/bazel-packages" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/bazel-packages plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/bazel-packages'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_bazel_runner.mdx b/api_docs/kbn_bazel_runner.mdx index 6d99f6c5f5299..54d8e93528fc5 100644 --- a/api_docs/kbn_bazel_runner.mdx +++ b/api_docs/kbn_bazel_runner.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-bazel-runner title: "@kbn/bazel-runner" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/bazel-runner plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/bazel-runner'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ci_stats_core.mdx b/api_docs/kbn_ci_stats_core.mdx index dc14fb459eb97..3ca28e5a00a81 100644 --- a/api_docs/kbn_ci_stats_core.mdx +++ b/api_docs/kbn_ci_stats_core.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ci-stats-core title: "@kbn/ci-stats-core" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ci-stats-core plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ci-stats-core'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ci_stats_performance_metrics.mdx b/api_docs/kbn_ci_stats_performance_metrics.mdx index 38dc0a15f5175..11f5ff83daab5 100644 --- a/api_docs/kbn_ci_stats_performance_metrics.mdx +++ b/api_docs/kbn_ci_stats_performance_metrics.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ci-stats-performance-metrics title: "@kbn/ci-stats-performance-metrics" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ci-stats-performance-metrics plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ci-stats-performance-metrics'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ci_stats_reporter.mdx b/api_docs/kbn_ci_stats_reporter.mdx index 869643ad84802..1df2abbea0d2e 100644 --- a/api_docs/kbn_ci_stats_reporter.mdx +++ b/api_docs/kbn_ci_stats_reporter.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ci-stats-reporter title: "@kbn/ci-stats-reporter" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ci-stats-reporter plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ci-stats-reporter'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_cli_dev_mode.mdx b/api_docs/kbn_cli_dev_mode.mdx index 15587ab667343..44ef4146a587a 100644 --- a/api_docs/kbn_cli_dev_mode.mdx +++ b/api_docs/kbn_cli_dev_mode.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-cli-dev-mode title: "@kbn/cli-dev-mode" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/cli-dev-mode plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/cli-dev-mode'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_coloring.mdx b/api_docs/kbn_coloring.mdx index 471a883e4db00..37692b467b530 100644 --- a/api_docs/kbn_coloring.mdx +++ b/api_docs/kbn_coloring.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-coloring title: "@kbn/coloring" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/coloring plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/coloring'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_config.mdx b/api_docs/kbn_config.mdx index e3f717c4d980a..ba10ea449d7ed 100644 --- a/api_docs/kbn_config.mdx +++ b/api_docs/kbn_config.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-config title: "@kbn/config" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/config plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/config'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_config_mocks.mdx b/api_docs/kbn_config_mocks.mdx index c8d686e8deda8..c5e14a6ce3ef8 100644 --- a/api_docs/kbn_config_mocks.mdx +++ b/api_docs/kbn_config_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-config-mocks title: "@kbn/config-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/config-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/config-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_config_schema.mdx b/api_docs/kbn_config_schema.mdx index a9387c456838b..e2369107ebad8 100644 --- a/api_docs/kbn_config_schema.mdx +++ b/api_docs/kbn_config_schema.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-config-schema title: "@kbn/config-schema" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/config-schema plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/config-schema'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_analytics_browser.mdx b/api_docs/kbn_core_analytics_browser.mdx index 2fc459ffbbe1a..f279096a8aeb8 100644 --- a/api_docs/kbn_core_analytics_browser.mdx +++ b/api_docs/kbn_core_analytics_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-analytics-browser title: "@kbn/core-analytics-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-analytics-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-analytics-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_analytics_browser_internal.mdx b/api_docs/kbn_core_analytics_browser_internal.mdx index c28cc9230262a..6e9c64f546655 100644 --- a/api_docs/kbn_core_analytics_browser_internal.mdx +++ b/api_docs/kbn_core_analytics_browser_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-analytics-browser-internal title: "@kbn/core-analytics-browser-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-analytics-browser-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-analytics-browser-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_analytics_browser_mocks.mdx b/api_docs/kbn_core_analytics_browser_mocks.mdx index c3dea4bb4fec1..4af5fc170de17 100644 --- a/api_docs/kbn_core_analytics_browser_mocks.mdx +++ b/api_docs/kbn_core_analytics_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-analytics-browser-mocks title: "@kbn/core-analytics-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-analytics-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-analytics-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_analytics_server.mdx b/api_docs/kbn_core_analytics_server.mdx index f2f99d527dd31..223d8d5438765 100644 --- a/api_docs/kbn_core_analytics_server.mdx +++ b/api_docs/kbn_core_analytics_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-analytics-server title: "@kbn/core-analytics-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-analytics-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-analytics-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_analytics_server_internal.mdx b/api_docs/kbn_core_analytics_server_internal.mdx index e6e247e4970ab..6d37d452f045a 100644 --- a/api_docs/kbn_core_analytics_server_internal.mdx +++ b/api_docs/kbn_core_analytics_server_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-analytics-server-internal title: "@kbn/core-analytics-server-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-analytics-server-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-analytics-server-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_analytics_server_mocks.mdx b/api_docs/kbn_core_analytics_server_mocks.mdx index 92e3d24c1bedb..13dd7f8718c31 100644 --- a/api_docs/kbn_core_analytics_server_mocks.mdx +++ b/api_docs/kbn_core_analytics_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-analytics-server-mocks title: "@kbn/core-analytics-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-analytics-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-analytics-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_base_browser_mocks.mdx b/api_docs/kbn_core_base_browser_mocks.mdx index ad6288df80ee0..4b27a8e593b66 100644 --- a/api_docs/kbn_core_base_browser_mocks.mdx +++ b/api_docs/kbn_core_base_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-base-browser-mocks title: "@kbn/core-base-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-base-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-base-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_base_common.mdx b/api_docs/kbn_core_base_common.mdx index ba1e4abd15ae2..ad49df0e0fc86 100644 --- a/api_docs/kbn_core_base_common.mdx +++ b/api_docs/kbn_core_base_common.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-base-common title: "@kbn/core-base-common" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-base-common plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-base-common'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_base_server_internal.mdx b/api_docs/kbn_core_base_server_internal.mdx index c7d4e0c80c19e..d4548895b8138 100644 --- a/api_docs/kbn_core_base_server_internal.mdx +++ b/api_docs/kbn_core_base_server_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-base-server-internal title: "@kbn/core-base-server-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-base-server-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-base-server-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_base_server_mocks.mdx b/api_docs/kbn_core_base_server_mocks.mdx index d2b99c2f95faf..10746192e53dc 100644 --- a/api_docs/kbn_core_base_server_mocks.mdx +++ b/api_docs/kbn_core_base_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-base-server-mocks title: "@kbn/core-base-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-base-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-base-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_config_server_internal.mdx b/api_docs/kbn_core_config_server_internal.mdx index 9c7741208effb..db2484ca5660b 100644 --- a/api_docs/kbn_core_config_server_internal.mdx +++ b/api_docs/kbn_core_config_server_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-config-server-internal title: "@kbn/core-config-server-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-config-server-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-config-server-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_deprecations_browser.devdocs.json b/api_docs/kbn_core_deprecations_browser.devdocs.json new file mode 100644 index 0000000000000..76ea9b00bad48 --- /dev/null +++ b/api_docs/kbn_core_deprecations_browser.devdocs.json @@ -0,0 +1,189 @@ +{ + "id": "@kbn/core-deprecations-browser", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [ + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart", + "type": "Interface", + "tags": [], + "label": "DeprecationsServiceStart", + "description": [ + "\nDeprecationsService provides methods to fetch domain deprecation details from\nthe Kibana server.\n" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart.getAllDeprecations", + "type": "Function", + "tags": [], + "label": "getAllDeprecations", + "description": [ + "\nGrabs deprecations details for all domains." + ], + "signature": [ + "() => Promise<", + "DomainDeprecationDetails", + "[]>" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "children": [], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart.getDeprecations", + "type": "Function", + "tags": [], + "label": "getDeprecations", + "description": [ + "\nGrabs deprecations for a specific domain.\n" + ], + "signature": [ + "(domainId: string) => Promise<", + "DomainDeprecationDetails", + "[]>" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart.getDeprecations.$1", + "type": "string", + "tags": [], + "label": "domainId", + "description": [], + "signature": [ + "string" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart.isDeprecationResolvable", + "type": "Function", + "tags": [], + "label": "isDeprecationResolvable", + "description": [ + "\nReturns a boolean if the provided deprecation can be automatically resolvable.\n" + ], + "signature": [ + "(details: ", + "DomainDeprecationDetails", + ") => boolean" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart.isDeprecationResolvable.$1", + "type": "CompoundType", + "tags": [], + "label": "details", + "description": [], + "signature": [ + "DomainDeprecationDetails" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart.resolveDeprecation", + "type": "Function", + "tags": [], + "label": "resolveDeprecation", + "description": [ + "\nCalls the correctiveActions.api to automatically resolve the depprecation.\n" + ], + "signature": [ + "(details: ", + "DomainDeprecationDetails", + ") => Promise<", + { + "pluginId": "@kbn/core-deprecations-browser", + "scope": "common", + "docId": "kibKbnCoreDeprecationsBrowserPluginApi", + "section": "def-common.ResolveDeprecationResponse", + "text": "ResolveDeprecationResponse" + }, + ">" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.DeprecationsServiceStart.resolveDeprecation.$1", + "type": "CompoundType", + "tags": [], + "label": "details", + "description": [], + "signature": [ + "DomainDeprecationDetails" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/contracts.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + } + ], + "initialIsOpen": false + } + ], + "enums": [], + "misc": [ + { + "parentPluginId": "@kbn/core-deprecations-browser", + "id": "def-common.ResolveDeprecationResponse", + "type": "Type", + "tags": [], + "label": "ResolveDeprecationResponse", + "description": [ + "\nResponse from correctiveActions.api call from automatically resolving the deprecation" + ], + "signature": [ + "{ status: \"ok\"; } | { status: \"fail\"; reason: string; }" + ], + "path": "packages/core/deprecations/core-deprecations-browser/src/types.ts", + "deprecated": false, + "initialIsOpen": false + } + ], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_deprecations_browser.mdx b/api_docs/kbn_core_deprecations_browser.mdx new file mode 100644 index 0000000000000..8a09d18d10e2d --- /dev/null +++ b/api_docs/kbn_core_deprecations_browser.mdx @@ -0,0 +1,30 @@ +--- +id: kibKbnCoreDeprecationsBrowserPluginApi +slug: /kibana-dev-docs/api/kbn-core-deprecations-browser +title: "@kbn/core-deprecations-browser" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-deprecations-browser plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-deprecations-browser'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreDeprecationsBrowserObj from './kbn_core_deprecations_browser.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 9 | 0 | 3 | 0 | + +## Common + +### Interfaces + + +### Consts, variables and types + + diff --git a/api_docs/kbn_core_deprecations_browser_internal.devdocs.json b/api_docs/kbn_core_deprecations_browser_internal.devdocs.json new file mode 100644 index 0000000000000..3d549b7a15850 --- /dev/null +++ b/api_docs/kbn_core_deprecations_browser_internal.devdocs.json @@ -0,0 +1,129 @@ +{ + "id": "@kbn/core-deprecations-browser-internal", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "common": { + "classes": [ + { + "parentPluginId": "@kbn/core-deprecations-browser-internal", + "id": "def-common.DeprecationsService", + "type": "Class", + "tags": [], + "label": "DeprecationsService", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-deprecations-browser-internal", + "scope": "common", + "docId": "kibKbnCoreDeprecationsBrowserInternalPluginApi", + "section": "def-common.DeprecationsService", + "text": "DeprecationsService" + }, + " implements ", + "CoreService", + "" + ], + "path": "packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser-internal", + "id": "def-common.DeprecationsService.setup", + "type": "Function", + "tags": [], + "label": "setup", + "description": [], + "signature": [ + "() => void" + ], + "path": "packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts", + "deprecated": false, + "children": [], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-deprecations-browser-internal", + "id": "def-common.DeprecationsService.start", + "type": "Function", + "tags": [], + "label": "start", + "description": [], + "signature": [ + "({ http }: { http: ", + "HttpSetup", + "; }) => ", + "DeprecationsServiceStart" + ], + "path": "packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser-internal", + "id": "def-common.DeprecationsService.start.$1", + "type": "Object", + "tags": [], + "label": "{ http }", + "description": [], + "path": "packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser-internal", + "id": "def-common.DeprecationsService.start.$1.http", + "type": "Object", + "tags": [], + "label": "http", + "description": [], + "signature": [ + "HttpSetup" + ], + "path": "packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts", + "deprecated": false + } + ] + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-deprecations-browser-internal", + "id": "def-common.DeprecationsService.stop", + "type": "Function", + "tags": [], + "label": "stop", + "description": [], + "signature": [ + "() => void" + ], + "path": "packages/core/deprecations/core-deprecations-browser-internal/src/deprecations_service.ts", + "deprecated": false, + "children": [], + "returnComment": [] + } + ], + "initialIsOpen": false + } + ], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_deprecations_browser_internal.mdx b/api_docs/kbn_core_deprecations_browser_internal.mdx new file mode 100644 index 0000000000000..1ff6711cbba7e --- /dev/null +++ b/api_docs/kbn_core_deprecations_browser_internal.mdx @@ -0,0 +1,27 @@ +--- +id: kibKbnCoreDeprecationsBrowserInternalPluginApi +slug: /kibana-dev-docs/api/kbn-core-deprecations-browser-internal +title: "@kbn/core-deprecations-browser-internal" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-deprecations-browser-internal plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-deprecations-browser-internal'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreDeprecationsBrowserInternalObj from './kbn_core_deprecations_browser_internal.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 6 | 0 | 6 | 0 | + +## Common + +### Classes + + diff --git a/api_docs/kbn_core_deprecations_browser_mocks.devdocs.json b/api_docs/kbn_core_deprecations_browser_mocks.devdocs.json new file mode 100644 index 0000000000000..6a3c846f820ae --- /dev/null +++ b/api_docs/kbn_core_deprecations_browser_mocks.devdocs.json @@ -0,0 +1,92 @@ +{ + "id": "@kbn/core-deprecations-browser-mocks", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [ + { + "parentPluginId": "@kbn/core-deprecations-browser-mocks", + "id": "def-common.deprecationsServiceMock", + "type": "Object", + "tags": [], + "label": "deprecationsServiceMock", + "description": [], + "path": "packages/core/deprecations/core-deprecations-browser-mocks/src/deprecations_service.mock.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-browser-mocks", + "id": "def-common.deprecationsServiceMock.create", + "type": "Function", + "tags": [], + "label": "create", + "description": [], + "signature": [ + "() => jest.Mocked<", + "PublicMethodsOf", + "<", + "DeprecationsService", + ">>" + ], + "path": "packages/core/deprecations/core-deprecations-browser-mocks/src/deprecations_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-deprecations-browser-mocks", + "id": "def-common.deprecationsServiceMock.createSetupContract", + "type": "Function", + "tags": [], + "label": "createSetupContract", + "description": [], + "signature": [ + "() => undefined" + ], + "path": "packages/core/deprecations/core-deprecations-browser-mocks/src/deprecations_service.mock.ts", + "deprecated": false, + "children": [], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-deprecations-browser-mocks", + "id": "def-common.deprecationsServiceMock.createStartContract", + "type": "Function", + "tags": [], + "label": "createStartContract", + "description": [], + "signature": [ + "() => jest.Mocked<", + "DeprecationsServiceStart", + ">" + ], + "path": "packages/core/deprecations/core-deprecations-browser-mocks/src/deprecations_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + } + ], + "initialIsOpen": false + } + ] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_deprecations_browser_mocks.mdx b/api_docs/kbn_core_deprecations_browser_mocks.mdx new file mode 100644 index 0000000000000..f613c435d770d --- /dev/null +++ b/api_docs/kbn_core_deprecations_browser_mocks.mdx @@ -0,0 +1,27 @@ +--- +id: kibKbnCoreDeprecationsBrowserMocksPluginApi +slug: /kibana-dev-docs/api/kbn-core-deprecations-browser-mocks +title: "@kbn/core-deprecations-browser-mocks" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-deprecations-browser-mocks plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-deprecations-browser-mocks'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreDeprecationsBrowserMocksObj from './kbn_core_deprecations_browser_mocks.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 4 | 0 | 4 | 0 | + +## Common + +### Objects + + diff --git a/api_docs/kbn_core_deprecations_common.devdocs.json b/api_docs/kbn_core_deprecations_common.devdocs.json new file mode 100644 index 0000000000000..bdaa9bdad8fd6 --- /dev/null +++ b/api_docs/kbn_core_deprecations_common.devdocs.json @@ -0,0 +1,321 @@ +{ + "id": "@kbn/core-deprecations-common", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [ + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails", + "type": "Interface", + "tags": [], + "label": "BaseDeprecationDetails", + "description": [ + "\nBase properties shared by all types of deprecations\n" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails.title", + "type": "string", + "tags": [], + "label": "title", + "description": [ + "\nThe title of the deprecation.\nCheck the README for writing deprecations in `src/core/server/deprecations/README.mdx`" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails.message", + "type": "string", + "tags": [], + "label": "message", + "description": [ + "\nThe description message to be displayed for the deprecation.\nCheck the README for writing deprecations in `src/core/server/deprecations/README.mdx`" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails.level", + "type": "CompoundType", + "tags": [], + "label": "level", + "description": [ + "\nlevels:\n- warning: will not break deployment upon upgrade\n- critical: needs to be addressed before upgrade.\n- fetch_error: Deprecations service failed to grab the deprecation details for the domain." + ], + "signature": [ + "\"warning\" | \"critical\" | \"fetch_error\"" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails.deprecationType", + "type": "CompoundType", + "tags": [], + "label": "deprecationType", + "description": [ + "\n(optional) Used to identify between different deprecation types.\nExample use case: in Upgrade Assistant, we may want to allow the user to sort by\ndeprecation type or show each type in a separate tab.\n\nFeel free to add new types if necessary.\nPredefined types are necessary to reduce having similar definitions with different keywords\nacross kibana deprecations." + ], + "signature": [ + "\"config\" | \"feature\" | undefined" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails.documentationUrl", + "type": "string", + "tags": [], + "label": "documentationUrl", + "description": [ + "(optional) link to the documentation for more details on the deprecation." + ], + "signature": [ + "string | undefined" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails.requireRestart", + "type": "CompoundType", + "tags": [], + "label": "requireRestart", + "description": [ + "(optional) specify the fix for this deprecation requires a full kibana restart." + ], + "signature": [ + "boolean | undefined" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.BaseDeprecationDetails.correctiveActions", + "type": "Object", + "tags": [], + "label": "correctiveActions", + "description": [ + "corrective action needed to fix this deprecation." + ], + "signature": [ + "{ api?: { path: string; method: \"POST\" | \"PUT\"; body?: { [key: string]: any; } | undefined; omitContextFromBody?: boolean | undefined; } | undefined; manualSteps: string[]; }" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.ConfigDeprecationDetails", + "type": "Interface", + "tags": [], + "label": "ConfigDeprecationDetails", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.ConfigDeprecationDetails", + "text": "ConfigDeprecationDetails" + }, + " extends ", + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.BaseDeprecationDetails", + "text": "BaseDeprecationDetails" + } + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.ConfigDeprecationDetails.configPath", + "type": "string", + "tags": [], + "label": "configPath", + "description": [], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.ConfigDeprecationDetails.deprecationType", + "type": "string", + "tags": [], + "label": "deprecationType", + "description": [], + "signature": [ + "\"config\"" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.DeprecationsGetResponse", + "type": "Interface", + "tags": [], + "label": "DeprecationsGetResponse", + "description": [], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.DeprecationsGetResponse.deprecations", + "type": "Array", + "tags": [], + "label": "deprecations", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.DomainDeprecationDetails", + "text": "DomainDeprecationDetails" + }, + "[]" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.FeatureDeprecationDetails", + "type": "Interface", + "tags": [], + "label": "FeatureDeprecationDetails", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.FeatureDeprecationDetails", + "text": "FeatureDeprecationDetails" + }, + " extends ", + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.BaseDeprecationDetails", + "text": "BaseDeprecationDetails" + } + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.FeatureDeprecationDetails.deprecationType", + "type": "string", + "tags": [], + "label": "deprecationType", + "description": [], + "signature": [ + "\"feature\" | undefined" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false + } + ], + "initialIsOpen": false + } + ], + "enums": [], + "misc": [ + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.DeprecationsDetails", + "type": "Type", + "tags": [], + "label": "DeprecationsDetails", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.ConfigDeprecationDetails", + "text": "ConfigDeprecationDetails" + }, + " | ", + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.FeatureDeprecationDetails", + "text": "FeatureDeprecationDetails" + } + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false, + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-deprecations-common", + "id": "def-common.DomainDeprecationDetails", + "type": "Type", + "tags": [], + "label": "DomainDeprecationDetails", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-deprecations-common", + "scope": "common", + "docId": "kibKbnCoreDeprecationsCommonPluginApi", + "section": "def-common.DeprecationsDetails", + "text": "DeprecationsDetails" + }, + " & { domainId: string; }" + ], + "path": "packages/core/deprecations/core-deprecations-common/src/types.ts", + "deprecated": false, + "initialIsOpen": false + } + ], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_deprecations_common.mdx b/api_docs/kbn_core_deprecations_common.mdx new file mode 100644 index 0000000000000..1655e5ace5d75 --- /dev/null +++ b/api_docs/kbn_core_deprecations_common.mdx @@ -0,0 +1,30 @@ +--- +id: kibKbnCoreDeprecationsCommonPluginApi +slug: /kibana-dev-docs/api/kbn-core-deprecations-common +title: "@kbn/core-deprecations-common" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-deprecations-common plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-deprecations-common'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreDeprecationsCommonObj from './kbn_core_deprecations_common.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 17 | 0 | 9 | 0 | + +## Common + +### Interfaces + + +### Consts, variables and types + + diff --git a/api_docs/kbn_core_doc_links_browser.mdx b/api_docs/kbn_core_doc_links_browser.mdx index 1a969e948111d..0d3d4b782a6e6 100644 --- a/api_docs/kbn_core_doc_links_browser.mdx +++ b/api_docs/kbn_core_doc_links_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-doc-links-browser title: "@kbn/core-doc-links-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-doc-links-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-doc-links-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_doc_links_browser_mocks.mdx b/api_docs/kbn_core_doc_links_browser_mocks.mdx index cd9441faafeae..3db9ce527e743 100644 --- a/api_docs/kbn_core_doc_links_browser_mocks.mdx +++ b/api_docs/kbn_core_doc_links_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-doc-links-browser-mocks title: "@kbn/core-doc-links-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-doc-links-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-doc-links-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_doc_links_server.mdx b/api_docs/kbn_core_doc_links_server.mdx index e960e0a78e180..b8bf4362d80e1 100644 --- a/api_docs/kbn_core_doc_links_server.mdx +++ b/api_docs/kbn_core_doc_links_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-doc-links-server title: "@kbn/core-doc-links-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-doc-links-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-doc-links-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_doc_links_server_mocks.mdx b/api_docs/kbn_core_doc_links_server_mocks.mdx index 6fcdb8e176c21..e02f196c84624 100644 --- a/api_docs/kbn_core_doc_links_server_mocks.mdx +++ b/api_docs/kbn_core_doc_links_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-doc-links-server-mocks title: "@kbn/core-doc-links-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-doc-links-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-doc-links-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_environment_server_internal.mdx b/api_docs/kbn_core_environment_server_internal.mdx index 51a204698e524..8e9ab43eac32f 100644 --- a/api_docs/kbn_core_environment_server_internal.mdx +++ b/api_docs/kbn_core_environment_server_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-environment-server-internal title: "@kbn/core-environment-server-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-environment-server-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-environment-server-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_environment_server_mocks.mdx b/api_docs/kbn_core_environment_server_mocks.mdx index d430edc47a08a..d7206b6566221 100644 --- a/api_docs/kbn_core_environment_server_mocks.mdx +++ b/api_docs/kbn_core_environment_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-environment-server-mocks title: "@kbn/core-environment-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-environment-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-environment-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_execution_context_browser.mdx b/api_docs/kbn_core_execution_context_browser.mdx index 83698a759bb1b..935c7d10bb4e4 100644 --- a/api_docs/kbn_core_execution_context_browser.mdx +++ b/api_docs/kbn_core_execution_context_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-execution-context-browser title: "@kbn/core-execution-context-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-execution-context-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-execution-context-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_execution_context_browser_internal.mdx b/api_docs/kbn_core_execution_context_browser_internal.mdx index ea919a39c9a6d..e9d8b97b72bd4 100644 --- a/api_docs/kbn_core_execution_context_browser_internal.mdx +++ b/api_docs/kbn_core_execution_context_browser_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-execution-context-browser-internal title: "@kbn/core-execution-context-browser-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-execution-context-browser-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-execution-context-browser-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_execution_context_browser_mocks.mdx b/api_docs/kbn_core_execution_context_browser_mocks.mdx index 05abf8327f857..ceebcf02bb548 100644 --- a/api_docs/kbn_core_execution_context_browser_mocks.mdx +++ b/api_docs/kbn_core_execution_context_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-execution-context-browser-mocks title: "@kbn/core-execution-context-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-execution-context-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-execution-context-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_execution_context_common.mdx b/api_docs/kbn_core_execution_context_common.mdx index 959a2dbc027ba..174ba7a2883ba 100644 --- a/api_docs/kbn_core_execution_context_common.mdx +++ b/api_docs/kbn_core_execution_context_common.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-execution-context-common title: "@kbn/core-execution-context-common" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-execution-context-common plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-execution-context-common'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_execution_context_server.mdx b/api_docs/kbn_core_execution_context_server.mdx index a88ed431d022f..1f3b85bc43bd5 100644 --- a/api_docs/kbn_core_execution_context_server.mdx +++ b/api_docs/kbn_core_execution_context_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-execution-context-server title: "@kbn/core-execution-context-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-execution-context-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-execution-context-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_execution_context_server_internal.mdx b/api_docs/kbn_core_execution_context_server_internal.mdx index 22d3cdf2819ec..a2ac783457fdf 100644 --- a/api_docs/kbn_core_execution_context_server_internal.mdx +++ b/api_docs/kbn_core_execution_context_server_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-execution-context-server-internal title: "@kbn/core-execution-context-server-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-execution-context-server-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-execution-context-server-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_execution_context_server_mocks.mdx b/api_docs/kbn_core_execution_context_server_mocks.mdx index 368b325e127a5..9f49fcec212b6 100644 --- a/api_docs/kbn_core_execution_context_server_mocks.mdx +++ b/api_docs/kbn_core_execution_context_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-execution-context-server-mocks title: "@kbn/core-execution-context-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-execution-context-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-execution-context-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_fatal_errors_browser.mdx b/api_docs/kbn_core_fatal_errors_browser.mdx index a7b2329ec2369..1d7ad995b0c82 100644 --- a/api_docs/kbn_core_fatal_errors_browser.mdx +++ b/api_docs/kbn_core_fatal_errors_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-fatal-errors-browser title: "@kbn/core-fatal-errors-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-fatal-errors-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-fatal-errors-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_fatal_errors_browser_mocks.mdx b/api_docs/kbn_core_fatal_errors_browser_mocks.mdx index bfea5fb0095d6..6b7c0d2ddcf77 100644 --- a/api_docs/kbn_core_fatal_errors_browser_mocks.mdx +++ b/api_docs/kbn_core_fatal_errors_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-fatal-errors-browser-mocks title: "@kbn/core-fatal-errors-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-fatal-errors-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-fatal-errors-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_http_browser.mdx b/api_docs/kbn_core_http_browser.mdx index 742d0816a7548..61a5977759133 100644 --- a/api_docs/kbn_core_http_browser.mdx +++ b/api_docs/kbn_core_http_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-http-browser title: "@kbn/core-http-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-http-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_http_browser_internal.mdx b/api_docs/kbn_core_http_browser_internal.mdx index c6859f2ef93e6..9c8c687cdb714 100644 --- a/api_docs/kbn_core_http_browser_internal.mdx +++ b/api_docs/kbn_core_http_browser_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-http-browser-internal title: "@kbn/core-http-browser-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-http-browser-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-browser-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_http_browser_mocks.mdx b/api_docs/kbn_core_http_browser_mocks.mdx index df680225c6251..12d2c6fbf3df9 100644 --- a/api_docs/kbn_core_http_browser_mocks.mdx +++ b/api_docs/kbn_core_http_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-http-browser-mocks title: "@kbn/core-http-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-http-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_http_common.mdx b/api_docs/kbn_core_http_common.mdx index 97ec4742c8089..5976a476a2c79 100644 --- a/api_docs/kbn_core_http_common.mdx +++ b/api_docs/kbn_core_http_common.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-http-common title: "@kbn/core-http-common" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-http-common plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-common'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_http_context_server_mocks.devdocs.json b/api_docs/kbn_core_http_context_server_mocks.devdocs.json new file mode 100644 index 0000000000000..2c77ba329d06d --- /dev/null +++ b/api_docs/kbn_core_http_context_server_mocks.devdocs.json @@ -0,0 +1,201 @@ +{ + "id": "@kbn/core-http-context-server-mocks", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [ + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.ContextContainerMock", + "type": "Type", + "tags": [], + "label": "ContextContainerMock", + "description": [], + "signature": [ + "{ registerContext: jest.MockInstance<", + "IContextContainer", + ", [pluginOpaqueId: symbol, contextName: \"resolve\", provider: ", + "IContextProvider", + "<", + "RequestHandlerContextBase", + ", \"resolve\">]>; createHandler: jest.MockInstance<(request: ", + "KibanaRequest", + ", response: ", + "KibanaResponseFactory", + ") => Promise<", + "IKibanaResponse", + ">, [pluginOpaqueId: symbol, handler: ", + "RequestHandler", + "]>; } & ", + "IContextContainer" + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_container.mock.ts", + "deprecated": false, + "initialIsOpen": false + } + ], + "objects": [ + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextMock", + "type": "Object", + "tags": [], + "label": "contextMock", + "description": [], + "path": "packages/core/http/core-http-context-server-mocks/src/context_container.mock.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextMock.create", + "type": "Function", + "tags": [], + "label": "create", + "description": [], + "signature": [ + "(mockContext?: any) => ", + { + "pluginId": "@kbn/core-http-context-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpContextServerMocksPluginApi", + "section": "def-server.ContextContainerMock", + "text": "ContextContainerMock" + } + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_container.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextMock.create.$1", + "type": "Any", + "tags": [], + "label": "mockContext", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_container.mock.ts", + "deprecated": false + } + ] + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextServiceMock", + "type": "Object", + "tags": [], + "label": "contextServiceMock", + "description": [], + "path": "packages/core/http/core-http-context-server-mocks/src/context_service.mock.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextServiceMock.create", + "type": "Function", + "tags": [], + "label": "create", + "description": [], + "signature": [ + "() => jest.Mocked" + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextServiceMock.createPrebootContract", + "type": "Function", + "tags": [], + "label": "createPrebootContract", + "description": [], + "signature": [ + "(mockContext?: {}) => jest.Mocked<", + "InternalContextSetup", + ">" + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextServiceMock.createPrebootContract.$1", + "type": "Object", + "tags": [], + "label": "mockContext", + "description": [], + "signature": [ + "{}" + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_service.mock.ts", + "deprecated": false + } + ] + }, + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextServiceMock.createSetupContract", + "type": "Function", + "tags": [], + "label": "createSetupContract", + "description": [], + "signature": [ + "(mockContext?: {}) => jest.Mocked<", + "InternalContextSetup", + ">" + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-context-server-mocks", + "id": "def-server.contextServiceMock.createSetupContract.$1", + "type": "Object", + "tags": [], + "label": "mockContext", + "description": [], + "signature": [ + "{}" + ], + "path": "packages/core/http/core-http-context-server-mocks/src/context_service.mock.ts", + "deprecated": false + } + ] + } + ], + "initialIsOpen": false + } + ] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_http_context_server_mocks.mdx b/api_docs/kbn_core_http_context_server_mocks.mdx new file mode 100644 index 0000000000000..b6a5c32870cfc --- /dev/null +++ b/api_docs/kbn_core_http_context_server_mocks.mdx @@ -0,0 +1,30 @@ +--- +id: kibKbnCoreHttpContextServerMocksPluginApi +slug: /kibana-dev-docs/api/kbn-core-http-context-server-mocks +title: "@kbn/core-http-context-server-mocks" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-http-context-server-mocks plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-context-server-mocks'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreHttpContextServerMocksObj from './kbn_core_http_context_server_mocks.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 10 | 1 | 10 | 0 | + +## Server + +### Objects + + +### Consts, variables and types + + diff --git a/api_docs/kbn_core_http_router_server_internal.devdocs.json b/api_docs/kbn_core_http_router_server_internal.devdocs.json new file mode 100644 index 0000000000000..444c019edeea9 --- /dev/null +++ b/api_docs/kbn_core_http_router_server_internal.devdocs.json @@ -0,0 +1,414 @@ +{ + "id": "@kbn/core-http-router-server-internal", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter", + "type": "Class", + "tags": [], + "label": "HapiResponseAdapter", + "description": [], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter.Unnamed", + "type": "Function", + "tags": [], + "label": "Constructor", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter.Unnamed.$1", + "type": "Object", + "tags": [], + "label": "responseToolkit", + "description": [], + "signature": [ + "ResponseToolkit" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter.toBadRequest", + "type": "Function", + "tags": [], + "label": "toBadRequest", + "description": [], + "signature": [ + "(message: string) => ", + "Boom", + "" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter.toBadRequest.$1", + "type": "string", + "tags": [], + "label": "message", + "description": [], + "signature": [ + "string" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter.toInternalError", + "type": "Function", + "tags": [], + "label": "toInternalError", + "description": [], + "signature": [ + "() => ", + "Boom", + "" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "children": [], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter.handle", + "type": "Function", + "tags": [], + "label": "handle", + "description": [], + "signature": [ + "(kibanaResponse: ", + "KibanaResponse", + ") => ", + "Boom", + " | ", + "ResponseObject" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.HapiResponseAdapter.handle.$1", + "type": "Object", + "tags": [], + "label": "kibanaResponse", + "description": [], + "signature": [ + "KibanaResponse", + "" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response_adapter.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + } + ], + "initialIsOpen": false + } + ], + "functions": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.filterHeaders", + "type": "Function", + "tags": [], + "label": "filterHeaders", + "description": [], + "signature": [ + "(headers: ", + "Headers", + ", fieldsToKeep: string[], fieldsToExclude: string[]) => ", + "Headers" + ], + "path": "packages/core/http/core-http-router-server-internal/src/headers.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.filterHeaders.$1", + "type": "CompoundType", + "tags": [], + "label": "headers", + "description": [], + "signature": [ + "Headers" + ], + "path": "packages/core/http/core-http-router-server-internal/src/headers.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.filterHeaders.$2", + "type": "Array", + "tags": [], + "label": "fieldsToKeep", + "description": [], + "signature": [ + "string[]" + ], + "path": "packages/core/http/core-http-router-server-internal/src/headers.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.filterHeaders.$3", + "type": "Array", + "tags": [], + "label": "fieldsToExclude", + "description": [], + "signature": [ + "string[]" + ], + "path": "packages/core/http/core-http-router-server-internal/src/headers.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.isKibanaResponse", + "type": "Function", + "tags": [], + "label": "isKibanaResponse", + "description": [], + "signature": [ + "(response: Record) => boolean" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.isKibanaResponse.$1", + "type": "Object", + "tags": [], + "label": "response", + "description": [], + "signature": [ + "Record" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.isSafeMethod", + "type": "Function", + "tags": [], + "label": "isSafeMethod", + "description": [], + "signature": [ + "(method: ", + "RouteMethod", + ") => boolean" + ], + "path": "packages/core/http/core-http-router-server-internal/src/route.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.isSafeMethod.$1", + "type": "CompoundType", + "tags": [], + "label": "method", + "description": [], + "signature": [ + "RouteMethod" + ], + "path": "packages/core/http/core-http-router-server-internal/src/route.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [], + "initialIsOpen": false + } + ], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.kibanaResponseFactory", + "type": "Object", + "tags": [], + "label": "kibanaResponseFactory", + "description": [], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.kibanaResponseFactory.Unnamed", + "type": "Any", + "tags": [], + "label": "Unnamed", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.kibanaResponseFactory.Unnamed", + "type": "Any", + "tags": [], + "label": "Unnamed", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.kibanaResponseFactory.Unnamed", + "type": "Any", + "tags": [], + "label": "Unnamed", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.kibanaResponseFactory.custom", + "type": "Function", + "tags": [], + "label": "custom", + "description": [], + "signature": [ + " | Error | ", + "Stream", + " | Buffer | { message: string | Error; attributes?: ", + "ResponseErrorAttributes", + " | undefined; } | undefined>(options: ", + "CustomHttpResponseOptions", + ") => ", + "KibanaResponse", + "" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.kibanaResponseFactory.custom.$1", + "type": "Object", + "tags": [], + "label": "options", + "description": [], + "signature": [ + "CustomHttpResponseOptions", + "" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.lifecycleResponseFactory", + "type": "Object", + "tags": [], + "label": "lifecycleResponseFactory", + "description": [], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.lifecycleResponseFactory.Unnamed", + "type": "Any", + "tags": [], + "label": "Unnamed", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-router-server-internal", + "id": "def-server.lifecycleResponseFactory.Unnamed", + "type": "Any", + "tags": [], + "label": "Unnamed", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-router-server-internal/src/response.ts", + "deprecated": false + } + ], + "initialIsOpen": false + } + ] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_http_router_server_internal.mdx b/api_docs/kbn_core_http_router_server_internal.mdx new file mode 100644 index 0000000000000..dfe9ea97fb622 --- /dev/null +++ b/api_docs/kbn_core_http_router_server_internal.mdx @@ -0,0 +1,33 @@ +--- +id: kibKbnCoreHttpRouterServerInternalPluginApi +slug: /kibana-dev-docs/api/kbn-core-http-router-server-internal +title: "@kbn/core-http-router-server-internal" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-http-router-server-internal plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-router-server-internal'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreHttpRouterServerInternalObj from './kbn_core_http_router_server_internal.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 25 | 5 | 25 | 1 | + +## Server + +### Objects + + +### Functions + + +### Classes + + diff --git a/api_docs/kbn_core_http_router_server_mocks.devdocs.json b/api_docs/kbn_core_http_router_server_mocks.devdocs.json new file mode 100644 index 0000000000000..90fbdecc75145 --- /dev/null +++ b/api_docs/kbn_core_http_router_server_mocks.devdocs.json @@ -0,0 +1,193 @@ +{ + "id": "@kbn/core-http-router-server-mocks", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [ + { + "parentPluginId": "@kbn/core-http-router-server-mocks", + "id": "def-server.RouterMock", + "type": "Type", + "tags": [], + "label": "RouterMock", + "description": [], + "signature": [ + "{ routerPath: string; get: jest.MockInstance, handler: ", + "RequestHandler", + "]>; post: jest.MockInstance, handler: ", + "RequestHandler", + "]>; put: jest.MockInstance, handler: ", + "RequestHandler", + "]>; patch: jest.MockInstance, handler: ", + "RequestHandler", + "]>; delete: jest.MockInstance, handler: ", + "RequestHandler", + "]>; handleLegacyErrors: jest.MockInstance<", + "RequestHandler", + ", [handler: ", + "RequestHandler", + "]>; getRoutes: jest.MockInstance<", + "RouterRoute", + "[], []>; } & ", + "IRouter", + "" + ], + "path": "packages/core/http/core-http-router-server-mocks/src/router.mock.ts", + "deprecated": false, + "initialIsOpen": false + } + ], + "objects": [ + { + "parentPluginId": "@kbn/core-http-router-server-mocks", + "id": "def-server.mockRouter", + "type": "Object", + "tags": [], + "label": "mockRouter", + "description": [], + "path": "packages/core/http/core-http-router-server-mocks/src/router.mock.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-mocks", + "id": "def-server.mockRouter.create", + "type": "Function", + "tags": [], + "label": "create", + "description": [], + "signature": [ + "({ routerPath }?: { routerPath?: string | undefined; }) => ", + { + "pluginId": "@kbn/core-http-router-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpRouterServerMocksPluginApi", + "section": "def-server.RouterMock", + "text": "RouterMock" + } + ], + "path": "packages/core/http/core-http-router-server-mocks/src/router.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-mocks", + "id": "def-server.mockRouter.create.$1", + "type": "Object", + "tags": [], + "label": "__0", + "description": [], + "signature": [ + "{ routerPath?: string | undefined; }" + ], + "path": "packages/core/http/core-http-router-server-mocks/src/router.mock.ts", + "deprecated": false + } + ] + }, + { + "parentPluginId": "@kbn/core-http-router-server-mocks", + "id": "def-server.mockRouter.createKibanaRequest", + "type": "Function", + "tags": [], + "label": "createKibanaRequest", + "description": [], + "signature": [ + "

({ path, headers, params, body, query, method, socket, routeTags, routeAuthRequired, validation, kibanaRouteOptions, kibanaRequestState, auth, }?: ", + "RequestFixtureOptions", + ") => ", + "KibanaRequest", + "" + ], + "path": "packages/core/http/core-http-router-server-mocks/src/router.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-router-server-mocks", + "id": "def-server.mockRouter.createKibanaRequest.$1", + "type": "Object", + "tags": [], + "label": "__0", + "description": [], + "signature": [ + "RequestFixtureOptions", + "" + ], + "path": "packages/core/http/core-http-router-server-mocks/src/router.mock.ts", + "deprecated": false + } + ] + }, + { + "parentPluginId": "@kbn/core-http-router-server-mocks", + "id": "def-server.mockRouter.createResponseFactory", + "type": "Function", + "tags": [], + "label": "createResponseFactory", + "description": [], + "signature": [ + "() => jest.Mocked<", + "KibanaResponseFactory", + ">" + ], + "path": "packages/core/http/core-http-router-server-mocks/src/router.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + } + ], + "initialIsOpen": false + } + ] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_http_router_server_mocks.mdx b/api_docs/kbn_core_http_router_server_mocks.mdx new file mode 100644 index 0000000000000..f0957357d4c7f --- /dev/null +++ b/api_docs/kbn_core_http_router_server_mocks.mdx @@ -0,0 +1,30 @@ +--- +id: kibKbnCoreHttpRouterServerMocksPluginApi +slug: /kibana-dev-docs/api/kbn-core-http-router-server-mocks +title: "@kbn/core-http-router-server-mocks" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-http-router-server-mocks plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-router-server-mocks'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreHttpRouterServerMocksObj from './kbn_core_http_router_server_mocks.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 7 | 0 | 7 | 1 | + +## Server + +### Objects + + +### Consts, variables and types + + diff --git a/api_docs/kbn_core_http_server.mdx b/api_docs/kbn_core_http_server.mdx index 80871a81a9d25..495e16540ff99 100644 --- a/api_docs/kbn_core_http_server.mdx +++ b/api_docs/kbn_core_http_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-http-server title: "@kbn/core-http-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-http-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_http_server_internal.devdocs.json b/api_docs/kbn_core_http_server_internal.devdocs.json new file mode 100644 index 0000000000000..b0c482d9afc03 --- /dev/null +++ b/api_docs/kbn_core_http_server_internal.devdocs.json @@ -0,0 +1,845 @@ +{ + "id": "@kbn/core-http-server-internal", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.CspConfig", + "type": "Class", + "tags": [], + "label": "CspConfig", + "description": [ + "\nCSP configuration for use in Kibana." + ], + "signature": [ + { + "pluginId": "@kbn/core-http-server-internal", + "scope": "server", + "docId": "kibKbnCoreHttpServerInternalPluginApi", + "section": "def-server.CspConfig", + "text": "CspConfig" + }, + " implements ", + "ICspConfig" + ], + "path": "packages/core/http/core-http-server-internal/src/csp/csp_config.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.CspConfig.DEFAULT", + "type": "Object", + "tags": [], + "label": "DEFAULT", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-http-server-internal", + "scope": "server", + "docId": "kibKbnCoreHttpServerInternalPluginApi", + "section": "def-server.CspConfig", + "text": "CspConfig" + } + ], + "path": "packages/core/http/core-http-server-internal/src/csp/csp_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.CspConfig.directives", + "type": "Object", + "tags": [], + "label": "#directives", + "description": [], + "signature": [ + "CspDirectives" + ], + "path": "packages/core/http/core-http-server-internal/src/csp/csp_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.CspConfig.strict", + "type": "boolean", + "tags": [], + "label": "strict", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/csp/csp_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.CspConfig.warnLegacyBrowsers", + "type": "boolean", + "tags": [], + "label": "warnLegacyBrowsers", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/csp/csp_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.CspConfig.disableEmbedding", + "type": "boolean", + "tags": [], + "label": "disableEmbedding", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/csp/csp_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.CspConfig.header", + "type": "string", + "tags": [], + "label": "header", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/csp/csp_config.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.ExternalUrlConfig", + "type": "Class", + "tags": [], + "label": "ExternalUrlConfig", + "description": [ + "\nExternal Url configuration for use in Kibana." + ], + "signature": [ + { + "pluginId": "@kbn/core-http-server-internal", + "scope": "server", + "docId": "kibKbnCoreHttpServerInternalPluginApi", + "section": "def-server.ExternalUrlConfig", + "text": "ExternalUrlConfig" + }, + " implements ", + "IExternalUrlConfig" + ], + "path": "packages/core/http/core-http-server-internal/src/external_url/external_url_config.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.ExternalUrlConfig.DEFAULT", + "type": "Object", + "tags": [], + "label": "DEFAULT", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-http-server-internal", + "scope": "server", + "docId": "kibKbnCoreHttpServerInternalPluginApi", + "section": "def-server.ExternalUrlConfig", + "text": "ExternalUrlConfig" + } + ], + "path": "packages/core/http/core-http-server-internal/src/external_url/external_url_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.ExternalUrlConfig.policy", + "type": "Array", + "tags": [], + "label": "policy", + "description": [], + "signature": [ + "IExternalUrlPolicy", + "[]" + ], + "path": "packages/core/http/core-http-server-internal/src/external_url/external_url_config.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig", + "type": "Class", + "tags": [], + "label": "HttpConfig", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-http-server-internal", + "scope": "server", + "docId": "kibKbnCoreHttpServerInternalPluginApi", + "section": "def-server.HttpConfig", + "text": "HttpConfig" + }, + " implements ", + "IHttpConfig" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.name", + "type": "string", + "tags": [], + "label": "name", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.autoListen", + "type": "boolean", + "tags": [], + "label": "autoListen", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.host", + "type": "string", + "tags": [], + "label": "host", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.keepaliveTimeout", + "type": "number", + "tags": [], + "label": "keepaliveTimeout", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.socketTimeout", + "type": "number", + "tags": [], + "label": "socketTimeout", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.port", + "type": "number", + "tags": [], + "label": "port", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.cors", + "type": "Object", + "tags": [], + "label": "cors", + "description": [], + "signature": [ + "{ enabled: boolean; allowCredentials: boolean; allowOrigin: string[]; }" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.securityResponseHeaders", + "type": "Object", + "tags": [], + "label": "securityResponseHeaders", + "description": [], + "signature": [ + "{ [x: string]: string | string[]; }" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.customResponseHeaders", + "type": "Object", + "tags": [], + "label": "customResponseHeaders", + "description": [], + "signature": [ + "{ [x: string]: string | string[]; }" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.maxPayload", + "type": "Object", + "tags": [], + "label": "maxPayload", + "description": [], + "signature": [ + "ByteSizeValue" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.basePath", + "type": "string", + "tags": [], + "label": "basePath", + "description": [], + "signature": [ + "string | undefined" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.publicBaseUrl", + "type": "string", + "tags": [], + "label": "publicBaseUrl", + "description": [], + "signature": [ + "string | undefined" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.rewriteBasePath", + "type": "boolean", + "tags": [], + "label": "rewriteBasePath", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.ssl", + "type": "Object", + "tags": [], + "label": "ssl", + "description": [], + "signature": [ + "SslConfig" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.compression", + "type": "Object", + "tags": [], + "label": "compression", + "description": [], + "signature": [ + "{ enabled: boolean; referrerWhitelist?: string[] | undefined; }" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.csp", + "type": "Object", + "tags": [], + "label": "csp", + "description": [], + "signature": [ + "ICspConfig" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.externalUrl", + "type": "Object", + "tags": [], + "label": "externalUrl", + "description": [], + "signature": [ + "IExternalUrlConfig" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.xsrf", + "type": "Object", + "tags": [], + "label": "xsrf", + "description": [], + "signature": [ + "{ disableProtection: boolean; allowlist: string[]; }" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.requestId", + "type": "Object", + "tags": [], + "label": "requestId", + "description": [], + "signature": [ + "{ allowFromAnyIp: boolean; ipAllowlist: string[]; }" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfig.shutdownTimeout", + "type": "Object", + "tags": [], + "label": "shutdownTimeout", + "description": [], + "signature": [ + "moment.Duration" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer", + "type": "Class", + "tags": [], + "label": "HttpServer", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.Unnamed", + "type": "Function", + "tags": [], + "label": "Constructor", + "description": [], + "signature": [ + "any" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.Unnamed.$1", + "type": "Object", + "tags": [], + "label": "logger", + "description": [], + "signature": [ + "LoggerFactory" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.Unnamed.$2", + "type": "string", + "tags": [], + "label": "name", + "description": [], + "signature": [ + "string" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.Unnamed.$3", + "type": "Object", + "tags": [], + "label": "shutdownTimeout$", + "description": [], + "signature": [ + "Observable", + "" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.isListening", + "type": "Function", + "tags": [], + "label": "isListening", + "description": [], + "signature": [ + "() => boolean" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "children": [], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.setup", + "type": "Function", + "tags": [], + "label": "setup", + "description": [], + "signature": [ + "(config: ", + { + "pluginId": "@kbn/core-http-server-internal", + "scope": "server", + "docId": "kibKbnCoreHttpServerInternalPluginApi", + "section": "def-server.HttpConfig", + "text": "HttpConfig" + }, + ", executionContext?: ", + "IExecutionContext", + " | undefined) => Promise<", + "HttpServerSetup", + ">" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.setup.$1", + "type": "Object", + "tags": [], + "label": "config", + "description": [], + "signature": [ + { + "pluginId": "@kbn/core-http-server-internal", + "scope": "server", + "docId": "kibKbnCoreHttpServerInternalPluginApi", + "section": "def-server.HttpConfig", + "text": "HttpConfig" + } + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.setup.$2", + "type": "Object", + "tags": [], + "label": "executionContext", + "description": [], + "signature": [ + "IExecutionContext", + " | undefined" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "isRequired": false + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.start", + "type": "Function", + "tags": [], + "label": "start", + "description": [], + "signature": [ + "() => Promise" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "children": [], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpServer.stop", + "type": "Function", + "tags": [], + "label": "stop", + "description": [], + "signature": [ + "() => Promise" + ], + "path": "packages/core/http/core-http-server-internal/src/http_server.ts", + "deprecated": false, + "children": [], + "returnComment": [] + } + ], + "initialIsOpen": false + } + ], + "functions": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.createCookieSessionStorageFactory", + "type": "Function", + "tags": [], + "label": "createCookieSessionStorageFactory", + "description": [ + "\nCreates SessionStorage factory, which abstract the way of\nsession storage implementation and scoping to the incoming requests.\n" + ], + "signature": [ + "(log: ", + "Logger", + ", server: ", + "Server", + ", cookieOptions: ", + "SessionStorageCookieOptions", + ", basePath: string | undefined) => Promise<", + "SessionStorageFactory", + ">" + ], + "path": "packages/core/http/core-http-server-internal/src/cookie_session_storage.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.createCookieSessionStorageFactory.$1", + "type": "Object", + "tags": [], + "label": "log", + "description": [], + "signature": [ + "Logger" + ], + "path": "packages/core/http/core-http-server-internal/src/cookie_session_storage.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.createCookieSessionStorageFactory.$2", + "type": "Object", + "tags": [], + "label": "server", + "description": [ + "- hapi server to create SessionStorage for" + ], + "signature": [ + "Server" + ], + "path": "packages/core/http/core-http-server-internal/src/cookie_session_storage.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.createCookieSessionStorageFactory.$3", + "type": "Object", + "tags": [], + "label": "cookieOptions", + "description": [ + "- cookies configuration" + ], + "signature": [ + "SessionStorageCookieOptions", + "" + ], + "path": "packages/core/http/core-http-server-internal/src/cookie_session_storage.ts", + "deprecated": false, + "isRequired": true + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.createCookieSessionStorageFactory.$4", + "type": "string", + "tags": [], + "label": "basePath", + "description": [], + "signature": [ + "string | undefined" + ], + "path": "packages/core/http/core-http-server-internal/src/cookie_session_storage.ts", + "deprecated": false, + "isRequired": false + } + ], + "returnComment": [], + "initialIsOpen": false + } + ], + "interfaces": [], + "enums": [], + "misc": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.HttpConfigType", + "type": "Type", + "tags": [], + "label": "HttpConfigType", + "description": [], + "signature": [ + "{ readonly basePath?: string | undefined; readonly uuid?: string | undefined; readonly publicBaseUrl?: string | undefined; readonly name: string; readonly ssl: Readonly<{ key?: string | undefined; certificateAuthorities?: string | string[] | undefined; certificate?: string | undefined; keyPassphrase?: string | undefined; redirectHttpFromPort?: number | undefined; } & { enabled: boolean; keystore: Readonly<{ path?: string | undefined; password?: string | undefined; } & {}>; truststore: Readonly<{ path?: string | undefined; password?: string | undefined; } & {}>; cipherSuites: string[]; supportedProtocols: string[]; clientAuthentication: \"none\" | \"required\" | \"optional\"; }>; readonly host: string; readonly port: number; readonly compression: Readonly<{ referrerWhitelist?: string[] | undefined; } & { enabled: boolean; }>; readonly cors: Readonly<{} & { enabled: boolean; allowCredentials: boolean; allowOrigin: string[] | \"*\"[]; }>; readonly autoListen: boolean; readonly shutdownTimeout: moment.Duration; readonly securityResponseHeaders: Readonly<{} & { referrerPolicy: \"origin\" | \"no-referrer\" | \"no-referrer-when-downgrade\" | \"origin-when-cross-origin\" | \"same-origin\" | \"strict-origin\" | \"strict-origin-when-cross-origin\" | \"unsafe-url\" | null; disableEmbedding: boolean; strictTransportSecurity: string | null; xContentTypeOptions: \"nosniff\" | null; permissionsPolicy: string | null; }>; readonly customResponseHeaders: Record; readonly maxPayload: ", + "ByteSizeValue", + "; readonly rewriteBasePath: boolean; readonly keepaliveTimeout: number; readonly socketTimeout: number; readonly xsrf: Readonly<{} & { disableProtection: boolean; allowlist: string[]; }>; readonly requestId: Readonly<{} & { allowFromAnyIp: boolean; ipAllowlist: string[]; }>; }" + ], + "path": "packages/core/http/core-http-server-internal/src/http_config.ts", + "deprecated": false, + "initialIsOpen": false + } + ], + "objects": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.cspConfig", + "type": "Object", + "tags": [], + "label": "cspConfig", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/csp/config.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.cspConfig.path", + "type": "string", + "tags": [], + "label": "path", + "description": [ + "// TODO: Move this to server.csp using config deprecations\n// ? https://github.com/elastic/kibana/pull/52251" + ], + "path": "packages/core/http/core-http-server-internal/src/csp/config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.cspConfig.schema", + "type": "Object", + "tags": [], + "label": "schema", + "description": [], + "signature": [ + "ObjectType", + "<{ disableUnsafeEval: ", + "ConditionalType", + "; script_src: ", + "Type", + "; worker_src: ", + "Type", + "; style_src: ", + "Type", + "; connect_src: ", + "Type", + "; default_src: ", + "Type", + "; font_src: ", + "Type", + "; frame_src: ", + "Type", + "; img_src: ", + "Type", + "; frame_ancestors: ", + "Type", + "; report_uri: ", + "Type", + "; report_to: ", + "Type", + "; strict: ", + "Type", + "; warnLegacyBrowsers: ", + "Type", + "; disableEmbedding: ", + "Type", + "; }>" + ], + "path": "packages/core/http/core-http-server-internal/src/csp/config.ts", + "deprecated": false + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.externalUrlConfig", + "type": "Object", + "tags": [], + "label": "externalUrlConfig", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/external_url/config.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.externalUrlConfig.path", + "type": "string", + "tags": [], + "label": "path", + "description": [], + "path": "packages/core/http/core-http-server-internal/src/external_url/config.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-internal", + "id": "def-server.externalUrlConfig.schema", + "type": "Object", + "tags": [], + "label": "schema", + "description": [], + "signature": [ + "ObjectType", + "<{ policy: ", + "Type", + "<", + "IExternalUrlPolicy", + "[]>; }>" + ], + "path": "packages/core/http/core-http-server-internal/src/external_url/config.ts", + "deprecated": false + } + ], + "initialIsOpen": false + } + ] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_http_server_internal.mdx b/api_docs/kbn_core_http_server_internal.mdx new file mode 100644 index 0000000000000..c73c69d8383de --- /dev/null +++ b/api_docs/kbn_core_http_server_internal.mdx @@ -0,0 +1,36 @@ +--- +id: kibKbnCoreHttpServerInternalPluginApi +slug: /kibana-dev-docs/api/kbn-core-http-server-internal +title: "@kbn/core-http-server-internal" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-http-server-internal plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-server-internal'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreHttpServerInternalObj from './kbn_core_http_server_internal.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 54 | 0 | 48 | 2 | + +## Server + +### Objects + + +### Functions + + +### Classes + + +### Consts, variables and types + + diff --git a/api_docs/kbn_core_http_server_mocks.devdocs.json b/api_docs/kbn_core_http_server_mocks.devdocs.json new file mode 100644 index 0000000000000..bdbc8ce677929 --- /dev/null +++ b/api_docs/kbn_core_http_server_mocks.devdocs.json @@ -0,0 +1,830 @@ +{ + "id": "@kbn/core-http-server-mocks", + "client": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + }, + "server": { + "classes": [], + "functions": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.createCoreContext", + "type": "Function", + "tags": [], + "label": "createCoreContext", + "description": [], + "signature": [ + "(overrides?: Partial<", + "CoreContext", + ">) => ", + "CoreContext" + ], + "path": "packages/core/http/core-http-server-mocks/src/test_utils.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.createCoreContext.$1", + "type": "Object", + "tags": [], + "label": "overrides", + "description": [], + "signature": [ + "Partial<", + "CoreContext", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/test_utils.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.createHttpServer", + "type": "Function", + "tags": [], + "label": "createHttpServer", + "description": [ + "\nCreates a concrete HttpServer with a mocked context." + ], + "signature": [ + "(overrides?: Partial<", + "CoreContext", + ">) => ", + "HttpService" + ], + "path": "packages/core/http/core-http-server-mocks/src/test_utils.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.createHttpServer.$1", + "type": "Object", + "tags": [], + "label": "overrides", + "description": [], + "signature": [ + "Partial<", + "CoreContext", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/test_utils.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [], + "initialIsOpen": false + } + ], + "interfaces": [], + "enums": [], + "misc": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.HttpServicePrebootMock", + "type": "Type", + "tags": [], + "label": "HttpServicePrebootMock", + "description": [], + "signature": [ + "{ registerRoutes: jest.MockInstance) => void]>; basePath: ", + "IBasePath", + "; getServerInfo: jest.MockInstance<", + "HttpServerInfo", + ", []>; } & ", + "HttpServicePreboot", + "<", + "RequestHandlerContextBase", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.HttpServiceSetupMock", + "type": "Type", + "tags": [], + "label": "HttpServiceSetupMock", + "description": [], + "signature": [ + "{ csp: ", + "ICspConfig", + "; createCookieSessionStorageFactory: jest.MockInstance>, [cookieOptions: ", + "SessionStorageCookieOptions", + "]>; registerOnPreRouting: jest.MockInstance; registerOnPreAuth: jest.MockInstance; registerAuth: jest.MockInstance; registerOnPostAuth: jest.MockInstance; registerOnPreResponse: jest.MockInstance; getServerInfo: jest.MockInstance<", + "HttpServerInfo", + ", []>; registerRouteHandlerContext: jest.MockInstance<", + "IContextContainer", + ", [contextName: Exclude, provider: ", + "IContextProvider", + ">]>; } & Omit<", + "HttpServiceSetup", + ", \"basePath\" | \"createRouter\"> & { basePath: BasePathMocked; createRouter: jest.MockedFunction<() => ", + "RouterMock", + ">; }" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.HttpServiceStartMock", + "type": "Type", + "tags": [], + "label": "HttpServiceStartMock", + "description": [], + "signature": [ + "{ basePath: ", + "IBasePath", + "; auth: ", + "HttpAuth", + "; getServerInfo: jest.MockInstance<", + "HttpServerInfo", + ", []>; } & ", + "HttpServiceStart", + " & { basePath: BasePathMocked; }" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.InternalHttpServicePrebootMock", + "type": "Type", + "tags": [], + "label": "InternalHttpServicePrebootMock", + "description": [], + "signature": [ + "{ auth: ", + "HttpAuth", + "; server: ", + "Server", + "; externalUrl: ", + "ExternalUrlConfig", + "; csp: ", + "ICspConfig", + "; registerStaticDir: jest.MockInstance; getServerInfo: jest.MockInstance<", + "HttpServerInfo", + ", []>; registerRouteHandlerContext: jest.MockInstance]>; registerRoutes: jest.MockInstance) => void]>; } & Omit<", + "InternalHttpServicePreboot", + ", \"basePath\"> & { basePath: BasePathMocked; }" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.InternalHttpServiceSetupMock", + "type": "Type", + "tags": [], + "label": "InternalHttpServiceSetupMock", + "description": [], + "signature": [ + "{ server: ", + "Server", + "; externalUrl: ", + "ExternalUrlConfig", + "; csp: ", + "ICspConfig", + "; registerRouterAfterListening: jest.MockInstance]>; registerStaticDir: jest.MockInstance; createCookieSessionStorageFactory: jest.MockInstance>, [cookieOptions: ", + "SessionStorageCookieOptions", + "]>; registerOnPreRouting: jest.MockInstance; registerOnPreAuth: jest.MockInstance; registerAuth: jest.MockInstance; registerOnPostAuth: jest.MockInstance; registerOnPreResponse: jest.MockInstance; getServerInfo: jest.MockInstance<", + "HttpServerInfo", + ", []>; registerRouteHandlerContext: jest.MockInstance]>; registerPrebootRoutes: jest.MockInstance) => void]>; } & Omit<", + "InternalHttpServiceSetup", + ", \"basePath\" | \"auth\" | \"authRequestHeaders\" | \"createRouter\"> & { auth: AuthMocked; basePath: BasePathMocked; createRouter: jest.MockedFunction<(path: string) => ", + "RouterMock", + ">; authRequestHeaders: jest.Mocked<", + "IAuthHeadersStorage", + ">; }" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.InternalHttpServiceStartMock", + "type": "Type", + "tags": [], + "label": "InternalHttpServiceStartMock", + "description": [], + "signature": [ + "{ isListening: jest.MockInstance; basePath: ", + "IBasePath", + "; auth: ", + "HttpAuth", + "; getServerInfo: jest.MockInstance<", + "HttpServerInfo", + ", []>; } & ", + "InternalHttpServiceStart", + " & { basePath: BasePathMocked; }" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "initialIsOpen": false + } + ], + "objects": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock", + "type": "Object", + "tags": [], + "label": "httpServerMock", + "description": [], + "path": "packages/core/http/core-http-server-mocks/src/http_server.mocks.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock.createKibanaRequest", + "type": "Function", + "tags": [], + "label": "createKibanaRequest", + "description": [], + "signature": [ + "

({ path, headers, params, body, query, method, socket, routeTags, routeAuthRequired, validation, kibanaRouteOptions, kibanaRequestState, auth, }?: ", + "RequestFixtureOptions", + " | undefined) => ", + "KibanaRequest", + "" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_server.mocks.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock.createKibanaRequest.$1", + "type": "Object", + "tags": [], + "label": "__0", + "description": [], + "signature": [ + "RequestFixtureOptions", + " | undefined" + ], + "path": "node_modules/@types/kbn__core-http-router-server-mocks/index.d.ts", + "deprecated": false + } + ] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock.createRawRequest", + "type": "Function", + "tags": [], + "label": "createRawRequest", + "description": [], + "signature": [ + "(customization?: ", + "DeepPartialObject", + "<", + "Request", + "> | undefined) => ", + "Request" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_server.mocks.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock.createRawRequest.$1", + "type": "Object", + "tags": [], + "label": "customization", + "description": [], + "signature": [ + "DeepPartialObject", + "<", + "Request", + "> | undefined" + ], + "path": "node_modules/@types/kbn__hapi-mocks/index.d.ts", + "deprecated": false + } + ] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock.createResponseFactory", + "type": "Function", + "tags": [], + "label": "createResponseFactory", + "description": [], + "signature": [ + "() => jest.Mocked<", + "KibanaResponseFactory", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_server.mocks.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock.createLifecycleResponseFactory", + "type": "Function", + "tags": [], + "label": "createLifecycleResponseFactory", + "description": [], + "signature": [ + "() => jest.Mocked<", + "LifecycleResponseFactory", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_server.mocks.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServerMock.createToolkit", + "type": "Function", + "tags": [], + "label": "createToolkit", + "description": [], + "signature": [ + "() => ToolkitMock" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_server.mocks.ts", + "deprecated": false, + "returnComment": [], + "children": [] + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock", + "type": "Object", + "tags": [], + "label": "httpServiceMock", + "description": [], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.create", + "type": "Function", + "tags": [], + "label": "create", + "description": [], + "signature": [ + "() => jest.Mocked" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createBasePath", + "type": "Function", + "tags": [], + "label": "createBasePath", + "description": [], + "signature": [ + "(serverBasePath?: string, publicBaseUrl?: string) => BasePathMocked" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createBasePath.$1", + "type": "string", + "tags": [], + "label": "serverBasePath", + "description": [], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createBasePath.$2", + "type": "string", + "tags": [], + "label": "publicBaseUrl", + "description": [], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false + } + ] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createAuth", + "type": "Function", + "tags": [], + "label": "createAuth", + "description": [], + "signature": [ + "() => AuthMocked" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createInternalPrebootContract", + "type": "Function", + "tags": [], + "label": "createInternalPrebootContract", + "description": [], + "signature": [ + "() => ", + { + "pluginId": "@kbn/core-http-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpServerMocksPluginApi", + "section": "def-server.InternalHttpServicePrebootMock", + "text": "InternalHttpServicePrebootMock" + } + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createPrebootContract", + "type": "Function", + "tags": [], + "label": "createPrebootContract", + "description": [], + "signature": [ + "() => ", + { + "pluginId": "@kbn/core-http-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpServerMocksPluginApi", + "section": "def-server.HttpServicePrebootMock", + "text": "HttpServicePrebootMock" + } + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createInternalSetupContract", + "type": "Function", + "tags": [], + "label": "createInternalSetupContract", + "description": [], + "signature": [ + "() => ", + { + "pluginId": "@kbn/core-http-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpServerMocksPluginApi", + "section": "def-server.InternalHttpServiceSetupMock", + "text": "InternalHttpServiceSetupMock" + } + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createSetupContract", + "type": "Function", + "tags": [], + "label": "createSetupContract", + "description": [], + "signature": [ + "() => ", + { + "pluginId": "@kbn/core-http-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpServerMocksPluginApi", + "section": "def-server.HttpServiceSetupMock", + "text": "HttpServiceSetupMock" + }, + "" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createInternalStartContract", + "type": "Function", + "tags": [], + "label": "createInternalStartContract", + "description": [], + "signature": [ + "() => ", + { + "pluginId": "@kbn/core-http-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpServerMocksPluginApi", + "section": "def-server.InternalHttpServiceStartMock", + "text": "InternalHttpServiceStartMock" + } + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createStartContract", + "type": "Function", + "tags": [], + "label": "createStartContract", + "description": [], + "signature": [ + "() => ", + { + "pluginId": "@kbn/core-http-server-mocks", + "scope": "server", + "docId": "kibKbnCoreHttpServerMocksPluginApi", + "section": "def-server.HttpServiceStartMock", + "text": "HttpServiceStartMock" + } + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createOnPreAuthToolkit", + "type": "Function", + "tags": [], + "label": "createOnPreAuthToolkit", + "description": [], + "signature": [ + "() => jest.Mocked<", + "OnPreAuthToolkit", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createOnPostAuthToolkit", + "type": "Function", + "tags": [], + "label": "createOnPostAuthToolkit", + "description": [], + "signature": [ + "() => jest.Mocked<", + "OnPostAuthToolkit", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createOnPreResponseToolkit", + "type": "Function", + "tags": [], + "label": "createOnPreResponseToolkit", + "description": [], + "signature": [ + "() => jest.Mocked<", + "OnPreResponseToolkit", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createOnPreRoutingToolkit", + "type": "Function", + "tags": [], + "label": "createOnPreRoutingToolkit", + "description": [], + "signature": [ + "() => jest.Mocked<", + "OnPreRoutingToolkit", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createAuthToolkit", + "type": "Function", + "tags": [], + "label": "createAuthToolkit", + "description": [], + "signature": [ + "() => jest.Mocked<", + "AuthToolkit", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createAuthHeaderStorage", + "type": "Function", + "tags": [], + "label": "createAuthHeaderStorage", + "description": [], + "signature": [ + "() => jest.Mocked<", + "IAuthHeadersStorage", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createRouter", + "type": "Function", + "tags": [], + "label": "createRouter", + "description": [], + "signature": [ + "({ routerPath }?: { routerPath?: string | undefined; } | undefined) => ", + "RouterMock" + ], + "path": "packages/core/http/core-http-server-mocks/src/http_service.mock.ts", + "deprecated": false, + "returnComment": [], + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.httpServiceMock.createRouter.$1", + "type": "Object", + "tags": [], + "label": "__0", + "description": [], + "signature": [ + "{ routerPath?: string | undefined; } | undefined" + ], + "path": "node_modules/@types/kbn__core-http-router-server-mocks/index.d.ts", + "deprecated": false + } + ] + } + ], + "initialIsOpen": false + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.sessionStorageMock", + "type": "Object", + "tags": [], + "label": "sessionStorageMock", + "description": [], + "path": "packages/core/http/core-http-server-mocks/src/cookie_session_storage.mocks.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.sessionStorageMock.create", + "type": "Function", + "tags": [], + "label": "create", + "description": [], + "signature": [ + "() => jest.Mocked<", + "SessionStorage", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/cookie_session_storage.mocks.ts", + "deprecated": false, + "returnComment": [], + "children": [] + }, + { + "parentPluginId": "@kbn/core-http-server-mocks", + "id": "def-server.sessionStorageMock.createFactory", + "type": "Function", + "tags": [], + "label": "createFactory", + "description": [], + "signature": [ + "() => DeepMocked<", + "SessionStorageFactory", + ">" + ], + "path": "packages/core/http/core-http-server-mocks/src/cookie_session_storage.mocks.ts", + "deprecated": false, + "returnComment": [], + "children": [] + } + ], + "initialIsOpen": false + } + ] + }, + "common": { + "classes": [], + "functions": [], + "interfaces": [], + "enums": [], + "misc": [], + "objects": [] + } +} \ No newline at end of file diff --git a/api_docs/kbn_core_http_server_mocks.mdx b/api_docs/kbn_core_http_server_mocks.mdx new file mode 100644 index 0000000000000..c516312a3b173 --- /dev/null +++ b/api_docs/kbn_core_http_server_mocks.mdx @@ -0,0 +1,33 @@ +--- +id: kibKbnCoreHttpServerMocksPluginApi +slug: /kibana-dev-docs/api/kbn-core-http-server-mocks +title: "@kbn/core-http-server-mocks" +image: https://source.unsplash.com/400x175/?github +summary: API docs for the @kbn/core-http-server-mocks plugin +date: 2022-07-14 +tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-http-server-mocks'] +warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. +--- +import kbnCoreHttpServerMocksObj from './kbn_core_http_server_mocks.devdocs.json'; + + + +Contact [Owner missing] for questions regarding this plugin. + +**Code health stats** + +| Public API count | Any count | Items lacking comments | Missing exports | +|-------------------|-----------|------------------------|-----------------| +| 41 | 0 | 37 | 0 | + +## Server + +### Objects + + +### Functions + + +### Consts, variables and types + + diff --git a/api_docs/kbn_core_i18n_browser.mdx b/api_docs/kbn_core_i18n_browser.mdx index fd5dc5578ec45..aa6d11478fe41 100644 --- a/api_docs/kbn_core_i18n_browser.mdx +++ b/api_docs/kbn_core_i18n_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-i18n-browser title: "@kbn/core-i18n-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-i18n-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-i18n-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_i18n_browser_mocks.mdx b/api_docs/kbn_core_i18n_browser_mocks.mdx index 451a717d03e00..a0fd4df5a9477 100644 --- a/api_docs/kbn_core_i18n_browser_mocks.mdx +++ b/api_docs/kbn_core_i18n_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-i18n-browser-mocks title: "@kbn/core-i18n-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-i18n-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-i18n-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_injected_metadata_browser.mdx b/api_docs/kbn_core_injected_metadata_browser.mdx index e1277bff51595..b47b634ce27c2 100644 --- a/api_docs/kbn_core_injected_metadata_browser.mdx +++ b/api_docs/kbn_core_injected_metadata_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-injected-metadata-browser title: "@kbn/core-injected-metadata-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-injected-metadata-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-injected-metadata-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_injected_metadata_browser_mocks.mdx b/api_docs/kbn_core_injected_metadata_browser_mocks.mdx index 315b6ccb8dd93..60a73253e7339 100644 --- a/api_docs/kbn_core_injected_metadata_browser_mocks.mdx +++ b/api_docs/kbn_core_injected_metadata_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-injected-metadata-browser-mocks title: "@kbn/core-injected-metadata-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-injected-metadata-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-injected-metadata-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_logging_server.mdx b/api_docs/kbn_core_logging_server.mdx index 1e2f604a6658a..1271bdaa68042 100644 --- a/api_docs/kbn_core_logging_server.mdx +++ b/api_docs/kbn_core_logging_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-logging-server title: "@kbn/core-logging-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-logging-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-logging-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_logging_server_internal.mdx b/api_docs/kbn_core_logging_server_internal.mdx index 6c2e940096f8a..6f0eec690a19c 100644 --- a/api_docs/kbn_core_logging_server_internal.mdx +++ b/api_docs/kbn_core_logging_server_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-logging-server-internal title: "@kbn/core-logging-server-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-logging-server-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-logging-server-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_logging_server_mocks.mdx b/api_docs/kbn_core_logging_server_mocks.mdx index 41a4a645ccbb6..643eb7e439c80 100644 --- a/api_docs/kbn_core_logging_server_mocks.mdx +++ b/api_docs/kbn_core_logging_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-logging-server-mocks title: "@kbn/core-logging-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-logging-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-logging-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_node_server.mdx b/api_docs/kbn_core_node_server.mdx index 1b2f3c80de467..7baf8f68460bd 100644 --- a/api_docs/kbn_core_node_server.mdx +++ b/api_docs/kbn_core_node_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-node-server title: "@kbn/core-node-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-node-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-node-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_node_server_internal.devdocs.json b/api_docs/kbn_core_node_server_internal.devdocs.json index 1937ba5e72c7d..0e598b07cd930 100644 --- a/api_docs/kbn_core_node_server_internal.devdocs.json +++ b/api_docs/kbn_core_node_server_internal.devdocs.json @@ -49,7 +49,7 @@ "ObjectType", "<{ roles: ", "Type", - "<(\"ui\" | \"background_tasks\")[] | \"*\"[]>; }>" + "<\"*\"[] | (\"ui\" | \"background_tasks\")[]>; }>" ], "path": "packages/core/node/core-node-server-internal/src/node_config.ts", "deprecated": false diff --git a/api_docs/kbn_core_node_server_internal.mdx b/api_docs/kbn_core_node_server_internal.mdx index 5885b29b2c8c8..5cadea53c1ad2 100644 --- a/api_docs/kbn_core_node_server_internal.mdx +++ b/api_docs/kbn_core_node_server_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-node-server-internal title: "@kbn/core-node-server-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-node-server-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-node-server-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_node_server_mocks.mdx b/api_docs/kbn_core_node_server_mocks.mdx index 9e667be321173..9b902ede606eb 100644 --- a/api_docs/kbn_core_node_server_mocks.mdx +++ b/api_docs/kbn_core_node_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-node-server-mocks title: "@kbn/core-node-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-node-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-node-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_preboot_server.mdx b/api_docs/kbn_core_preboot_server.mdx index b109431d1dbad..c5b4f7fd3a743 100644 --- a/api_docs/kbn_core_preboot_server.mdx +++ b/api_docs/kbn_core_preboot_server.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-preboot-server title: "@kbn/core-preboot-server" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-preboot-server plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-preboot-server'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_preboot_server_mocks.mdx b/api_docs/kbn_core_preboot_server_mocks.mdx index ed3173fb57216..da8147070af3c 100644 --- a/api_docs/kbn_core_preboot_server_mocks.mdx +++ b/api_docs/kbn_core_preboot_server_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-preboot-server-mocks title: "@kbn/core-preboot-server-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-preboot-server-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-preboot-server-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_theme_browser.mdx b/api_docs/kbn_core_theme_browser.mdx index 09957ca3e6854..d34910c499bec 100644 --- a/api_docs/kbn_core_theme_browser.mdx +++ b/api_docs/kbn_core_theme_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-theme-browser title: "@kbn/core-theme-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-theme-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-theme-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_theme_browser_internal.mdx b/api_docs/kbn_core_theme_browser_internal.mdx index c3a60618f7845..bfa6185b08084 100644 --- a/api_docs/kbn_core_theme_browser_internal.mdx +++ b/api_docs/kbn_core_theme_browser_internal.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-theme-browser-internal title: "@kbn/core-theme-browser-internal" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-theme-browser-internal plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-theme-browser-internal'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_core_theme_browser_mocks.mdx b/api_docs/kbn_core_theme_browser_mocks.mdx index 3a7174fc1b2e3..af0cf0d8eb376 100644 --- a/api_docs/kbn_core_theme_browser_mocks.mdx +++ b/api_docs/kbn_core_theme_browser_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-core-theme-browser-mocks title: "@kbn/core-theme-browser-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/core-theme-browser-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/core-theme-browser-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_crypto.mdx b/api_docs/kbn_crypto.mdx index 7c0e6e7648ffa..f9666b549b956 100644 --- a/api_docs/kbn_crypto.mdx +++ b/api_docs/kbn_crypto.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-crypto title: "@kbn/crypto" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/crypto plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/crypto'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_crypto_browser.mdx b/api_docs/kbn_crypto_browser.mdx index 6017c04753893..5dc3a3a9ce3d7 100644 --- a/api_docs/kbn_crypto_browser.mdx +++ b/api_docs/kbn_crypto_browser.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-crypto-browser title: "@kbn/crypto-browser" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/crypto-browser plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/crypto-browser'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_datemath.mdx b/api_docs/kbn_datemath.mdx index 87f44ac0da128..ff8d5e58a4b30 100644 --- a/api_docs/kbn_datemath.mdx +++ b/api_docs/kbn_datemath.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-datemath title: "@kbn/datemath" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/datemath plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/datemath'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_dev_cli_errors.mdx b/api_docs/kbn_dev_cli_errors.mdx index 0889027b5ed49..42af03db50d80 100644 --- a/api_docs/kbn_dev_cli_errors.mdx +++ b/api_docs/kbn_dev_cli_errors.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-dev-cli-errors title: "@kbn/dev-cli-errors" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/dev-cli-errors plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/dev-cli-errors'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_dev_cli_runner.mdx b/api_docs/kbn_dev_cli_runner.mdx index 759f8039981f8..b397c9ca8b990 100644 --- a/api_docs/kbn_dev_cli_runner.mdx +++ b/api_docs/kbn_dev_cli_runner.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-dev-cli-runner title: "@kbn/dev-cli-runner" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/dev-cli-runner plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/dev-cli-runner'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_dev_proc_runner.mdx b/api_docs/kbn_dev_proc_runner.mdx index 2d5e8095c3ffd..7f40c05c56b03 100644 --- a/api_docs/kbn_dev_proc_runner.mdx +++ b/api_docs/kbn_dev_proc_runner.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-dev-proc-runner title: "@kbn/dev-proc-runner" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/dev-proc-runner plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/dev-proc-runner'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_dev_utils.mdx b/api_docs/kbn_dev_utils.mdx index 2a578260588bf..90779a5021782 100644 --- a/api_docs/kbn_dev_utils.mdx +++ b/api_docs/kbn_dev_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-dev-utils title: "@kbn/dev-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/dev-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/dev-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_doc_links.mdx b/api_docs/kbn_doc_links.mdx index 00ef15c27f6c6..5e8a7dd11f985 100644 --- a/api_docs/kbn_doc_links.mdx +++ b/api_docs/kbn_doc_links.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-doc-links title: "@kbn/doc-links" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/doc-links plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/doc-links'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_docs_utils.mdx b/api_docs/kbn_docs_utils.mdx index 1745e95ece2ba..9954cf11e03ed 100644 --- a/api_docs/kbn_docs_utils.mdx +++ b/api_docs/kbn_docs_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-docs-utils title: "@kbn/docs-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/docs-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/docs-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_es_archiver.mdx b/api_docs/kbn_es_archiver.mdx index 59a8a0413c64c..33ed18985a880 100644 --- a/api_docs/kbn_es_archiver.mdx +++ b/api_docs/kbn_es_archiver.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-es-archiver title: "@kbn/es-archiver" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/es-archiver plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/es-archiver'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_es_errors.mdx b/api_docs/kbn_es_errors.mdx index 65d64b1d89a75..fb1b50360c1a2 100644 --- a/api_docs/kbn_es_errors.mdx +++ b/api_docs/kbn_es_errors.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-es-errors title: "@kbn/es-errors" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/es-errors plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/es-errors'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_es_query.mdx b/api_docs/kbn_es_query.mdx index 9084761693e28..9e2abca838898 100644 --- a/api_docs/kbn_es_query.mdx +++ b/api_docs/kbn_es_query.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-es-query title: "@kbn/es-query" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/es-query plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/es-query'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_eslint_plugin_imports.mdx b/api_docs/kbn_eslint_plugin_imports.mdx index 46381bd6e4ed9..395685fc79323 100644 --- a/api_docs/kbn_eslint_plugin_imports.mdx +++ b/api_docs/kbn_eslint_plugin_imports.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-eslint-plugin-imports title: "@kbn/eslint-plugin-imports" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/eslint-plugin-imports plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/eslint-plugin-imports'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_field_types.mdx b/api_docs/kbn_field_types.mdx index 851a8217b16ca..94e56499a960e 100644 --- a/api_docs/kbn_field_types.mdx +++ b/api_docs/kbn_field_types.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-field-types title: "@kbn/field-types" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/field-types plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/field-types'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_find_used_node_modules.mdx b/api_docs/kbn_find_used_node_modules.mdx index c1e107406b828..40e5082986662 100644 --- a/api_docs/kbn_find_used_node_modules.mdx +++ b/api_docs/kbn_find_used_node_modules.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-find-used-node-modules title: "@kbn/find-used-node-modules" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/find-used-node-modules plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/find-used-node-modules'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_generate.mdx b/api_docs/kbn_generate.mdx index b77f7771f716b..b256d678f979c 100644 --- a/api_docs/kbn_generate.mdx +++ b/api_docs/kbn_generate.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-generate title: "@kbn/generate" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/generate plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/generate'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_handlebars.mdx b/api_docs/kbn_handlebars.mdx index c9dfd16d549fe..e4ede6274d832 100644 --- a/api_docs/kbn_handlebars.mdx +++ b/api_docs/kbn_handlebars.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-handlebars title: "@kbn/handlebars" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/handlebars plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/handlebars'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_hapi_mocks.mdx b/api_docs/kbn_hapi_mocks.mdx index 74193484aaa01..e65a0d5610c8e 100644 --- a/api_docs/kbn_hapi_mocks.mdx +++ b/api_docs/kbn_hapi_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-hapi-mocks title: "@kbn/hapi-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/hapi-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/hapi-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_home_sample_data_cards.mdx b/api_docs/kbn_home_sample_data_cards.mdx index ff0d667da085f..b9dcbec9e5980 100644 --- a/api_docs/kbn_home_sample_data_cards.mdx +++ b/api_docs/kbn_home_sample_data_cards.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-home-sample-data-cards title: "@kbn/home-sample-data-cards" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/home-sample-data-cards plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/home-sample-data-cards'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_i18n.mdx b/api_docs/kbn_i18n.mdx index c8164c7778e15..e352cba531780 100644 --- a/api_docs/kbn_i18n.mdx +++ b/api_docs/kbn_i18n.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-i18n title: "@kbn/i18n" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/i18n plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/i18n'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_import_resolver.mdx b/api_docs/kbn_import_resolver.mdx index 95f220bd9fb5b..0ce4b91ab8488 100644 --- a/api_docs/kbn_import_resolver.mdx +++ b/api_docs/kbn_import_resolver.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-import-resolver title: "@kbn/import-resolver" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/import-resolver plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/import-resolver'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_interpreter.mdx b/api_docs/kbn_interpreter.mdx index ea07bac765030..7ac13aed307e1 100644 --- a/api_docs/kbn_interpreter.mdx +++ b/api_docs/kbn_interpreter.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-interpreter title: "@kbn/interpreter" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/interpreter plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/interpreter'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_io_ts_utils.mdx b/api_docs/kbn_io_ts_utils.mdx index 2b5ce56a5d60f..85956d04c0326 100644 --- a/api_docs/kbn_io_ts_utils.mdx +++ b/api_docs/kbn_io_ts_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-io-ts-utils title: "@kbn/io-ts-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/io-ts-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/io-ts-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_jest_serializers.mdx b/api_docs/kbn_jest_serializers.mdx index a994586c8a74e..abf0e153fb8fc 100644 --- a/api_docs/kbn_jest_serializers.mdx +++ b/api_docs/kbn_jest_serializers.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-jest-serializers title: "@kbn/jest-serializers" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/jest-serializers plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/jest-serializers'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_kibana_json_schema.mdx b/api_docs/kbn_kibana_json_schema.mdx index e351775e76cee..16c8895f92067 100644 --- a/api_docs/kbn_kibana_json_schema.mdx +++ b/api_docs/kbn_kibana_json_schema.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-kibana-json-schema title: "@kbn/kibana-json-schema" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/kibana-json-schema plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/kibana-json-schema'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_logging.mdx b/api_docs/kbn_logging.mdx index d2b10fc180773..937e89a6f60bb 100644 --- a/api_docs/kbn_logging.mdx +++ b/api_docs/kbn_logging.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-logging title: "@kbn/logging" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/logging plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/logging'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_logging_mocks.mdx b/api_docs/kbn_logging_mocks.mdx index e6ebec63e1632..0375141e756fd 100644 --- a/api_docs/kbn_logging_mocks.mdx +++ b/api_docs/kbn_logging_mocks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-logging-mocks title: "@kbn/logging-mocks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/logging-mocks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/logging-mocks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_mapbox_gl.mdx b/api_docs/kbn_mapbox_gl.mdx index 28115f56adc24..fe260609be7c3 100644 --- a/api_docs/kbn_mapbox_gl.mdx +++ b/api_docs/kbn_mapbox_gl.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-mapbox-gl title: "@kbn/mapbox-gl" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/mapbox-gl plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/mapbox-gl'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ml_agg_utils.mdx b/api_docs/kbn_ml_agg_utils.mdx index d9073ce0d303d..2326cb5088e7e 100644 --- a/api_docs/kbn_ml_agg_utils.mdx +++ b/api_docs/kbn_ml_agg_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ml-agg-utils title: "@kbn/ml-agg-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ml-agg-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ml-agg-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ml_is_populated_object.mdx b/api_docs/kbn_ml_is_populated_object.mdx index a9e31ddb35448..8cddd1bca6fa2 100644 --- a/api_docs/kbn_ml_is_populated_object.mdx +++ b/api_docs/kbn_ml_is_populated_object.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ml-is-populated-object title: "@kbn/ml-is-populated-object" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ml-is-populated-object plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ml-is-populated-object'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ml_string_hash.mdx b/api_docs/kbn_ml_string_hash.mdx index f9f2be975e065..8899e289794ea 100644 --- a/api_docs/kbn_ml_string_hash.mdx +++ b/api_docs/kbn_ml_string_hash.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ml-string-hash title: "@kbn/ml-string-hash" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ml-string-hash plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ml-string-hash'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_monaco.mdx b/api_docs/kbn_monaco.mdx index c51c233e79489..ab1d72895d2ab 100644 --- a/api_docs/kbn_monaco.mdx +++ b/api_docs/kbn_monaco.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-monaco title: "@kbn/monaco" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/monaco plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/monaco'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_optimizer.mdx b/api_docs/kbn_optimizer.mdx index 26d65a3ead693..e12739a0389a8 100644 --- a/api_docs/kbn_optimizer.mdx +++ b/api_docs/kbn_optimizer.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-optimizer title: "@kbn/optimizer" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/optimizer plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/optimizer'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_optimizer_webpack_helpers.mdx b/api_docs/kbn_optimizer_webpack_helpers.mdx index 401301b348c9e..4306f86b1cbc2 100644 --- a/api_docs/kbn_optimizer_webpack_helpers.mdx +++ b/api_docs/kbn_optimizer_webpack_helpers.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-optimizer-webpack-helpers title: "@kbn/optimizer-webpack-helpers" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/optimizer-webpack-helpers plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/optimizer-webpack-helpers'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_performance_testing_dataset_extractor.mdx b/api_docs/kbn_performance_testing_dataset_extractor.mdx index f57e25cf322cb..a6bbf05299d66 100644 --- a/api_docs/kbn_performance_testing_dataset_extractor.mdx +++ b/api_docs/kbn_performance_testing_dataset_extractor.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-performance-testing-dataset-extractor title: "@kbn/performance-testing-dataset-extractor" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/performance-testing-dataset-extractor plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/performance-testing-dataset-extractor'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_plugin_discovery.mdx b/api_docs/kbn_plugin_discovery.mdx index 55e9a6b95abc0..bb0a1cbeb1d81 100644 --- a/api_docs/kbn_plugin_discovery.mdx +++ b/api_docs/kbn_plugin_discovery.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-plugin-discovery title: "@kbn/plugin-discovery" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/plugin-discovery plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/plugin-discovery'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_plugin_generator.mdx b/api_docs/kbn_plugin_generator.mdx index e4578b1f4a432..29e0dbe26454d 100644 --- a/api_docs/kbn_plugin_generator.mdx +++ b/api_docs/kbn_plugin_generator.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-plugin-generator title: "@kbn/plugin-generator" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/plugin-generator plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/plugin-generator'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_plugin_helpers.mdx b/api_docs/kbn_plugin_helpers.mdx index 4374d72505a63..a469596277018 100644 --- a/api_docs/kbn_plugin_helpers.mdx +++ b/api_docs/kbn_plugin_helpers.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-plugin-helpers title: "@kbn/plugin-helpers" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/plugin-helpers plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/plugin-helpers'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_pm.mdx b/api_docs/kbn_pm.mdx index da5a74d30c957..a6ddd54dbaa4c 100644 --- a/api_docs/kbn_pm.mdx +++ b/api_docs/kbn_pm.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-pm title: "@kbn/pm" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/pm plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/pm'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_react_field.mdx b/api_docs/kbn_react_field.mdx index ca8e694697cd0..472f8f650e343 100644 --- a/api_docs/kbn_react_field.mdx +++ b/api_docs/kbn_react_field.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-react-field title: "@kbn/react-field" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/react-field plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/react-field'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_rule_data_utils.mdx b/api_docs/kbn_rule_data_utils.mdx index 5482e0bedb1a2..69a31da2c9fbc 100644 --- a/api_docs/kbn_rule_data_utils.mdx +++ b/api_docs/kbn_rule_data_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-rule-data-utils title: "@kbn/rule-data-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/rule-data-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/rule-data-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_scalability_simulation_generator.mdx b/api_docs/kbn_scalability_simulation_generator.mdx index e79d76f12349e..6732b843b90f3 100644 --- a/api_docs/kbn_scalability_simulation_generator.mdx +++ b/api_docs/kbn_scalability_simulation_generator.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-scalability-simulation-generator title: "@kbn/scalability-simulation-generator" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/scalability-simulation-generator plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/scalability-simulation-generator'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_autocomplete.mdx b/api_docs/kbn_securitysolution_autocomplete.mdx index e8ccd05d48c9a..bbbfaf383c906 100644 --- a/api_docs/kbn_securitysolution_autocomplete.mdx +++ b/api_docs/kbn_securitysolution_autocomplete.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-autocomplete title: "@kbn/securitysolution-autocomplete" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-autocomplete plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-autocomplete'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_es_utils.mdx b/api_docs/kbn_securitysolution_es_utils.mdx index 6c944bcd5e19e..c5b943774e8e0 100644 --- a/api_docs/kbn_securitysolution_es_utils.mdx +++ b/api_docs/kbn_securitysolution_es_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-es-utils title: "@kbn/securitysolution-es-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-es-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-es-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_hook_utils.mdx b/api_docs/kbn_securitysolution_hook_utils.mdx index 6728b6ba14dee..ac1c7b8967aa3 100644 --- a/api_docs/kbn_securitysolution_hook_utils.mdx +++ b/api_docs/kbn_securitysolution_hook_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-hook-utils title: "@kbn/securitysolution-hook-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-hook-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-hook-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_io_ts_alerting_types.mdx b/api_docs/kbn_securitysolution_io_ts_alerting_types.mdx index 347d01b914dbc..4ae789c8cccc6 100644 --- a/api_docs/kbn_securitysolution_io_ts_alerting_types.mdx +++ b/api_docs/kbn_securitysolution_io_ts_alerting_types.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-io-ts-alerting-types title: "@kbn/securitysolution-io-ts-alerting-types" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-io-ts-alerting-types plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-io-ts-alerting-types'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_io_ts_list_types.mdx b/api_docs/kbn_securitysolution_io_ts_list_types.mdx index 833b86fa341b0..51ffe4adef099 100644 --- a/api_docs/kbn_securitysolution_io_ts_list_types.mdx +++ b/api_docs/kbn_securitysolution_io_ts_list_types.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-io-ts-list-types title: "@kbn/securitysolution-io-ts-list-types" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-io-ts-list-types plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-io-ts-list-types'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_io_ts_types.mdx b/api_docs/kbn_securitysolution_io_ts_types.mdx index 762606a0b72b1..52ec4ab06d2cd 100644 --- a/api_docs/kbn_securitysolution_io_ts_types.mdx +++ b/api_docs/kbn_securitysolution_io_ts_types.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-io-ts-types title: "@kbn/securitysolution-io-ts-types" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-io-ts-types plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-io-ts-types'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_io_ts_utils.mdx b/api_docs/kbn_securitysolution_io_ts_utils.mdx index 71a19be9283bf..09f6659d3c294 100644 --- a/api_docs/kbn_securitysolution_io_ts_utils.mdx +++ b/api_docs/kbn_securitysolution_io_ts_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-io-ts-utils title: "@kbn/securitysolution-io-ts-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-io-ts-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-io-ts-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_list_api.mdx b/api_docs/kbn_securitysolution_list_api.mdx index b85e37444435f..2af92d9d20ef3 100644 --- a/api_docs/kbn_securitysolution_list_api.mdx +++ b/api_docs/kbn_securitysolution_list_api.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-list-api title: "@kbn/securitysolution-list-api" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-list-api plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-list-api'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_list_constants.mdx b/api_docs/kbn_securitysolution_list_constants.mdx index fe27d37be1ed7..0a7a1a861d403 100644 --- a/api_docs/kbn_securitysolution_list_constants.mdx +++ b/api_docs/kbn_securitysolution_list_constants.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-list-constants title: "@kbn/securitysolution-list-constants" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-list-constants plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-list-constants'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_list_hooks.mdx b/api_docs/kbn_securitysolution_list_hooks.mdx index 36797c388c072..e373f97a3eaf3 100644 --- a/api_docs/kbn_securitysolution_list_hooks.mdx +++ b/api_docs/kbn_securitysolution_list_hooks.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-list-hooks title: "@kbn/securitysolution-list-hooks" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-list-hooks plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-list-hooks'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_list_utils.mdx b/api_docs/kbn_securitysolution_list_utils.mdx index 192b8ec9d7554..4112405b146b6 100644 --- a/api_docs/kbn_securitysolution_list_utils.mdx +++ b/api_docs/kbn_securitysolution_list_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-list-utils title: "@kbn/securitysolution-list-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-list-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-list-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_rules.mdx b/api_docs/kbn_securitysolution_rules.mdx index 26020f321d906..c506a01635d44 100644 --- a/api_docs/kbn_securitysolution_rules.mdx +++ b/api_docs/kbn_securitysolution_rules.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-rules title: "@kbn/securitysolution-rules" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-rules plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-rules'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_t_grid.mdx b/api_docs/kbn_securitysolution_t_grid.mdx index 39c4712d09079..53b3e62b0d9ad 100644 --- a/api_docs/kbn_securitysolution_t_grid.mdx +++ b/api_docs/kbn_securitysolution_t_grid.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-t-grid title: "@kbn/securitysolution-t-grid" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-t-grid plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-t-grid'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_securitysolution_utils.mdx b/api_docs/kbn_securitysolution_utils.mdx index bb30474236d0c..26df2ef43dede 100644 --- a/api_docs/kbn_securitysolution_utils.mdx +++ b/api_docs/kbn_securitysolution_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-securitysolution-utils title: "@kbn/securitysolution-utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/securitysolution-utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/securitysolution-utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_server_http_tools.mdx b/api_docs/kbn_server_http_tools.mdx index 2ae808a2f4544..ea74768f25ac3 100644 --- a/api_docs/kbn_server_http_tools.mdx +++ b/api_docs/kbn_server_http_tools.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-server-http-tools title: "@kbn/server-http-tools" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/server-http-tools plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/server-http-tools'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_server_route_repository.mdx b/api_docs/kbn_server_route_repository.mdx index a8d94e51fd268..ef73fedb99385 100644 --- a/api_docs/kbn_server_route_repository.mdx +++ b/api_docs/kbn_server_route_repository.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-server-route-repository title: "@kbn/server-route-repository" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/server-route-repository plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/server-route-repository'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_button_toolbar.mdx b/api_docs/kbn_shared_ux_button_toolbar.mdx index 4fc6f96dc869a..45d7af90368e6 100644 --- a/api_docs/kbn_shared_ux_button_toolbar.mdx +++ b/api_docs/kbn_shared_ux_button_toolbar.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-button-toolbar title: "@kbn/shared-ux-button-toolbar" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-button-toolbar plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-button-toolbar'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_card_no_data.mdx b/api_docs/kbn_shared_ux_card_no_data.mdx index 3120a76d22182..0ad1ee7db478b 100644 --- a/api_docs/kbn_shared_ux_card_no_data.mdx +++ b/api_docs/kbn_shared_ux_card_no_data.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-card-no-data title: "@kbn/shared-ux-card-no-data" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-card-no-data plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-card-no-data'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_components.mdx b/api_docs/kbn_shared_ux_components.mdx index 55b064588053a..63abc719681ba 100644 --- a/api_docs/kbn_shared_ux_components.mdx +++ b/api_docs/kbn_shared_ux_components.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-components title: "@kbn/shared-ux-components" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-components plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-components'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_page_analytics_no_data.mdx b/api_docs/kbn_shared_ux_page_analytics_no_data.mdx index b2c92e8913396..08c60b30869e6 100644 --- a/api_docs/kbn_shared_ux_page_analytics_no_data.mdx +++ b/api_docs/kbn_shared_ux_page_analytics_no_data.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-page-analytics-no-data title: "@kbn/shared-ux-page-analytics-no-data" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-page-analytics-no-data plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-page-analytics-no-data'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_page_kibana_no_data.mdx b/api_docs/kbn_shared_ux_page_kibana_no_data.mdx index d1c4b518a2b54..0fb75e8e5ce02 100644 --- a/api_docs/kbn_shared_ux_page_kibana_no_data.mdx +++ b/api_docs/kbn_shared_ux_page_kibana_no_data.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-page-kibana-no-data title: "@kbn/shared-ux-page-kibana-no-data" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-page-kibana-no-data plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-page-kibana-no-data'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_page_solution_nav.mdx b/api_docs/kbn_shared_ux_page_solution_nav.mdx index ec5eb2ca715e7..f2e65d846dd67 100644 --- a/api_docs/kbn_shared_ux_page_solution_nav.mdx +++ b/api_docs/kbn_shared_ux_page_solution_nav.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-page-solution-nav title: "@kbn/shared-ux-page-solution-nav" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-page-solution-nav plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-page-solution-nav'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_prompt_no_data_views.mdx b/api_docs/kbn_shared_ux_prompt_no_data_views.mdx index 3cd347e515853..282815be4cdf2 100644 --- a/api_docs/kbn_shared_ux_prompt_no_data_views.mdx +++ b/api_docs/kbn_shared_ux_prompt_no_data_views.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-prompt-no-data-views title: "@kbn/shared-ux-prompt-no-data-views" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-prompt-no-data-views plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-prompt-no-data-views'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_services.mdx b/api_docs/kbn_shared_ux_services.mdx index 0d2aefce71fdc..929788630e809 100644 --- a/api_docs/kbn_shared_ux_services.mdx +++ b/api_docs/kbn_shared_ux_services.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-services title: "@kbn/shared-ux-services" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-services plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-services'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_storybook.mdx b/api_docs/kbn_shared_ux_storybook.mdx index 42b4f931b1d85..ee95534091753 100644 --- a/api_docs/kbn_shared_ux_storybook.mdx +++ b/api_docs/kbn_shared_ux_storybook.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-storybook title: "@kbn/shared-ux-storybook" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-storybook plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-storybook'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_shared_ux_utility.mdx b/api_docs/kbn_shared_ux_utility.mdx index 711fb0e0cd990..1032117e3abb1 100644 --- a/api_docs/kbn_shared_ux_utility.mdx +++ b/api_docs/kbn_shared_ux_utility.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-shared-ux-utility title: "@kbn/shared-ux-utility" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/shared-ux-utility plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/shared-ux-utility'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_sort_package_json.mdx b/api_docs/kbn_sort_package_json.mdx index 5ae42cf4f2d29..109cb2d509e91 100644 --- a/api_docs/kbn_sort_package_json.mdx +++ b/api_docs/kbn_sort_package_json.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-sort-package-json title: "@kbn/sort-package-json" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/sort-package-json plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/sort-package-json'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_std.mdx b/api_docs/kbn_std.mdx index 00e47f058bb0e..963cde0877b05 100644 --- a/api_docs/kbn_std.mdx +++ b/api_docs/kbn_std.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-std title: "@kbn/std" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/std plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/std'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_stdio_dev_helpers.mdx b/api_docs/kbn_stdio_dev_helpers.mdx index a3912ad4534f4..cbc555b6edf9f 100644 --- a/api_docs/kbn_stdio_dev_helpers.mdx +++ b/api_docs/kbn_stdio_dev_helpers.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-stdio-dev-helpers title: "@kbn/stdio-dev-helpers" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/stdio-dev-helpers plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/stdio-dev-helpers'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_storybook.mdx b/api_docs/kbn_storybook.mdx index 6bd0a35d7781a..576de95c0b823 100644 --- a/api_docs/kbn_storybook.mdx +++ b/api_docs/kbn_storybook.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-storybook title: "@kbn/storybook" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/storybook plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/storybook'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_telemetry_tools.mdx b/api_docs/kbn_telemetry_tools.mdx index 01f7ecfa62fa7..0d6717d1bf28e 100644 --- a/api_docs/kbn_telemetry_tools.mdx +++ b/api_docs/kbn_telemetry_tools.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-telemetry-tools title: "@kbn/telemetry-tools" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/telemetry-tools plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/telemetry-tools'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_test.devdocs.json b/api_docs/kbn_test.devdocs.json index 0304ca46ffea1..2fdec23b80a59 100644 --- a/api_docs/kbn_test.devdocs.json +++ b/api_docs/kbn_test.devdocs.json @@ -3008,7 +3008,7 @@ "\nDetermine if a service is avaliable" ], "signature": [ - "{ (serviceName: \"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\"): true; (serviceName: K): serviceName is K; (serviceName: string): serviceName is Extract; }" + "{ (serviceName: \"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\" | \"dedicatedTaskRunner\"): true; (serviceName: K): serviceName is K; (serviceName: string): serviceName is Extract; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", "deprecated": false, @@ -3021,7 +3021,7 @@ "label": "serviceName", "description": [], "signature": [ - "\"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\"" + "\"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\" | \"dedicatedTaskRunner\"" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", "deprecated": false, @@ -3038,7 +3038,7 @@ "label": "hasService", "description": [], "signature": [ - "{ (serviceName: \"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\"): true; (serviceName: K): serviceName is K; (serviceName: string): serviceName is Extract; }" + "{ (serviceName: \"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\" | \"dedicatedTaskRunner\"): true; (serviceName: K): serviceName is K; (serviceName: string): serviceName is Extract; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", "deprecated": false, @@ -3068,7 +3068,7 @@ "label": "hasService", "description": [], "signature": [ - "{ (serviceName: \"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\"): true; (serviceName: K): serviceName is K; (serviceName: string): serviceName is Extract; }" + "{ (serviceName: \"log\" | \"config\" | \"lifecycle\" | \"dockerServers\" | \"esVersion\" | \"dedicatedTaskRunner\"): true; (serviceName: K): serviceName is K; (serviceName: string): serviceName is Extract; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", "deprecated": false, @@ -3134,6 +3134,8 @@ "section": "def-server.EsVersion", "text": "EsVersion" }, + "; (serviceName: \"dedicatedTaskRunner\"): ", + "DedicatedTaskRunner", "; (serviceName: T): ServiceMap[T]; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", @@ -3198,6 +3200,8 @@ "section": "def-server.EsVersion", "text": "EsVersion" }, + "; (serviceName: \"dedicatedTaskRunner\"): ", + "DedicatedTaskRunner", "; (serviceName: T): ServiceMap[T]; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", @@ -3262,6 +3266,8 @@ "section": "def-server.EsVersion", "text": "EsVersion" }, + "; (serviceName: \"dedicatedTaskRunner\"): ", + "DedicatedTaskRunner", "; (serviceName: T): ServiceMap[T]; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", @@ -3326,6 +3332,8 @@ "section": "def-server.EsVersion", "text": "EsVersion" }, + "; (serviceName: \"dedicatedTaskRunner\"): ", + "DedicatedTaskRunner", "; (serviceName: T): ServiceMap[T]; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", @@ -3390,6 +3398,8 @@ "section": "def-server.EsVersion", "text": "EsVersion" }, + "; (serviceName: \"dedicatedTaskRunner\"): ", + "DedicatedTaskRunner", "; (serviceName: T): ServiceMap[T]; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", @@ -3454,6 +3464,74 @@ "section": "def-server.EsVersion", "text": "EsVersion" }, + "; (serviceName: \"dedicatedTaskRunner\"): ", + "DedicatedTaskRunner", + "; (serviceName: T): ServiceMap[T]; }" + ], + "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", + "deprecated": false, + "children": [ + { + "parentPluginId": "@kbn/test", + "id": "def-server.GenericFtrProviderContext.getService.$1", + "type": "string", + "tags": [], + "label": "serviceName", + "description": [], + "signature": [ + "\"dedicatedTaskRunner\"" + ], + "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", + "deprecated": false, + "isRequired": true + } + ], + "returnComment": [] + }, + { + "parentPluginId": "@kbn/test", + "id": "def-server.GenericFtrProviderContext.getService", + "type": "Function", + "tags": [], + "label": "getService", + "description": [], + "signature": [ + "{ (serviceName: \"config\"): ", + { + "pluginId": "@kbn/test", + "scope": "server", + "docId": "kibKbnTestPluginApi", + "section": "def-server.Config", + "text": "Config" + }, + "; (serviceName: \"log\"): ", + "ToolingLog", + "; (serviceName: \"lifecycle\"): ", + { + "pluginId": "@kbn/test", + "scope": "server", + "docId": "kibKbnTestPluginApi", + "section": "def-server.Lifecycle", + "text": "Lifecycle" + }, + "; (serviceName: \"dockerServers\"): ", + { + "pluginId": "@kbn/test", + "scope": "server", + "docId": "kibKbnTestPluginApi", + "section": "def-server.DockerServersService", + "text": "DockerServersService" + }, + "; (serviceName: \"esVersion\"): ", + { + "pluginId": "@kbn/test", + "scope": "server", + "docId": "kibKbnTestPluginApi", + "section": "def-server.EsVersion", + "text": "EsVersion" + }, + "; (serviceName: \"dedicatedTaskRunner\"): ", + "DedicatedTaskRunner", "; (serviceName: T): ServiceMap[T]; }" ], "path": "packages/kbn-test/src/functional_test_runner/public_types.ts", @@ -4085,17 +4163,6 @@ "deprecated": false, "initialIsOpen": false }, - { - "parentPluginId": "@kbn/test", - "id": "def-server.KIBANA_ROOT", - "type": "string", - "tags": [], - "label": "KIBANA_ROOT", - "description": [], - "path": "packages/kbn-test/src/functional_tests/lib/paths.ts", - "deprecated": false, - "initialIsOpen": false - }, { "parentPluginId": "@kbn/test", "id": "def-server.ProvidedType", diff --git a/api_docs/kbn_test.mdx b/api_docs/kbn_test.mdx index e02a0e7631088..100a2b0809468 100644 --- a/api_docs/kbn_test.mdx +++ b/api_docs/kbn_test.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-test title: "@kbn/test" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/test plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/test'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact Operations for questions regarding this plugin. | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 251 | 5 | 210 | 10 | +| 252 | 5 | 211 | 11 | ## Server diff --git a/api_docs/kbn_test_jest_helpers.mdx b/api_docs/kbn_test_jest_helpers.mdx index e5a7fbdfff162..7d52dc054c9e4 100644 --- a/api_docs/kbn_test_jest_helpers.mdx +++ b/api_docs/kbn_test_jest_helpers.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-test-jest-helpers title: "@kbn/test-jest-helpers" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/test-jest-helpers plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/test-jest-helpers'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_tooling_log.mdx b/api_docs/kbn_tooling_log.mdx index f5328706fcf4b..2ab7c2e09048d 100644 --- a/api_docs/kbn_tooling_log.mdx +++ b/api_docs/kbn_tooling_log.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-tooling-log title: "@kbn/tooling-log" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/tooling-log plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/tooling-log'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_type_summarizer.mdx b/api_docs/kbn_type_summarizer.mdx index f243d4dc40658..bdea1cff0e372 100644 --- a/api_docs/kbn_type_summarizer.mdx +++ b/api_docs/kbn_type_summarizer.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-type-summarizer title: "@kbn/type-summarizer" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/type-summarizer plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/type-summarizer'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_type_summarizer_core.mdx b/api_docs/kbn_type_summarizer_core.mdx index 82bdca5e9d8b2..b1b9ead231e46 100644 --- a/api_docs/kbn_type_summarizer_core.mdx +++ b/api_docs/kbn_type_summarizer_core.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-type-summarizer-core title: "@kbn/type-summarizer-core" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/type-summarizer-core plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/type-summarizer-core'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_typed_react_router_config.mdx b/api_docs/kbn_typed_react_router_config.mdx index 3bb61421b625d..59448572ff829 100644 --- a/api_docs/kbn_typed_react_router_config.mdx +++ b/api_docs/kbn_typed_react_router_config.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-typed-react-router-config title: "@kbn/typed-react-router-config" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/typed-react-router-config plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/typed-react-router-config'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_ui_theme.mdx b/api_docs/kbn_ui_theme.mdx index 1b007f581dd8f..855b1423815ef 100644 --- a/api_docs/kbn_ui_theme.mdx +++ b/api_docs/kbn_ui_theme.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-ui-theme title: "@kbn/ui-theme" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/ui-theme plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/ui-theme'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_utility_types.mdx b/api_docs/kbn_utility_types.mdx index 6464c4216069e..d4061ca811b7e 100644 --- a/api_docs/kbn_utility_types.mdx +++ b/api_docs/kbn_utility_types.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-utility-types title: "@kbn/utility-types" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/utility-types plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/utility-types'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_utility_types_jest.mdx b/api_docs/kbn_utility_types_jest.mdx index f1ca30178f685..3fb921d16e6bb 100644 --- a/api_docs/kbn_utility_types_jest.mdx +++ b/api_docs/kbn_utility_types_jest.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-utility-types-jest title: "@kbn/utility-types-jest" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/utility-types-jest plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/utility-types-jest'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kbn_utils.mdx b/api_docs/kbn_utils.mdx index 66520bf1db066..57327df0012ce 100644 --- a/api_docs/kbn_utils.mdx +++ b/api_docs/kbn_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kbn-utils title: "@kbn/utils" image: https://source.unsplash.com/400x175/?github summary: API docs for the @kbn/utils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', '@kbn/utils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kibana_overview.mdx b/api_docs/kibana_overview.mdx index ca0fd397bc94c..893bd46e05684 100644 --- a/api_docs/kibana_overview.mdx +++ b/api_docs/kibana_overview.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kibanaOverview title: "kibanaOverview" image: https://source.unsplash.com/400x175/?github summary: API docs for the kibanaOverview plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'kibanaOverview'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kibana_react.devdocs.json b/api_docs/kibana_react.devdocs.json index 921e088a13418..0f34d3ce4eb49 100644 --- a/api_docs/kibana_react.devdocs.json +++ b/api_docs/kibana_react.devdocs.json @@ -1114,15 +1114,15 @@ }, { "plugin": "enterpriseSearch", - "path": "x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/product_selector/product_selector.tsx" + "path": "x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx" }, { "plugin": "enterpriseSearch", - "path": "x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/product_selector/product_selector.tsx" + "path": "x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx" }, { "plugin": "enterpriseSearch", - "path": "x-pack/plugins/enterprise_search/public/applications/enterprise_search_overview/components/product_selector/product_selector.tsx" + "path": "x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx" }, { "plugin": "enterpriseSearch", @@ -1136,18 +1136,6 @@ "plugin": "enterpriseSearch", "path": "x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/error_connecting/error_connecting.tsx" }, - { - "plugin": "enterpriseSearch", - "path": "x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx" - }, - { - "plugin": "enterpriseSearch", - "path": "x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx" - }, - { - "plugin": "enterpriseSearch", - "path": "x-pack/plugins/enterprise_search/public/applications/shared/layout/page_template.tsx" - }, { "plugin": "enterpriseSearch", "path": "x-pack/plugins/enterprise_search/public/applications/app_search/components/error_connecting/error_connecting.tsx" @@ -4391,13 +4379,7 @@ " | undefined; fatalErrors?: ", "FatalErrorsSetup", " | undefined; deprecations?: ", - { - "pluginId": "core", - "scope": "public", - "docId": "kibCorePluginApi", - "section": "def-public.DeprecationsServiceStart", - "text": "DeprecationsServiceStart" - }, + "DeprecationsServiceStart", " | undefined; theme?: ", "ThemeServiceStart", " | undefined; injectedMetadata?: ", diff --git a/api_docs/kibana_react.mdx b/api_docs/kibana_react.mdx index 3c4b6ed0309fc..52f3d687d2aa2 100644 --- a/api_docs/kibana_react.mdx +++ b/api_docs/kibana_react.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kibanaReact title: "kibanaReact" image: https://source.unsplash.com/400x175/?github summary: API docs for the kibanaReact plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'kibanaReact'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kibana_utils.mdx b/api_docs/kibana_utils.mdx index e57d0e2d3b29e..7e229a785ea75 100644 --- a/api_docs/kibana_utils.mdx +++ b/api_docs/kibana_utils.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kibanaUtils title: "kibanaUtils" image: https://source.unsplash.com/400x175/?github summary: API docs for the kibanaUtils plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'kibanaUtils'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/kubernetes_security.mdx b/api_docs/kubernetes_security.mdx index 736bf513869f4..4925d77903fe7 100644 --- a/api_docs/kubernetes_security.mdx +++ b/api_docs/kubernetes_security.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/kubernetesSecurity title: "kubernetesSecurity" image: https://source.unsplash.com/400x175/?github summary: API docs for the kubernetesSecurity plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'kubernetesSecurity'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/lens.devdocs.json b/api_docs/lens.devdocs.json index 990dbbafbda78..406a04922c602 100644 --- a/api_docs/lens.devdocs.json +++ b/api_docs/lens.devdocs.json @@ -1007,10 +1007,10 @@ }, { "parentPluginId": "lens", - "id": "def-public.DataLayerArgs.hide", + "id": "def-public.DataLayerArgs.simpleView", "type": "CompoundType", "tags": [], - "label": "hide", + "label": "simpleView", "description": [], "signature": [ "boolean | undefined" @@ -5402,10 +5402,10 @@ }, { "parentPluginId": "lens", - "id": "def-public.XYAnnotationLayerConfig.hide", + "id": "def-public.XYAnnotationLayerConfig.simpleView", "type": "CompoundType", "tags": [], - "label": "hide", + "label": "simpleView", "description": [], "signature": [ "boolean | undefined" @@ -5889,10 +5889,10 @@ }, { "parentPluginId": "lens", - "id": "def-public.XYDataLayerConfig.hide", + "id": "def-public.XYDataLayerConfig.simpleView", "type": "CompoundType", "tags": [], - "label": "hide", + "label": "simpleView", "description": [], "signature": [ "boolean | undefined" @@ -9944,7 +9944,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined) => ", { @@ -9974,7 +9974,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined" ], diff --git a/api_docs/lens.mdx b/api_docs/lens.mdx index 1c49503e62394..c85080551c808 100644 --- a/api_docs/lens.mdx +++ b/api_docs/lens.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/lens title: "lens" image: https://source.unsplash.com/400x175/?github summary: API docs for the lens plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'lens'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/license_api_guard.mdx b/api_docs/license_api_guard.mdx index 331b37523bb0b..354f9509d85b8 100644 --- a/api_docs/license_api_guard.mdx +++ b/api_docs/license_api_guard.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/licenseApiGuard title: "licenseApiGuard" image: https://source.unsplash.com/400x175/?github summary: API docs for the licenseApiGuard plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'licenseApiGuard'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/license_management.mdx b/api_docs/license_management.mdx index 7d70dd7118c5b..7f2c726743dec 100644 --- a/api_docs/license_management.mdx +++ b/api_docs/license_management.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/licenseManagement title: "licenseManagement" image: https://source.unsplash.com/400x175/?github summary: API docs for the licenseManagement plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'licenseManagement'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/licensing.mdx b/api_docs/licensing.mdx index dce399078a361..1b60079a59977 100644 --- a/api_docs/licensing.mdx +++ b/api_docs/licensing.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/licensing title: "licensing" image: https://source.unsplash.com/400x175/?github summary: API docs for the licensing plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'licensing'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/lists.mdx b/api_docs/lists.mdx index c5bf01ce7e4e4..14e1fd3a97cb9 100644 --- a/api_docs/lists.mdx +++ b/api_docs/lists.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/lists title: "lists" image: https://source.unsplash.com/400x175/?github summary: API docs for the lists plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'lists'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/management.mdx b/api_docs/management.mdx index d0fe3a0d4d7c6..9d5cc8eb94663 100644 --- a/api_docs/management.mdx +++ b/api_docs/management.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/management title: "management" image: https://source.unsplash.com/400x175/?github summary: API docs for the management plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'management'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/maps.devdocs.json b/api_docs/maps.devdocs.json index f25dab745052a..4732fd45134ad 100644 --- a/api_docs/maps.devdocs.json +++ b/api_docs/maps.devdocs.json @@ -644,6 +644,21 @@ "children": [], "returnComment": [] }, + { + "parentPluginId": "maps", + "id": "def-public.MapEmbeddable._getIsFilterByMapExtent", + "type": "Function", + "tags": [], + "label": "_getIsFilterByMapExtent", + "description": [], + "signature": [ + "() => boolean" + ], + "path": "x-pack/plugins/maps/public/embeddable/map_embeddable.tsx", + "deprecated": false, + "children": [], + "returnComment": [] + }, { "parentPluginId": "maps", "id": "def-public.MapEmbeddable._gotoSynchronizedLocation", @@ -1093,25 +1108,25 @@ }, { "parentPluginId": "maps", - "id": "def-public.MapEmbeddable.setMapExtentFilter", + "id": "def-public.MapEmbeddable._setMapExtentFilter", "type": "Function", "tags": [], - "label": "setMapExtentFilter", + "label": "_setMapExtentFilter", "description": [], "signature": [ - "() => void" + "(() => void) & _.Cancelable" ], "path": "x-pack/plugins/maps/public/embeddable/map_embeddable.tsx", "deprecated": false, - "children": [], - "returnComment": [] + "returnComment": [], + "children": [] }, { "parentPluginId": "maps", - "id": "def-public.MapEmbeddable.clearMapExtentFilter", + "id": "def-public.MapEmbeddable._clearMapExtentFilter", "type": "Function", "tags": [], - "label": "clearMapExtentFilter", + "label": "_clearMapExtentFilter", "description": [], "signature": [ "() => void" diff --git a/api_docs/maps.mdx b/api_docs/maps.mdx index c3af9f2b2b8ce..5533f216bc311 100644 --- a/api_docs/maps.mdx +++ b/api_docs/maps.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/maps title: "maps" image: https://source.unsplash.com/400x175/?github summary: API docs for the maps plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'maps'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [GIS](https://github.com/orgs/elastic/teams/kibana-gis) for questions re | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 249 | 0 | 248 | 24 | +| 250 | 0 | 249 | 24 | ## Client diff --git a/api_docs/maps_ems.mdx b/api_docs/maps_ems.mdx index 8d4fa80184619..b2f1b093fe708 100644 --- a/api_docs/maps_ems.mdx +++ b/api_docs/maps_ems.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/mapsEms title: "mapsEms" image: https://source.unsplash.com/400x175/?github summary: API docs for the mapsEms plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'mapsEms'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/ml.mdx b/api_docs/ml.mdx index 7cf5e6f08934f..b8c74a83791fa 100644 --- a/api_docs/ml.mdx +++ b/api_docs/ml.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/ml title: "ml" image: https://source.unsplash.com/400x175/?github summary: API docs for the ml plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'ml'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/monitoring.mdx b/api_docs/monitoring.mdx index 9a96f5fb71459..378819242c8ba 100644 --- a/api_docs/monitoring.mdx +++ b/api_docs/monitoring.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/monitoring title: "monitoring" image: https://source.unsplash.com/400x175/?github summary: API docs for the monitoring plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'monitoring'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/monitoring_collection.mdx b/api_docs/monitoring_collection.mdx index dd904b036cb13..19e39fc9ab761 100644 --- a/api_docs/monitoring_collection.mdx +++ b/api_docs/monitoring_collection.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/monitoringCollection title: "monitoringCollection" image: https://source.unsplash.com/400x175/?github summary: API docs for the monitoringCollection plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'monitoringCollection'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/navigation.mdx b/api_docs/navigation.mdx index c34729aae4333..8d158347118e6 100644 --- a/api_docs/navigation.mdx +++ b/api_docs/navigation.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/navigation title: "navigation" image: https://source.unsplash.com/400x175/?github summary: API docs for the navigation plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'navigation'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/newsfeed.mdx b/api_docs/newsfeed.mdx index 9fd49bf331ce3..1b26ead546787 100644 --- a/api_docs/newsfeed.mdx +++ b/api_docs/newsfeed.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/newsfeed title: "newsfeed" image: https://source.unsplash.com/400x175/?github summary: API docs for the newsfeed plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'newsfeed'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/observability.devdocs.json b/api_docs/observability.devdocs.json index b7ed67de04c43..58534e319fad7 100644 --- a/api_docs/observability.devdocs.json +++ b/api_docs/observability.devdocs.json @@ -205,7 +205,7 @@ "section": "def-public.ObservabilityRuleTypeFormatter", "text": "ObservabilityRuleTypeFormatter" }, - " | undefined; list: () => string[]; } & { getFormatter: () => () => string; registerFormatter: () => void; }" + " | undefined; list: () => string[]; } & { getFormatter: () => () => string; registerFormatter: () => void; list: () => string[]; }" ], "path": "x-pack/plugins/observability/public/rules/observability_rule_type_registry_mock.ts", "deprecated": false, @@ -3364,60 +3364,99 @@ }, { "parentPluginId": "observability", - "id": "def-public.ObservabilityPublicPluginsStart.features", + "id": "def-public.ObservabilityPublicPluginsStart.sharedUX", "type": "Object", "tags": [], - "label": "features", + "label": "sharedUX", "description": [], "signature": [ - "{ getFeatures: () => Promise<", { - "pluginId": "features", - "scope": "common", - "docId": "kibFeaturesPluginApi", - "section": "def-common.KibanaFeature", - "text": "KibanaFeature" - }, - "[]>; }" + "pluginId": "sharedUX", + "scope": "public", + "docId": "kibSharedUXPluginApi", + "section": "def-public.SharedUXPluginStart", + "text": "SharedUXPluginStart" + } ], "path": "x-pack/plugins/observability/public/plugin.ts", "deprecated": false }, { "parentPluginId": "observability", - "id": "def-public.ObservabilityPublicPluginsStart.kibanaFeatures", - "type": "Array", + "id": "def-public.ObservabilityPublicPluginsStart.ruleTypeRegistry", + "type": "Object", "tags": [], - "label": "kibanaFeatures", + "label": "ruleTypeRegistry", "description": [], "signature": [ + "{ list: () => ", { - "pluginId": "features", + "pluginId": "triggersActionsUi", + "scope": "public", + "docId": "kibTriggersActionsUiPluginApi", + "section": "def-public.RuleTypeModel", + "text": "RuleTypeModel" + }, + "<", + { + "pluginId": "alerting", "scope": "common", - "docId": "kibFeaturesPluginApi", - "section": "def-common.KibanaFeature", - "text": "KibanaFeature" + "docId": "kibAlertingPluginApi", + "section": "def-common.RuleTypeParams", + "text": "RuleTypeParams" }, - "[]" + ">[]; get: (id: string) => ", + { + "pluginId": "triggersActionsUi", + "scope": "public", + "docId": "kibTriggersActionsUiPluginApi", + "section": "def-public.RuleTypeModel", + "text": "RuleTypeModel" + }, + "<", + { + "pluginId": "alerting", + "scope": "common", + "docId": "kibAlertingPluginApi", + "section": "def-common.RuleTypeParams", + "text": "RuleTypeParams" + }, + ">; register: (objectType: ", + { + "pluginId": "triggersActionsUi", + "scope": "public", + "docId": "kibTriggersActionsUiPluginApi", + "section": "def-public.RuleTypeModel", + "text": "RuleTypeModel" + }, + "<", + { + "pluginId": "alerting", + "scope": "common", + "docId": "kibAlertingPluginApi", + "section": "def-common.RuleTypeParams", + "text": "RuleTypeParams" + }, + ">) => void; has: (id: string) => boolean; }" ], "path": "x-pack/plugins/observability/public/plugin.ts", "deprecated": false }, { "parentPluginId": "observability", - "id": "def-public.ObservabilityPublicPluginsStart.sharedUX", + "id": "def-public.ObservabilityPublicPluginsStart.actionTypeRegistry", "type": "Object", "tags": [], - "label": "sharedUX", + "label": "actionTypeRegistry", "description": [], "signature": [ - { - "pluginId": "sharedUX", - "scope": "public", - "docId": "kibSharedUXPluginApi", - "section": "def-public.SharedUXPluginStart", - "text": "SharedUXPluginStart" - } + "{ list: () => ", + "ActionTypeModel", + "[]; get: (id: string) => ", + "ActionTypeModel", + "; register: (objectType: ", + "ActionTypeModel", + ") => void; has: (id: string) => boolean; }" ], "path": "x-pack/plugins/observability/public/plugin.ts", "deprecated": false diff --git a/api_docs/observability.mdx b/api_docs/observability.mdx index 71cfee396b9d1..befddb468d6e4 100644 --- a/api_docs/observability.mdx +++ b/api_docs/observability.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/observability title: "observability" image: https://source.unsplash.com/400x175/?github summary: API docs for the observability plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'observability'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/osquery.mdx b/api_docs/osquery.mdx index 52aac69572b83..b56428d38b910 100644 --- a/api_docs/osquery.mdx +++ b/api_docs/osquery.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/osquery title: "osquery" image: https://source.unsplash.com/400x175/?github summary: API docs for the osquery plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'osquery'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/plugin_directory.mdx b/api_docs/plugin_directory.mdx index 80e714e48ffa2..f42c92bf244c1 100644 --- a/api_docs/plugin_directory.mdx +++ b/api_docs/plugin_directory.mdx @@ -3,7 +3,7 @@ id: kibDevDocsPluginDirectory slug: /kibana-dev-docs/api-meta/plugin-api-directory title: Directory summary: Directory of public APIs available through plugins or packages. -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -12,13 +12,13 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | Count | Plugins or Packages with a
public API | Number of teams | |--------------|----------|------------------------| -| 335 | 276 | 36 | +| 345 | 285 | 36 | ### Public API health stats | API Count | Any Count | Missing comments | Missing exports | |--------------|----------|-----------------|--------| -| 27414 | 172 | 19519 | 1433 | +| 27567 | 175 | 19645 | 1459 | ## Plugin Directory @@ -26,7 +26,7 @@ warning: This document is auto-generated and is meant to be viewed inside our ex |--------------|----------------|-----------|--------------|----------|---------------|--------| | | [Response Ops](https://github.com/orgs/elastic/teams/response-ops) | - | 241 | 0 | 236 | 19 | | | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 23 | 0 | 19 | 1 | -| | [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) | AIOps plugin maintained by ML team. | 12 | 0 | 0 | 0 | +| | [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) | AIOps plugin maintained by ML team. | 9 | 0 | 0 | 1 | | | [Response Ops](https://github.com/orgs/elastic/teams/response-ops) | - | 365 | 0 | 356 | 20 | | | [APM UI](https://github.com/orgs/elastic/teams/apm-ui) | The user interface for Elastic APM | 40 | 0 | 40 | 55 | | | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 9 | 0 | 9 | 0 | @@ -38,14 +38,14 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | | [Cloud Security Posture](https://github.com/orgs/elastic/teams/cloud-posture-security) | The cloud security posture plugin | 6 | 0 | 6 | 0 | | | [Stack Management](https://github.com/orgs/elastic/teams/kibana-stack-management) | - | 13 | 0 | 13 | 1 | | | [Kibana Presentation](https://github.com/orgs/elastic/teams/kibana-presentation) | The Controls Plugin contains embeddable components intended to create a simple query interface for end users, and a powerful editing suite that allows dashboard authors to build controls | 206 | 0 | 198 | 7 | -| | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 2489 | 9 | 746 | 25 | +| | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 2472 | 6 | 724 | 22 | | crossClusterReplication | [Stack Management](https://github.com/orgs/elastic/teams/kibana-stack-management) | - | 0 | 0 | 0 | 0 | | | [Fleet](https://github.com/orgs/elastic/teams/fleet) | Add custom data integrations so they can be displayed in the Fleet integrations app | 102 | 0 | 83 | 1 | | | [Kibana Presentation](https://github.com/orgs/elastic/teams/kibana-presentation) | Adds the Dashboard app to Kibana | 143 | 0 | 141 | 12 | | | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | - | 52 | 0 | 51 | 0 | | | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Data services are useful for searching and querying data from Elasticsearch. Helpful utilities include: a re-usable react query bar, KQL autocomplete, async search, Data Views (Index Patterns) and field formatters. | 3075 | 34 | 2402 | 21 | -| | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | This plugin provides the ability to create data views via a modal flyout from any kibana app | 14 | 0 | 7 | 0 | -| | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Reusable data view field editor across Kibana | 42 | 0 | 37 | 3 | +| | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | This plugin provides the ability to create data views via a modal flyout from any kibana app | 15 | 0 | 7 | 0 | +| | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Reusable data view field editor across Kibana | 41 | 0 | 36 | 3 | | | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Data view management app | 2 | 0 | 2 | 0 | | | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Data services are useful for searching and querying data from Elasticsearch. Helpful utilities include: a re-usable react query bar, KQL autocomplete, async search, Data Views (Index Patterns) and field formatters. | 938 | 1 | 199 | 1 | | | [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) | The Data Visualizer tools help you understand your data, by analyzing the metrics and fields in a log file or an existing Elasticsearch index. | 28 | 3 | 24 | 1 | @@ -76,7 +76,7 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 222 | 0 | 95 | 2 | | | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Index pattern fields and ambiguous values formatters | 288 | 5 | 249 | 3 | | | [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) | The file upload plugin contains components and services for uploading a file, analyzing its data, and then importing the data into an Elasticsearch index. Supported file types include CSV, TSV, newline-delimited JSON and GeoJSON. | 62 | 0 | 62 | 2 | -| | [Fleet](https://github.com/orgs/elastic/teams/fleet) | - | 1522 | 8 | 1390 | 10 | +| | [Fleet](https://github.com/orgs/elastic/teams/fleet) | - | 1525 | 8 | 1393 | 10 | | | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 68 | 0 | 14 | 5 | | globalSearchBar | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 0 | 0 | 0 | 0 | | globalSearchProviders | [Kibana Core](https://github.com/orgs/elastic/teams/kibana-core) | - | 0 | 0 | 0 | 0 | @@ -102,7 +102,7 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | | [Security detections response](https://github.com/orgs/elastic/teams/security-detections-response) | - | 198 | 0 | 90 | 49 | | logstash | [Logstash](https://github.com/orgs/elastic/teams/logstash) | - | 0 | 0 | 0 | 0 | | | [Vis Editors](https://github.com/orgs/elastic/teams/kibana-vis-editors) | - | 41 | 0 | 41 | 6 | -| | [GIS](https://github.com/orgs/elastic/teams/kibana-gis) | - | 249 | 0 | 248 | 24 | +| | [GIS](https://github.com/orgs/elastic/teams/kibana-gis) | - | 250 | 0 | 249 | 24 | | | [GIS](https://github.com/orgs/elastic/teams/kibana-gis) | - | 67 | 0 | 67 | 0 | | | [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) | This plugin provides access to the machine learning features provided by Elastic. | 251 | 10 | 78 | 31 | | | [Stack Monitoring](https://github.com/orgs/elastic/teams/stack-monitoring-ui) | - | 11 | 0 | 9 | 1 | @@ -142,7 +142,7 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | | [Security solution](https://github.com/orgs/elastic/teams/security-solution) | - | 447 | 1 | 342 | 32 | | | [Machine Learning UI](https://github.com/orgs/elastic/teams/ml-ui) | This plugin provides access to the transforms features provided by Elastic. Transforms enable you to convert existing Elasticsearch indices into summarized indices, which provide opportunities for new insights and analytics. | 4 | 0 | 4 | 1 | | translations | [Kibana Localization](https://github.com/orgs/elastic/teams/kibana-localization) | - | 0 | 0 | 0 | 0 | -| | [Response Ops](https://github.com/orgs/elastic/teams/response-ops) | - | 412 | 0 | 391 | 40 | +| | [Response Ops](https://github.com/orgs/elastic/teams/response-ops) | - | 407 | 0 | 386 | 42 | | | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Adds UI Actions service to Kibana | 130 | 0 | 91 | 11 | | | [App Services](https://github.com/orgs/elastic/teams/kibana-app-services) | Extends UI Actions plugin with more functionality | 205 | 0 | 142 | 9 | | | [Unified Search](https://github.com/orgs/elastic/teams/kibana-app-services) | Contains all the key functionality of Kibana's unified search experience.Contains all the key functionality of Kibana's unified search experience. | 82 | 2 | 78 | 13 | @@ -206,6 +206,10 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | | [Owner missing] | - | 7 | 0 | 7 | 0 | | | [Owner missing] | - | 3 | 0 | 3 | 0 | | | [Owner missing] | - | 15 | 0 | 13 | 0 | +| | [Owner missing] | - | 9 | 0 | 3 | 0 | +| | [Owner missing] | - | 6 | 0 | 6 | 0 | +| | [Owner missing] | - | 4 | 0 | 4 | 0 | +| | [Owner missing] | - | 17 | 0 | 9 | 0 | | | [Owner missing] | - | 4 | 0 | 4 | 0 | | | [Owner missing] | - | 4 | 0 | 4 | 0 | | | [Owner missing] | - | 5 | 0 | 2 | 0 | @@ -225,7 +229,12 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | | [Owner missing] | - | 10 | 0 | 10 | 0 | | | [Owner missing] | - | 16 | 0 | 16 | 0 | | | [Owner missing] | - | 4 | 0 | 0 | 0 | +| | [Owner missing] | - | 10 | 1 | 10 | 0 | +| | [Owner missing] | - | 25 | 5 | 25 | 1 | +| | [Owner missing] | - | 7 | 0 | 7 | 1 | | | [Owner missing] | - | 392 | 1 | 154 | 0 | +| | [Owner missing] | - | 54 | 0 | 48 | 2 | +| | [Owner missing] | - | 41 | 0 | 37 | 0 | | | [Owner missing] | - | 4 | 0 | 2 | 0 | | | [Owner missing] | - | 3 | 0 | 3 | 0 | | | [Owner missing] | - | 8 | 2 | 6 | 0 | @@ -314,7 +323,7 @@ warning: This document is auto-generated and is meant to be viewed inside our ex | | [Owner missing] | - | 4 | 0 | 2 | 0 | | | Operations | - | 38 | 2 | 21 | 0 | | | [Owner missing] | - | 2 | 0 | 2 | 0 | -| | Operations | - | 251 | 5 | 210 | 10 | +| | Operations | - | 252 | 5 | 211 | 11 | | | [Owner missing] | - | 135 | 8 | 103 | 2 | | | [Owner missing] | - | 72 | 0 | 55 | 0 | | | [Owner missing] | - | 8 | 0 | 2 | 0 | diff --git a/api_docs/presentation_util.mdx b/api_docs/presentation_util.mdx index c7b08aab4bd73..04d1978da0585 100644 --- a/api_docs/presentation_util.mdx +++ b/api_docs/presentation_util.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/presentationUtil title: "presentationUtil" image: https://source.unsplash.com/400x175/?github summary: API docs for the presentationUtil plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'presentationUtil'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/remote_clusters.mdx b/api_docs/remote_clusters.mdx index 59c7c219a1602..234251ac33a92 100644 --- a/api_docs/remote_clusters.mdx +++ b/api_docs/remote_clusters.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/remoteClusters title: "remoteClusters" image: https://source.unsplash.com/400x175/?github summary: API docs for the remoteClusters plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'remoteClusters'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/reporting.mdx b/api_docs/reporting.mdx index 8d73fbaa1f36a..0e0dfa097fa0a 100644 --- a/api_docs/reporting.mdx +++ b/api_docs/reporting.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/reporting title: "reporting" image: https://source.unsplash.com/400x175/?github summary: API docs for the reporting plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'reporting'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/rollup.mdx b/api_docs/rollup.mdx index deb418b833fe3..a75cacfcc1572 100644 --- a/api_docs/rollup.mdx +++ b/api_docs/rollup.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/rollup title: "rollup" image: https://source.unsplash.com/400x175/?github summary: API docs for the rollup plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'rollup'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/rule_registry.mdx b/api_docs/rule_registry.mdx index db25b33fb89f9..d6e20d8034ea6 100644 --- a/api_docs/rule_registry.mdx +++ b/api_docs/rule_registry.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/ruleRegistry title: "ruleRegistry" image: https://source.unsplash.com/400x175/?github summary: API docs for the ruleRegistry plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'ruleRegistry'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/runtime_fields.mdx b/api_docs/runtime_fields.mdx index e0a004928b4b2..22edf2e545f0e 100644 --- a/api_docs/runtime_fields.mdx +++ b/api_docs/runtime_fields.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/runtimeFields title: "runtimeFields" image: https://source.unsplash.com/400x175/?github summary: API docs for the runtimeFields plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'runtimeFields'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/saved_objects.mdx b/api_docs/saved_objects.mdx index 2792e2107d074..89d4585144a26 100644 --- a/api_docs/saved_objects.mdx +++ b/api_docs/saved_objects.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/savedObjects title: "savedObjects" image: https://source.unsplash.com/400x175/?github summary: API docs for the savedObjects plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'savedObjects'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/saved_objects_management.mdx b/api_docs/saved_objects_management.mdx index 4d25d3bf28f50..fd466c3c3a99b 100644 --- a/api_docs/saved_objects_management.mdx +++ b/api_docs/saved_objects_management.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/savedObjectsManagement title: "savedObjectsManagement" image: https://source.unsplash.com/400x175/?github summary: API docs for the savedObjectsManagement plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'savedObjectsManagement'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/saved_objects_tagging.mdx b/api_docs/saved_objects_tagging.mdx index 5b61e650b0976..d5ddfca5055d9 100644 --- a/api_docs/saved_objects_tagging.mdx +++ b/api_docs/saved_objects_tagging.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/savedObjectsTagging title: "savedObjectsTagging" image: https://source.unsplash.com/400x175/?github summary: API docs for the savedObjectsTagging plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'savedObjectsTagging'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/saved_objects_tagging_oss.mdx b/api_docs/saved_objects_tagging_oss.mdx index 8f7e57b1e2718..e0aead29fe244 100644 --- a/api_docs/saved_objects_tagging_oss.mdx +++ b/api_docs/saved_objects_tagging_oss.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/savedObjectsTaggingOss title: "savedObjectsTaggingOss" image: https://source.unsplash.com/400x175/?github summary: API docs for the savedObjectsTaggingOss plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'savedObjectsTaggingOss'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/screenshot_mode.mdx b/api_docs/screenshot_mode.mdx index 7b042ea1f93c6..8525bfa3cc6ca 100644 --- a/api_docs/screenshot_mode.mdx +++ b/api_docs/screenshot_mode.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/screenshotMode title: "screenshotMode" image: https://source.unsplash.com/400x175/?github summary: API docs for the screenshotMode plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'screenshotMode'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/screenshotting.mdx b/api_docs/screenshotting.mdx index 51a7e1a61919f..346eb39633f9b 100644 --- a/api_docs/screenshotting.mdx +++ b/api_docs/screenshotting.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/screenshotting title: "screenshotting" image: https://source.unsplash.com/400x175/?github summary: API docs for the screenshotting plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'screenshotting'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/security.devdocs.json b/api_docs/security.devdocs.json index 17da37f5902c4..f48eba18053c2 100644 --- a/api_docs/security.devdocs.json +++ b/api_docs/security.devdocs.json @@ -2401,13 +2401,7 @@ "label": "errors", "description": [], "signature": [ - { - "pluginId": "core", - "scope": "server", - "docId": "kibCorePluginApi", - "section": "def-server.DeprecationsDetails", - "text": "DeprecationsDetails" - }, + "DeprecationsDetails", "[] | undefined" ], "path": "x-pack/plugins/security/common/model/deprecations.ts", diff --git a/api_docs/security.mdx b/api_docs/security.mdx index 434d136388f5e..4d47b746b500c 100644 --- a/api_docs/security.mdx +++ b/api_docs/security.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/security title: "security" image: https://source.unsplash.com/400x175/?github summary: API docs for the security plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'security'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/security_solution.mdx b/api_docs/security_solution.mdx index d1d77eae3d5fc..31aaf47e64dfd 100644 --- a/api_docs/security_solution.mdx +++ b/api_docs/security_solution.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/securitySolution title: "securitySolution" image: https://source.unsplash.com/400x175/?github summary: API docs for the securitySolution plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'securitySolution'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/session_view.mdx b/api_docs/session_view.mdx index da2c2cf09a878..5541e10a3b3bb 100644 --- a/api_docs/session_view.mdx +++ b/api_docs/session_view.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/sessionView title: "sessionView" image: https://source.unsplash.com/400x175/?github summary: API docs for the sessionView plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'sessionView'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/share.mdx b/api_docs/share.mdx index b6a02d17aecc4..feea0969781ec 100644 --- a/api_docs/share.mdx +++ b/api_docs/share.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/share title: "share" image: https://source.unsplash.com/400x175/?github summary: API docs for the share plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'share'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/shared_u_x.mdx b/api_docs/shared_u_x.mdx index de326e69e0fe2..6ae95456986e7 100644 --- a/api_docs/shared_u_x.mdx +++ b/api_docs/shared_u_x.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/sharedUX title: "sharedUX" image: https://source.unsplash.com/400x175/?github summary: API docs for the sharedUX plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'sharedUX'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/snapshot_restore.mdx b/api_docs/snapshot_restore.mdx index 2d533df972c65..8e903897b9a35 100644 --- a/api_docs/snapshot_restore.mdx +++ b/api_docs/snapshot_restore.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/snapshotRestore title: "snapshotRestore" image: https://source.unsplash.com/400x175/?github summary: API docs for the snapshotRestore plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'snapshotRestore'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/spaces.mdx b/api_docs/spaces.mdx index 2082447ea3258..7ce756b9afaa2 100644 --- a/api_docs/spaces.mdx +++ b/api_docs/spaces.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/spaces title: "spaces" image: https://source.unsplash.com/400x175/?github summary: API docs for the spaces plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'spaces'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/stack_alerts.mdx b/api_docs/stack_alerts.mdx index e5cce413d231b..ae5f9513f9769 100644 --- a/api_docs/stack_alerts.mdx +++ b/api_docs/stack_alerts.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/stackAlerts title: "stackAlerts" image: https://source.unsplash.com/400x175/?github summary: API docs for the stackAlerts plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'stackAlerts'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/task_manager.mdx b/api_docs/task_manager.mdx index 2ca6c69bacca9..84a68efa150be 100644 --- a/api_docs/task_manager.mdx +++ b/api_docs/task_manager.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/taskManager title: "taskManager" image: https://source.unsplash.com/400x175/?github summary: API docs for the taskManager plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'taskManager'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/telemetry.mdx b/api_docs/telemetry.mdx index b0a927943f987..a96031bcd465d 100644 --- a/api_docs/telemetry.mdx +++ b/api_docs/telemetry.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/telemetry title: "telemetry" image: https://source.unsplash.com/400x175/?github summary: API docs for the telemetry plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'telemetry'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/telemetry_collection_manager.mdx b/api_docs/telemetry_collection_manager.mdx index 5ed1647e3fd4e..ff5555bf4f259 100644 --- a/api_docs/telemetry_collection_manager.mdx +++ b/api_docs/telemetry_collection_manager.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/telemetryCollectionManager title: "telemetryCollectionManager" image: https://source.unsplash.com/400x175/?github summary: API docs for the telemetryCollectionManager plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'telemetryCollectionManager'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/telemetry_collection_xpack.mdx b/api_docs/telemetry_collection_xpack.mdx index 421ef5b38c9a8..e3c006af01c2c 100644 --- a/api_docs/telemetry_collection_xpack.mdx +++ b/api_docs/telemetry_collection_xpack.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/telemetryCollectionXpack title: "telemetryCollectionXpack" image: https://source.unsplash.com/400x175/?github summary: API docs for the telemetryCollectionXpack plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'telemetryCollectionXpack'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/telemetry_management_section.mdx b/api_docs/telemetry_management_section.mdx index 3d33d343a8620..3a039df3de72d 100644 --- a/api_docs/telemetry_management_section.mdx +++ b/api_docs/telemetry_management_section.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/telemetryManagementSection title: "telemetryManagementSection" image: https://source.unsplash.com/400x175/?github summary: API docs for the telemetryManagementSection plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'telemetryManagementSection'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/timelines.mdx b/api_docs/timelines.mdx index c384f9da142fc..1d765a9f54761 100644 --- a/api_docs/timelines.mdx +++ b/api_docs/timelines.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/timelines title: "timelines" image: https://source.unsplash.com/400x175/?github summary: API docs for the timelines plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'timelines'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/transform.mdx b/api_docs/transform.mdx index a8e0315881b2d..52625666bf734 100644 --- a/api_docs/transform.mdx +++ b/api_docs/transform.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/transform title: "transform" image: https://source.unsplash.com/400x175/?github summary: API docs for the transform plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'transform'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/triggers_actions_ui.devdocs.json b/api_docs/triggers_actions_ui.devdocs.json index 21cdbb34c1e45..308ee72116682 100644 --- a/api_docs/triggers_actions_ui.devdocs.json +++ b/api_docs/triggers_actions_ui.devdocs.json @@ -1647,7 +1647,7 @@ "label": "useLoadRuleTypes", "description": [], "signature": [ - "({ filteredSolutions }: RuleTypesProps) => { ruleTypes: ", + "({ filteredRuleTypes }: RuleTypesProps) => { ruleTypes: ", { "pluginId": "triggersActionsUi", "scope": "public", @@ -1656,13 +1656,7 @@ "text": "RuleType" }, "[]; error: string | null; ruleTypeIndex: ", - { - "pluginId": "triggersActionsUi", - "scope": "public", - "docId": "kibTriggersActionsUiPluginApi", - "section": "def-public.RuleTypeIndex", - "text": "RuleTypeIndex" - }, + "RuleTypeIndex", "; }" ], "path": "x-pack/plugins/triggers_actions_ui/public/application/hooks/use_load_rule_types.ts", @@ -1673,7 +1667,7 @@ "id": "def-public.useLoadRuleTypes.$1", "type": "Object", "tags": [], - "label": "{ filteredSolutions }", + "label": "{ filteredRuleTypes }", "description": [], "signature": [ "RuleTypesProps" @@ -2906,105 +2900,16 @@ "deprecated": false, "children": [], "returnComment": [] - } - ], - "initialIsOpen": false - }, - { - "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTableItem", - "type": "Interface", - "tags": [], - "label": "RuleTableItem", - "description": [], - "signature": [ - { - "pluginId": "triggersActionsUi", - "scope": "public", - "docId": "kibTriggersActionsUiPluginApi", - "section": "def-public.RuleTableItem", - "text": "RuleTableItem" - }, - " extends ", - { - "pluginId": "triggersActionsUi", - "scope": "public", - "docId": "kibTriggersActionsUiPluginApi", - "section": "def-public.Rule", - "text": "Rule" - }, - "<", - { - "pluginId": "alerting", - "scope": "common", - "docId": "kibAlertingPluginApi", - "section": "def-common.RuleTypeParams", - "text": "RuleTypeParams" - }, - ">" - ], - "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", - "deprecated": false, - "children": [ - { - "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTableItem.ruleType", - "type": "string", - "tags": [], - "label": "ruleType", - "description": [], - "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", - "deprecated": false - }, - { - "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTableItem.index", - "type": "number", - "tags": [], - "label": "index", - "description": [], - "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", - "deprecated": false - }, - { - "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTableItem.actionsCount", - "type": "number", - "tags": [], - "label": "actionsCount", - "description": [], - "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", - "deprecated": false - }, - { - "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTableItem.isEditable", - "type": "boolean", - "tags": [], - "label": "isEditable", - "description": [], - "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", - "deprecated": false }, { "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTableItem.enabledInLicense", - "type": "boolean", - "tags": [], - "label": "enabledInLicense", - "description": [], - "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", - "deprecated": false - }, - { - "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTableItem.showIntervalWarning", - "type": "CompoundType", + "id": "def-public.RuleDefinitionProps.filteredRuleTypes", + "type": "Array", "tags": [], - "label": "showIntervalWarning", + "label": "filteredRuleTypes", "description": [], "signature": [ - "boolean | undefined" + "string[] | undefined" ], "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", "deprecated": false @@ -4268,35 +4173,27 @@ }, { "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleStatus", + "id": "def-public.RulesListVisibleColumns", "type": "Type", "tags": [], - "label": "RuleStatus", + "label": "RulesListVisibleColumns", "description": [], "signature": [ - "\"disabled\" | \"enabled\" | \"snoozed\"" + "\"ruleName\" | \"ruleTags\" | \"ruleExecutionStatusLastDate\" | \"ruleSnoozeNotify\" | \"ruleScheduleInterval\" | \"ruleExecutionStatusLastDuration\" | \"ruleExecutionPercentile\" | \"ruleExecutionSuccessRatio\" | \"ruleExecutionStatus\" | \"ruleExecutionState\"" ], - "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", + "path": "x-pack/plugins/triggers_actions_ui/public/application/sections/rules_list/components/rules_list_column_selector.tsx", "deprecated": false, "initialIsOpen": false }, { "parentPluginId": "triggersActionsUi", - "id": "def-public.RuleTypeIndex", + "id": "def-public.RuleStatus", "type": "Type", "tags": [], - "label": "RuleTypeIndex", + "label": "RuleStatus", "description": [], "signature": [ - "Map>" + "\"disabled\" | \"enabled\" | \"snoozed\"" ], "path": "x-pack/plugins/triggers_actions_ui/public/types.ts", "deprecated": false, @@ -5772,30 +5669,28 @@ }, { "parentPluginId": "triggersActionsUi", - "id": "def-public.TriggersAndActionsUIPublicPluginStart.getRulesListNotifyBadge", + "id": "def-public.TriggersAndActionsUIPublicPluginStart.getRulesList", "type": "Function", "tags": [], - "label": "getRulesListNotifyBadge", + "label": "getRulesList", "description": [], "signature": [ "(props: ", - "RulesListNotifyBadgeProps", - ") => React.ReactElement<", - "RulesListNotifyBadgeProps", - ", string | React.JSXElementConstructor>" + "RulesListProps", + ") => React.ReactElement>" ], "path": "x-pack/plugins/triggers_actions_ui/public/plugin.ts", "deprecated": false, "children": [ { "parentPluginId": "triggersActionsUi", - "id": "def-public.TriggersAndActionsUIPublicPluginStart.getRulesListNotifyBadge.$1", + "id": "def-public.TriggersAndActionsUIPublicPluginStart.getRulesList.$1", "type": "Object", "tags": [], "label": "props", "description": [], "signature": [ - "RulesListNotifyBadgeProps" + "RulesListProps" ], "path": "x-pack/plugins/triggers_actions_ui/public/plugin.ts", "deprecated": false, @@ -5806,17 +5701,36 @@ }, { "parentPluginId": "triggersActionsUi", - "id": "def-public.TriggersAndActionsUIPublicPluginStart.getRulesList", + "id": "def-public.TriggersAndActionsUIPublicPluginStart.getRulesListNotifyBadge", "type": "Function", "tags": [], - "label": "getRulesList", + "label": "getRulesListNotifyBadge", "description": [], "signature": [ - "() => React.ReactElement>" + "(props: ", + "RulesListNotifyBadgeProps", + ") => React.ReactElement<", + "RulesListNotifyBadgeProps", + ", string | React.JSXElementConstructor>" ], "path": "x-pack/plugins/triggers_actions_ui/public/plugin.ts", "deprecated": false, - "children": [], + "children": [ + { + "parentPluginId": "triggersActionsUi", + "id": "def-public.TriggersAndActionsUIPublicPluginStart.getRulesListNotifyBadge.$1", + "type": "Object", + "tags": [], + "label": "props", + "description": [], + "signature": [ + "RulesListNotifyBadgeProps" + ], + "path": "x-pack/plugins/triggers_actions_ui/public/plugin.ts", + "deprecated": false, + "isRequired": true + } + ], "returnComment": [] }, { diff --git a/api_docs/triggers_actions_ui.mdx b/api_docs/triggers_actions_ui.mdx index c5522864a1c75..75f8479dac735 100644 --- a/api_docs/triggers_actions_ui.mdx +++ b/api_docs/triggers_actions_ui.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/triggersActionsUi title: "triggersActionsUi" image: https://source.unsplash.com/400x175/?github summary: API docs for the triggersActionsUi plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'triggersActionsUi'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- @@ -18,7 +18,7 @@ Contact [Response Ops](https://github.com/orgs/elastic/teams/response-ops) for q | Public API count | Any count | Items lacking comments | Missing exports | |-------------------|-----------|------------------------|-----------------| -| 412 | 0 | 391 | 40 | +| 407 | 0 | 386 | 42 | ## Client diff --git a/api_docs/ui_actions.mdx b/api_docs/ui_actions.mdx index 49db9908f5e09..97fb23e83f3df 100644 --- a/api_docs/ui_actions.mdx +++ b/api_docs/ui_actions.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/uiActions title: "uiActions" image: https://source.unsplash.com/400x175/?github summary: API docs for the uiActions plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'uiActions'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/ui_actions_enhanced.mdx b/api_docs/ui_actions_enhanced.mdx index 176c8a902aa9c..bb8880d47c606 100644 --- a/api_docs/ui_actions_enhanced.mdx +++ b/api_docs/ui_actions_enhanced.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/uiActionsEnhanced title: "uiActionsEnhanced" image: https://source.unsplash.com/400x175/?github summary: API docs for the uiActionsEnhanced plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'uiActionsEnhanced'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/unified_search.mdx b/api_docs/unified_search.mdx index 31a4820f9da14..0cd501995770f 100644 --- a/api_docs/unified_search.mdx +++ b/api_docs/unified_search.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/unifiedSearch title: "unifiedSearch" image: https://source.unsplash.com/400x175/?github summary: API docs for the unifiedSearch plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'unifiedSearch'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/unified_search_autocomplete.mdx b/api_docs/unified_search_autocomplete.mdx index 40f91935ccaeb..29766e609bf00 100644 --- a/api_docs/unified_search_autocomplete.mdx +++ b/api_docs/unified_search_autocomplete.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/unifiedSearch-autocomplete title: "unifiedSearch.autocomplete" image: https://source.unsplash.com/400x175/?github summary: API docs for the unifiedSearch.autocomplete plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'unifiedSearch.autocomplete'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/url_forwarding.mdx b/api_docs/url_forwarding.mdx index 257045a1a7cd8..1fad07a494c85 100644 --- a/api_docs/url_forwarding.mdx +++ b/api_docs/url_forwarding.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/urlForwarding title: "urlForwarding" image: https://source.unsplash.com/400x175/?github summary: API docs for the urlForwarding plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'urlForwarding'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/usage_collection.mdx b/api_docs/usage_collection.mdx index 68a4cf6640fa6..dd8818245282a 100644 --- a/api_docs/usage_collection.mdx +++ b/api_docs/usage_collection.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/usageCollection title: "usageCollection" image: https://source.unsplash.com/400x175/?github summary: API docs for the usageCollection plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'usageCollection'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/ux.mdx b/api_docs/ux.mdx index c59920507b2c0..34058194ec5d3 100644 --- a/api_docs/ux.mdx +++ b/api_docs/ux.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/ux title: "ux" image: https://source.unsplash.com/400x175/?github summary: API docs for the ux plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'ux'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_default_editor.mdx b/api_docs/vis_default_editor.mdx index 643412cbea7b5..ec8236e6f5118 100644 --- a/api_docs/vis_default_editor.mdx +++ b/api_docs/vis_default_editor.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visDefaultEditor title: "visDefaultEditor" image: https://source.unsplash.com/400x175/?github summary: API docs for the visDefaultEditor plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visDefaultEditor'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_gauge.mdx b/api_docs/vis_type_gauge.mdx index 73b3fd805469b..407ea28ce7063 100644 --- a/api_docs/vis_type_gauge.mdx +++ b/api_docs/vis_type_gauge.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeGauge title: "visTypeGauge" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeGauge plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeGauge'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_heatmap.mdx b/api_docs/vis_type_heatmap.mdx index 8fced74534107..926a05ae26c60 100644 --- a/api_docs/vis_type_heatmap.mdx +++ b/api_docs/vis_type_heatmap.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeHeatmap title: "visTypeHeatmap" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeHeatmap plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeHeatmap'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_pie.devdocs.json b/api_docs/vis_type_pie.devdocs.json index 04d01630e4108..e7612bd29b859 100644 --- a/api_docs/vis_type_pie.devdocs.json +++ b/api_docs/vis_type_pie.devdocs.json @@ -90,7 +90,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; }" ], diff --git a/api_docs/vis_type_pie.mdx b/api_docs/vis_type_pie.mdx index 6f2df2634dae4..be74dcbeb159e 100644 --- a/api_docs/vis_type_pie.mdx +++ b/api_docs/vis_type_pie.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypePie title: "visTypePie" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypePie plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypePie'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_table.mdx b/api_docs/vis_type_table.mdx index 399fdf3d04609..791bed4ef1d41 100644 --- a/api_docs/vis_type_table.mdx +++ b/api_docs/vis_type_table.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeTable title: "visTypeTable" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeTable plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeTable'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_timelion.mdx b/api_docs/vis_type_timelion.mdx index 35ceba01e9d4c..05c0f109bd2c9 100644 --- a/api_docs/vis_type_timelion.mdx +++ b/api_docs/vis_type_timelion.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeTimelion title: "visTypeTimelion" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeTimelion plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeTimelion'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_timeseries.mdx b/api_docs/vis_type_timeseries.mdx index 0e79bc87dad38..9ae9fa6db9d2b 100644 --- a/api_docs/vis_type_timeseries.mdx +++ b/api_docs/vis_type_timeseries.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeTimeseries title: "visTypeTimeseries" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeTimeseries plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeTimeseries'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_vega.mdx b/api_docs/vis_type_vega.mdx index 9c7e5004768fd..3ebbe662877aa 100644 --- a/api_docs/vis_type_vega.mdx +++ b/api_docs/vis_type_vega.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeVega title: "visTypeVega" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeVega plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeVega'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_vislib.mdx b/api_docs/vis_type_vislib.mdx index 63b6b57590f6d..58c34f869c85b 100644 --- a/api_docs/vis_type_vislib.mdx +++ b/api_docs/vis_type_vislib.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeVislib title: "visTypeVislib" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeVislib plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeVislib'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/vis_type_xy.mdx b/api_docs/vis_type_xy.mdx index 7ddcc5d5423f9..faf14dab5c609 100644 --- a/api_docs/vis_type_xy.mdx +++ b/api_docs/vis_type_xy.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visTypeXy title: "visTypeXy" image: https://source.unsplash.com/400x175/?github summary: API docs for the visTypeXy plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visTypeXy'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- diff --git a/api_docs/visualizations.devdocs.json b/api_docs/visualizations.devdocs.json index 07a10571b64cb..d647aaa69542f 100644 --- a/api_docs/visualizations.devdocs.json +++ b/api_docs/visualizations.devdocs.json @@ -1306,7 +1306,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; source?: string | undefined; sourceParams?: ", "SerializableRecord", @@ -4919,7 +4919,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", ">; }" ], @@ -6104,7 +6104,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined) => { id?: string | undefined; params?: Record | undefined; } | undefined" ], @@ -6168,7 +6168,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined" ], @@ -6267,7 +6267,7 @@ "section": "def-common.SerializedFieldFormat", "text": "SerializedFieldFormat" }, - "<", + "<{}, ", "SerializableRecord", "> | undefined; source?: string | undefined; sourceParams?: ", "SerializableRecord", diff --git a/api_docs/visualizations.mdx b/api_docs/visualizations.mdx index 13b8faa002999..0622481dda318 100644 --- a/api_docs/visualizations.mdx +++ b/api_docs/visualizations.mdx @@ -4,7 +4,7 @@ slug: /kibana-dev-docs/api/visualizations title: "visualizations" image: https://source.unsplash.com/400x175/?github summary: API docs for the visualizations plugin -date: 2022-07-13 +date: 2022-07-14 tags: ['contributor', 'dev', 'apidocs', 'kibana', 'visualizations'] warning: This document is auto-generated and is meant to be viewed inside our experimental, new docs system. Reach out in #docs-engineering for more info. --- From 6110d1b66008192b816f96886aa9d8ae37e7dece Mon Sep 17 00:00:00 2001 From: Angela Chuang <6295984+angorayc@users.noreply.github.com> Date: Thu, 14 Jul 2022 09:12:58 +0100 Subject: [PATCH 009/111] Refactoring network DNS to use useSearchStrategy (#136005) Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../security_solution/network/dns/index.ts | 7 - .../components/network_dns_table/mock.ts | 52 ------- .../containers/network_dns/index.test.tsx | 68 +++++++-- .../network/containers/network_dns/index.tsx | 137 +++++------------- .../pages/navigation/dns_query_tab_body.tsx | 1 - 5 files changed, 95 insertions(+), 170 deletions(-) diff --git a/x-pack/plugins/security_solution/common/search_strategy/security_solution/network/dns/index.ts b/x-pack/plugins/security_solution/common/search_strategy/security_solution/network/dns/index.ts index 54c1b418f83bd..cb0fa20deb36d 100644 --- a/x-pack/plugins/security_solution/common/search_strategy/security_solution/network/dns/index.ts +++ b/x-pack/plugins/security_solution/common/search_strategy/security_solution/network/dns/index.ts @@ -28,7 +28,6 @@ export interface NetworkDnsStrategyResponse extends IEsSearchResponse { totalCount: number; pageInfo: PageInfoPaginated; inspect?: Maybe; - histogram?: Maybe; } export interface NetworkDnsEdges { @@ -45,12 +44,6 @@ export interface NetworkDnsItem { uniqueDomains?: Maybe; } -export interface MatrixOverOrdinalHistogramData { - x: string; - y: number; - g: string; -} - export interface NetworkDnsBuckets { key: string; doc_count: number; diff --git a/x-pack/plugins/security_solution/public/network/components/network_dns_table/mock.ts b/x-pack/plugins/security_solution/public/network/components/network_dns_table/mock.ts index 3fa4ddd3fc9c0..2af67776534b2 100644 --- a/x-pack/plugins/security_solution/public/network/components/network_dns_table/mock.ts +++ b/x-pack/plugins/security_solution/public/network/components/network_dns_table/mock.ts @@ -126,57 +126,5 @@ export const mockData: NetworkDnsStrategyResponse = { fakeTotalCount: 50, showMorePagesIndicator: true, }, - histogram: [ - { - x: 'nflxvideo.net', - g: 'nflxvideo.net', - y: 12546, - }, - { - x: 'apple.com', - g: 'apple.com', - y: 31687, - }, - { - x: 'googlevideo.com', - g: 'googlevideo.com', - y: 16292, - }, - { - x: 'netflix.com', - g: 'netflix.com', - y: 218193, - }, - { - x: 'samsungcloudsolution.com', - g: 'samsungcloudsolution.com', - y: 11702, - }, - { - x: 'doubleclick.net', - g: 'doubleclick.net', - y: 14372, - }, - { - x: 'digitalocean.com', - g: 'digitalocean.com', - y: 4111, - }, - { - x: 'samsungelectronics.com', - g: 'samsungelectronics.com', - y: 36592, - }, - { - x: 'google.com', - g: 'google.com', - y: 8072, - }, - { - x: 'samsungcloudsolution.net', - g: 'samsungcloudsolution.net', - y: 11518, - }, - ], rawResponse: {} as NetworkDnsStrategyResponse['rawResponse'], }; diff --git a/x-pack/plugins/security_solution/public/network/containers/network_dns/index.test.tsx b/x-pack/plugins/security_solution/public/network/containers/network_dns/index.test.tsx index af634f629fedd..34272cd7cbccf 100644 --- a/x-pack/plugins/security_solution/public/network/containers/network_dns/index.test.tsx +++ b/x-pack/plugins/security_solution/public/network/containers/network_dns/index.test.tsx @@ -8,25 +8,73 @@ import { act, renderHook } from '@testing-library/react-hooks'; import { TestProviders } from '../../../common/mock'; import { ID, useNetworkDns } from '.'; -import { NetworkType } from '../../store/model'; +import { useSearchStrategy } from '../../../common/containers/use_search_strategy'; + +jest.mock('../../../common/containers/use_search_strategy', () => ({ + useSearchStrategy: jest.fn(), +})); +const mockUseSearchStrategy = useSearchStrategy as jest.Mock; +const mockSearch = jest.fn(); + +const props = { + docValueFields: [], + endDate: '2020-07-08T08:20:18.966Z', + id: ID, + indexNames: ['auditbeat-*'], + skip: false, + startDate: '2020-07-07T08:20:18.966Z', +}; describe('useNetworkDns', () => { + beforeEach(() => { + jest.clearAllMocks(); + mockUseSearchStrategy.mockReturnValue({ + loading: false, + result: { + edges: [], + totalCount: -1, + pageInfo: { + activePage: 0, + fakeTotalCount: 0, + showMorePagesIndicator: false, + }, + }, + search: mockSearch, + refetch: jest.fn(), + inspect: {}, + }); + }); + + it('runs search', () => { + renderHook(() => useNetworkDns(props), { + wrapper: TestProviders, + }); + + expect(mockSearch).toHaveBeenCalled(); + }); + + it('does not run search when skip = true', () => { + const localProps = { + ...props, + skip: true, + }; + renderHook(() => useNetworkDns(localProps), { + wrapper: TestProviders, + }); + + expect(mockSearch).not.toHaveBeenCalled(); + }); + it('skip = true will cancel any running request', () => { - const abortSpy = jest.spyOn(AbortController.prototype, 'abort'); const localProps = { - docValueFields: [], - startDate: '2020-07-07T08:20:18.966Z', - endDate: '2020-07-08T08:20:18.966Z', - id: `${ID}-${NetworkType.page}`, - indexNames: ['cool'], - type: NetworkType.page, - skip: false, + ...props, }; const { rerender } = renderHook(() => useNetworkDns(localProps), { wrapper: TestProviders, }); localProps.skip = true; act(() => rerender()); - expect(abortSpy).toHaveBeenCalledTimes(4); + expect(mockUseSearchStrategy).toHaveBeenCalledTimes(3); + expect(mockUseSearchStrategy.mock.calls[2][0].abort).toEqual(true); }); }); diff --git a/x-pack/plugins/security_solution/public/network/containers/network_dns/index.tsx b/x-pack/plugins/security_solution/public/network/containers/network_dns/index.tsx index e13036cc0d3bc..28dc7e657191c 100644 --- a/x-pack/plugins/security_solution/public/network/containers/network_dns/index.tsx +++ b/x-pack/plugins/security_solution/public/network/containers/network_dns/index.tsx @@ -5,37 +5,29 @@ * 2.0. */ -import { noop } from 'lodash/fp'; -import { useState, useEffect, useCallback, useMemo, useRef } from 'react'; +import { useState, useEffect, useCallback, useMemo } from 'react'; import deepEqual from 'fast-deep-equal'; -import { Subscription } from 'rxjs'; -import { isCompleteResponse, isErrorResponse } from '@kbn/data-plugin/common'; import type { ESTermQuery } from '../../../../common/typed_json'; import type { inputsModel } from '../../../common/store'; import { useDeepEqualSelector } from '../../../common/hooks/use_selector'; -import { useKibana } from '../../../common/lib/kibana'; import { createFilter } from '../../../common/containers/helpers'; import { generateTablePaginationOptions } from '../../../common/components/paginated_table/helpers'; -import type { networkModel } from '../../store'; import { networkSelectors } from '../../store'; import type { DocValueFields, NetworkDnsRequestOptions, - NetworkDnsStrategyResponse, - MatrixOverOrdinalHistogramData, NetworkDnsEdges, PageInfoPaginated, } from '../../../../common/search_strategy'; import { NetworkQueries } from '../../../../common/search_strategy'; import * as i18n from './translations'; -import { getInspectResponse } from '../../../helpers'; import type { InspectResponse } from '../../../types'; -import { useAppToasts } from '../../../common/hooks/use_app_toasts'; +import { useSearchStrategy } from '../../../common/containers/use_search_strategy'; export const ID = 'networkDnsQuery'; -export interface NetworkDnsArgs { +export interface NetworkDnsResponse { id: string; inspect: InspectResponse; isInspected: boolean; @@ -45,14 +37,12 @@ export interface NetworkDnsArgs { refetch: inputsModel.Refetch; stackByField?: string; totalCount: number; - histogram: MatrixOverOrdinalHistogramData[]; } interface UseNetworkDns { id: string; docValueFields: DocValueFields[]; indexNames: string[]; - type: networkModel.NetworkType; filterQuery?: ESTermQuery | string; endDate: string; startDate: string; @@ -67,15 +57,9 @@ export const useNetworkDns = ({ indexNames, skip, startDate, - type, -}: UseNetworkDns): [boolean, NetworkDnsArgs] => { +}: UseNetworkDns): [boolean, NetworkDnsResponse] => { const getNetworkDnsSelector = useMemo(() => networkSelectors.dnsSelector(), []); const { activePage, sort, isPtrIncluded, limit } = useDeepEqualSelector(getNetworkDnsSelector); - const { data } = useKibana().services; - const refetch = useRef(noop); - const abortCtrl = useRef(new AbortController()); - const searchSubscription$ = useRef(new Subscription()); - const [loading, setLoading] = useState(false); const [networkDnsRequest, setNetworkDnsRequest] = useState(null); @@ -95,76 +79,39 @@ export const useNetworkDns = ({ [limit] ); - const [networkDnsResponse, setNetworkDnsResponse] = useState({ - networkDns: [], - histogram: [], - id, - inspect: { - dsl: [], - response: [], + const { + loading, + result: response, + search, + refetch, + inspect, + } = useSearchStrategy({ + factoryQueryType: NetworkQueries.dns, + initialResult: { + edges: [], + totalCount: -1, + pageInfo: { + activePage: 0, + fakeTotalCount: 0, + showMorePagesIndicator: false, + }, }, - isInspected: false, - loadPage: wrappedLoadMore, - pageInfo: { - activePage: 0, - fakeTotalCount: 0, - showMorePagesIndicator: false, - }, - refetch: refetch.current, - totalCount: -1, + errorMessage: i18n.ERROR_NETWORK_DNS, + abort: skip, }); - const { addError, addWarning } = useAppToasts(); - - const networkDnsSearch = useCallback( - (request: NetworkDnsRequestOptions | null) => { - if (request == null || skip) { - return; - } - - const asyncSearch = async () => { - abortCtrl.current = new AbortController(); - setLoading(true); - searchSubscription$.current = data.search - .search(request, { - strategy: 'securitySolutionSearchStrategy', - abortSignal: abortCtrl.current.signal, - }) - .subscribe({ - next: (response) => { - if (isCompleteResponse(response)) { - setLoading(false); - setNetworkDnsResponse((prevResponse) => ({ - ...prevResponse, - networkDns: response.edges, - inspect: getInspectResponse(response, prevResponse.inspect), - pageInfo: response.pageInfo, - refetch: refetch.current, - totalCount: response.totalCount, - histogram: response.histogram ?? prevResponse.histogram, - })); - searchSubscription$.current.unsubscribe(); - } else if (isErrorResponse(response)) { - setLoading(false); - addWarning(i18n.ERROR_NETWORK_DNS); - searchSubscription$.current.unsubscribe(); - } - }, - error: (msg) => { - setLoading(false); - addError(msg, { - title: i18n.FAIL_NETWORK_DNS, - }); - searchSubscription$.current.unsubscribe(); - }, - }); - }; - searchSubscription$.current.unsubscribe(); - abortCtrl.current.abort(); - asyncSearch(); - refetch.current = asyncSearch; - }, - [data.search, addError, addWarning, skip] + const networkDnsResponse = useMemo( + () => ({ + id, + inspect, + isInspected: false, + loadPage: wrappedLoadMore, + networkDns: response.edges, + pageInfo: response.pageInfo, + refetch, + totalCount: response.totalCount, + }), + [id, inspect, refetch, response.edges, response.pageInfo, response.totalCount, wrappedLoadMore] ); useEffect(() => { @@ -202,20 +149,10 @@ export const useNetworkDns = ({ ]); useEffect(() => { - networkDnsSearch(networkDnsRequest); - return () => { - searchSubscription$.current.unsubscribe(); - abortCtrl.current.abort(); - }; - }, [networkDnsRequest, networkDnsSearch]); - - useEffect(() => { - if (skip) { - setLoading(false); - searchSubscription$.current.unsubscribe(); - abortCtrl.current.abort(); + if (!skip && networkDnsRequest) { + search(networkDnsRequest); } - }, [skip]); + }, [networkDnsRequest, search, skip]); return [loading, networkDnsResponse]; }; diff --git a/x-pack/plugins/security_solution/public/network/pages/navigation/dns_query_tab_body.tsx b/x-pack/plugins/security_solution/public/network/pages/navigation/dns_query_tab_body.tsx index 971c424d78fe1..ee423b0343088 100644 --- a/x-pack/plugins/security_solution/public/network/pages/navigation/dns_query_tab_body.tsx +++ b/x-pack/plugins/security_solution/public/network/pages/navigation/dns_query_tab_body.tsx @@ -89,7 +89,6 @@ const DnsQueryTabBodyComponent: React.FC = ({ indexNames, skip: querySkip, startDate, - type, }); const getTitle = useCallback( From 4e8a0719a34dbf25a1463713c4f5f64ce3fb462a Mon Sep 17 00:00:00 2001 From: Sander Philipse <94373878+sphilipse@users.noreply.github.com> Date: Thu, 14 Jul 2022 10:39:30 +0200 Subject: [PATCH 010/111] [Enterprise Search] Adds connector status and fixes configuration page (#136317) --- .../common/types/connector_package.ts | 12 --- .../types/connectors.ts} | 30 +++++-- .../enterprise_search/common/types/indices.ts | 5 +- ...pdate_connector_configuration_api_logic.ts | 3 +- .../update_connector_scheduling_api_logic.ts | 2 +- .../api/index/fetch_index_api_logic.ts | 52 +---------- .../connector/api_key_configuration.tsx | 26 +----- .../connector/connector_configuration.tsx | 90 +++++++++++++++++-- .../connector_configuration_config.tsx | 35 +++++++- .../connector_configuration_logic.ts | 2 +- .../connector/connector_scheduling_logic.ts | 2 +- .../enterprise_search_content/types.ts | 30 ++++++- .../lib/connectors/add_connector.test.ts | 7 +- .../server/lib/connectors/add_connector.ts | 14 +-- .../server/lib/connectors/fetch_connectors.ts | 16 ++-- .../update_connector_configuration.ts | 16 +++- .../connectors/update_connector_scheduling.ts | 6 +- .../server/lib/indices/generate_api_key.ts | 4 +- .../routes/enterprise_search/connectors.ts | 2 +- 19 files changed, 213 insertions(+), 141 deletions(-) delete mode 100644 x-pack/plugins/enterprise_search/common/types/connector_package.ts rename x-pack/plugins/enterprise_search/{server/types/connector.ts => common/types/connectors.ts} (61%) diff --git a/x-pack/plugins/enterprise_search/common/types/connector_package.ts b/x-pack/plugins/enterprise_search/common/types/connector_package.ts deleted file mode 100644 index 2051360b733f4..0000000000000 --- a/x-pack/plugins/enterprise_search/common/types/connector_package.ts +++ /dev/null @@ -1,12 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -export interface ConnectorPackage { - id: string; - indexName: string; - name: string; -} diff --git a/x-pack/plugins/enterprise_search/server/types/connector.ts b/x-pack/plugins/enterprise_search/common/types/connectors.ts similarity index 61% rename from x-pack/plugins/enterprise_search/server/types/connector.ts rename to x-pack/plugins/enterprise_search/common/types/connectors.ts index 95e1e6876e4a8..bdeac44734286 100644 --- a/x-pack/plugins/enterprise_search/server/types/connector.ts +++ b/x-pack/plugins/enterprise_search/common/types/connectors.ts @@ -7,30 +7,44 @@ export interface KeyValuePair { label: string; - value: string | null; + value: string; } -export type ConnectorConfiguration = Record; +export type ConnectorConfiguration = Record; export interface ConnectorScheduling { enabled: boolean; interval: string; } +export enum ConnectorStatus { + CREATED = 'created', + NEEDS_CONFIGURATION = 'needs_configuration', + CONFIGURED = 'configured', + CONNECTED = 'connected', + ERROR = 'error', +} + +export enum SyncStatus { + IN_PROGRESS = 'in_progress', + COMPLETED = 'completed', + ERROR = 'error', +} export interface Connector { api_key_id: string | null; configuration: ConnectorConfiguration; - created_at: string | null; + id: string; index_name: string; last_seen: string | null; last_synced: string | null; - scheduling: ConnectorScheduling; + scheduling: { + enabled: boolean; + interval: string; // crontab syntax + }; service_type: string | null; - status: string | null; + status: ConnectorStatus; sync_error: string | null; sync_now: boolean; sync_status: string | null; } -export interface ConnectorWithId extends Connector { - id: string; -} +export type ConnectorDocument = Omit; diff --git a/x-pack/plugins/enterprise_search/common/types/indices.ts b/x-pack/plugins/enterprise_search/common/types/indices.ts index 485c2274a5f20..4b3007c36ec1d 100644 --- a/x-pack/plugins/enterprise_search/common/types/indices.ts +++ b/x-pack/plugins/enterprise_search/common/types/indices.ts @@ -14,9 +14,9 @@ import { export interface ElasticsearchIndex { health?: HealthStatus; - status?: IndicesStatsIndexMetadataState; + name: IndexName; - uuid?: Uuid; + status?: IndicesStatsIndexMetadataState; total: { docs: { count: number; @@ -26,4 +26,5 @@ export interface ElasticsearchIndex { size_in_bytes: string; }; }; + uuid?: Uuid; } diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_configuration_api_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_configuration_api_logic.ts index 91c6495f3cdfb..49373a45eb99c 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_configuration_api_logic.ts +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_configuration_api_logic.ts @@ -5,11 +5,10 @@ * 2.0. */ +import { ConnectorConfiguration } from '../../../../../common/types/connectors'; import { createApiLogic } from '../../../shared/api_logic/create_api_logic'; import { HttpLogic } from '../../../shared/http'; -import { ConnectorConfiguration } from '../index/fetch_index_api_logic'; - export interface PostConnectorConfigurationArgs { configuration: ConnectorConfiguration; indexId: string; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_scheduling_api_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_scheduling_api_logic.ts index 47679ee1caa0e..eebbd2b2bedf4 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_scheduling_api_logic.ts +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/connector_package/update_connector_scheduling_api_logic.ts @@ -5,9 +5,9 @@ * 2.0. */ +import { ConnectorScheduling } from '../../../../../common/types/connectors'; import { createApiLogic } from '../../../shared/api_logic/create_api_logic'; import { HttpLogic } from '../../../shared/http'; -import { ConnectorScheduling } from '../index/fetch_index_api_logic'; export interface UpdateConnectorSchedulingArgs { connectorId: string; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts index adfd99a8a2d24..87ab8ecc700ba 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts @@ -7,57 +7,7 @@ import { createApiLogic } from '../../../shared/api_logic/create_api_logic'; import { HttpLogic } from '../../../shared/http'; - -export interface KeyValuePair { - label: string; - value: string; -} - -export type ConnectorConfiguration = Record; -export interface ConnectorScheduling { - enabled: boolean; - interval: string; -} - -export interface Connector { - api_key_id: string | null; - configuration: ConnectorConfiguration; - created_at: string | null; - id: string; - index_name: string; - last_seen: string | null; - last_synced: string | null; - scheduling: { - enabled: boolean; - interval: string; // crontab syntax - }; - service_type: string | null; - status: string; - sync_error: string | null; - sync_now: boolean; - sync_status: string | null; -} - -export interface Crawler { - domains: []; -} - -export interface IndexData { - connector?: Connector; - crawler?: Crawler; - index: { - aliases: string[]; - health: string; - name: string; - total: { - docs: { - count: number; - deleted: number; - }; - }; - uuid: string; - }; -} +import { IndexData } from '../../types'; export const fetchIndex = async ({ indexName }: { indexName: string }) => { const route = `/internal/enterprise_search/indices/${indexName}`; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/api_key_configuration.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/api_key_configuration.tsx index e53ffac0d4393..d4b8c82909e9f 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/api_key_configuration.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/api_key_configuration.tsx @@ -16,7 +16,6 @@ import { EuiButton, EuiLink, EuiSpacer, - EuiCallOut, EuiConfirmModal, } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; @@ -72,7 +71,7 @@ export const ApiKeyConfig: React.FC<{ hasApiKey: boolean; indexName: string }> = confirmButtonText={i18n.translate( 'xpack.enterpriseSearch.content.indices.configurationConnector.apiKey.confirmModal.confirmButton.label', { - defaultMessage: 'Generate an Elasticsearch API key', + defaultMessage: 'Generate API key', } )} defaultFocusedButton="confirm" @@ -81,7 +80,7 @@ export const ApiKeyConfig: React.FC<{ hasApiKey: boolean; indexName: string }> = 'xpack.enterpriseSearch.content.indices.configurationConnector.apiKey.confirmModal.description', { defaultMessage: - 'Generating a new Elasticsearch API key will invalidate the previous key. Are you sure you want to generate a new Elasticsearch API key? This can not be undone.', + 'Generating a new API key will invalidate the previous key. Are you sure you want to generate a new API key? This can not be undone.', } )} @@ -96,7 +95,7 @@ export const ApiKeyConfig: React.FC<{ hasApiKey: boolean; indexName: string }> = 'xpack.enterpriseSearch.content.indices.configurationConnector.apiKey.description', { defaultMessage: - 'Keep your Elasticsearch API key somewhere safe while you configure your connector. Generating a new Elasticsearch API key will invalidate the previous key.', + 'Keep your Elasticsearch API key somewhere safe while you configure your connector.', } )} @@ -134,25 +133,6 @@ export const ApiKeyConfig: React.FC<{ hasApiKey: boolean; indexName: string }> = )} - {hasApiKey && ( - - - {i18n.translate( - 'xpack.enterpriseSearch.content.indices.configurationConnector.apiKey.warning.description', - { - defaultMessage: - 'Generating a new Elasticsearch API key will invalidate the previous key.', - } - )} - - - )} ); }; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration.tsx index e41761e01dcfd..8243f901b70f8 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration.tsx @@ -7,14 +7,11 @@ import React from 'react'; -import { useParams } from 'react-router-dom'; - import { useValues } from 'kea'; import { EuiText, EuiFlexGroup, - EuiButton, EuiFlexItem, EuiLink, EuiPanel, @@ -24,17 +21,26 @@ import { import { i18n } from '@kbn/i18n'; +import { ConnectorStatus } from '../../../../../../common/types/connectors'; +import { generateEncodedPath } from '../../../../shared/encode_path_params'; +import { EuiButtonTo } from '../../../../shared/react_router_helpers'; + import { GenerateConnectorApiKeyApiLogic } from '../../../api/connector_package/generate_connector_api_key_api_logic'; import { FetchIndexApiLogic } from '../../../api/index/fetch_index_api_logic'; +import { SEARCH_INDEX_TAB_PATH } from '../../../routes'; import { ApiKey } from '../../api_key/api_key'; +import { IndexNameLogic } from '../index_name_logic'; + +import { SearchIndexTabId } from '../search_index'; + import { ApiKeyConfig } from './api_key_configuration'; import { ConnectorConfigurationConfig } from './connector_configuration_config'; export const ConnectorConfiguration: React.FC = () => { const { data: apiKeyData } = useValues(GenerateConnectorApiKeyApiLogic); const { data: indexData } = useValues(FetchIndexApiLogic); - const { indexName } = useParams<{ indexName: string }>(); + const { indexName } = useValues(IndexNameLogic); const indexId = indexData?.connector?.id ?? ''; const hasApiKey = !!(indexData?.connector?.api_key_id ?? apiKeyData); @@ -42,7 +48,9 @@ export const ConnectorConfiguration: React.FC = () => { const ConnectorConfig: React.FC = () => indexData?.connector ? ( @@ -50,6 +58,41 @@ export const ConnectorConfiguration: React.FC = () => { <> ); + const ScheduleStep: React.FC = () => ( + + + + {i18n.translate( + 'xpack.enterpriseSearch.content.indices.configurationConnector.scheduleSync.description', + { + defaultMessage: + 'To start a sync you need to set a schedule. Once done your documents will begin to sync.', + } + )} + + + + + + + {i18n.translate( + 'xpack.enterpriseSearch.content.indices.configurationConnector.steps.schedule.button.label', + { + defaultMessage: 'Set schedule and sync', + } + )} + + + + + + ); + const ConnectorPackage: React.FC = () => ( @@ -65,14 +108,14 @@ export const ConnectorConfiguration: React.FC = () => { - + {i18n.translate( 'xpack.enterpriseSearch.content.indices.configurationConnector.connectorPackage.button.label', { defaultMessage: 'Clone and deploy connector package', } )} - + @@ -82,7 +125,7 @@ export const ConnectorConfiguration: React.FC = () => { label={i18n.translate( 'xpack.enterpriseSearch.content.indices.configurationConnector.connectorPackage.apiKey.label', { - defaultMessage: 'Connector package ID', + defaultMessage: 'Connector ID', } )} /> @@ -116,7 +159,11 @@ export const ConnectorConfiguration: React.FC = () => { }, { children: , - status: 'incomplete', + status: + !indexData?.connector?.status || + indexData.connector.status === ConnectorStatus.CREATED + ? 'incomplete' + : 'complete', title: i18n.translate( 'xpack.enterpriseSearch.content.indices.configurationConnector.steps.deployConnector.title', { @@ -127,7 +174,11 @@ export const ConnectorConfiguration: React.FC = () => { }, { children: , - status: 'incomplete', + status: + indexData?.connector?.status && + indexData.connector.status === ConnectorStatus.CONNECTED + ? 'complete' + : 'incomplete', title: i18n.translate( 'xpack.enterpriseSearch.content.indices.configurationConnector.steps.connect.title', { @@ -136,6 +187,17 @@ export const ConnectorConfiguration: React.FC = () => { ), titleSize: 'xs', }, + { + children: , + status: indexData?.connector?.scheduling.enabled ? 'complete' : 'incomplete', + title: i18n.translate( + 'xpack.enterpriseSearch.content.indices.configurationConnector.steps.schedule.title', + { + defaultMessage: 'Set a schedule and start a sync', + } + ), + titleSize: 'xs', + }, ]} /> @@ -191,6 +253,16 @@ export const ConnectorConfiguration: React.FC = () => { )} + + + {i18n.translate( + 'xpack.enterpriseSearch.content.indices.configurationConnector.support.feedback.label', + { + defaultMessage: 'Custom connector feedback', + } + )} + + diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_config.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_config.tsx index 233207d6cf427..c1927aeea0dfc 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_config.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_config.tsx @@ -12,32 +12,38 @@ import { useActions, useValues } from 'kea'; import { EuiButton, EuiButtonEmpty, + EuiCodeBlock, EuiDescriptionList, EuiFieldText, EuiFlexGroup, EuiFlexItem, EuiForm, EuiFormRow, + EuiSpacer, EuiText, } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; import { Status } from '../../../../../../common/types/api'; +import { ConnectorConfiguration } from '../../../../../../common/types/connectors'; import { isNotNullish } from '../../../../../../common/utils/is_not_nullish'; import { ConnectorConfigurationApiLogic } from '../../../api/connector_package/update_connector_configuration_api_logic'; -import { ConnectorConfiguration } from '../../../api/index/fetch_index_api_logic'; import { ConnectorConfigurationLogic } from './connector_configuration_logic'; interface ConnectorConfigurationConfigArgs { + apiKey: string | undefined; configuration: ConnectorConfiguration; + connectorId: string; indexId: string; indexName: string; } export const ConnectorConfigurationConfig: React.FC = ({ + apiKey, configuration, + connectorId, indexId, indexName, }) => { @@ -54,6 +60,19 @@ export const ConnectorConfigurationConfig: React.FC + {`${ + apiKey + ? `elasticsearch: + api_key: "${apiKey}" +` + : '' + }connector_package_id: "${connectorId}" +`} + + ); + const form = ( { @@ -122,6 +141,7 @@ export const ConnectorConfigurationConfig: React.FC ({ description: value ?? '--', title: label })); + const display = ( @@ -158,6 +178,19 @@ export const ConnectorConfigurationConfig: React.FC + + + {i18n.translate( + 'xpack.enterpriseSearch.content.indices.configurationConnector.yml.description', + { + defaultMessage: + 'Use this YAML sample with your Elastic API key and Connector id to get going faster', + } + )} + + + {ymlBlock} + {displayList.length > 0 && fields} ); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_logic.ts index cb4bfe2e5621f..ecbbb2616f88b 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_logic.ts +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_configuration_logic.ts @@ -9,6 +9,7 @@ import { kea, MakeLogicType } from 'kea'; import { i18n } from '@kbn/i18n'; +import { ConnectorConfiguration } from '../../../../../../common/types/connectors'; import { Actions } from '../../../../shared/api_logic/create_api_logic'; import { clearFlashMessages, @@ -21,7 +22,6 @@ import { PostConnectorConfigurationArgs, PostConnectorConfigurationResponse, } from '../../../api/connector_package/update_connector_configuration_api_logic'; -import { ConnectorConfiguration } from '../../../api/index/fetch_index_api_logic'; type ConnectorConfigurationActions = Pick< Actions, diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_scheduling_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_scheduling_logic.ts index 6ab8072d27ecf..a6adb47ff88ee 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_scheduling_logic.ts +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/connector/connector_scheduling_logic.ts @@ -9,6 +9,7 @@ import { kea, MakeLogicType } from 'kea'; import { i18n } from '@kbn/i18n'; +import { ConnectorScheduling } from '../../../../../../common/types/connectors'; import { Actions } from '../../../../shared/api_logic/create_api_logic'; import { clearFlashMessages, @@ -20,7 +21,6 @@ import { UpdateConnectorSchedulingApiLogic, UpdateConnectorSchedulingArgs, } from '../../../api/connector_package/update_connector_scheduling_api_logic'; -import { ConnectorScheduling } from '../../../api/index/fetch_index_api_logic'; type ConnectorSchedulingActions = Pick< Actions, diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/types.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/types.ts index 5ada08728e468..b6c88caf63ed6 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/types.ts +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/types.ts @@ -12,11 +12,35 @@ import { HealthStatus } from '@elastic/elasticsearch/lib/api/types'; +import { Connector } from '../../../common/types/connectors'; + export interface SearchIndex { - name: string; - elasticsearch_index_name: string; + data_ingestion: 'connected' | 'incomplete'; document_count: number; + elasticsearch_index_name: string; health: HealthStatus; - data_ingestion: 'connected' | 'incomplete'; + name: string; + storage: string; } + +export interface Crawler { + domains: []; +} + +export interface IndexData { + connector?: Connector; + crawler?: Crawler; + index: { + aliases: string[]; + health: string; + name: string; + total: { + docs: { + count: number; + deleted: number; + }; + }; + uuid: string; + }; +} diff --git a/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.test.ts b/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.test.ts index aa4290e241a2f..fbc8924e499cd 100644 --- a/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.test.ts +++ b/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.test.ts @@ -8,6 +8,7 @@ import { IScopedClusterClient } from '@kbn/core/server'; import { CONNECTORS_INDEX } from '../..'; +import { ConnectorStatus } from '../../../common/types/connectors'; import { setupConnectorsIndices } from '../../index_management/setup_indices'; @@ -42,13 +43,12 @@ describe('addConnector lib function', () => { document: { api_key_id: null, configuration: {}, - created_at: null, index_name: 'index_name', last_seen: null, last_synced: null, scheduling: { enabled: false, interval: '* * * * *' }, service_type: null, - status: 'not connected', + status: ConnectorStatus.CREATED, sync_error: null, sync_now: false, sync_status: null, @@ -73,13 +73,12 @@ describe('addConnector lib function', () => { document: { api_key_id: null, configuration: {}, - created_at: null, index_name: 'index_name', last_seen: null, last_synced: null, scheduling: { enabled: false, interval: '* * * * *' }, service_type: null, - status: 'not connected', + status: ConnectorStatus.CREATED, sync_error: null, sync_now: false, sync_status: null, diff --git a/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.ts b/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.ts index c416d698157da..8314b3ac059b0 100644 --- a/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.ts +++ b/x-pack/plugins/enterprise_search/server/lib/connectors/add_connector.ts @@ -8,13 +8,18 @@ import { IScopedClusterClient } from '@kbn/core/server'; import { CONNECTORS_INDEX } from '../..'; +import { ConnectorDocument, ConnectorStatus } from '../../../common/types/connectors'; import { setupConnectorsIndices } from '../../index_management/setup_indices'; -import { Connector } from '../../types/connector'; import { isIndexNotFoundException } from '../../utils/identify_exceptions'; +export const createConnectorsIndex = async (client: IScopedClusterClient): Promise => { + const index = CONNECTORS_INDEX; + await client.asCurrentUser.indices.create({ index }); +}; + const createConnector = async ( index: string, - document: Connector, + document: ConnectorDocument, client: IScopedClusterClient ): Promise<{ id: string; index_name: string }> => { const result = await client.asCurrentUser.index({ @@ -31,16 +36,15 @@ export const addConnector = async ( input: { index_name: string } ): Promise<{ id: string; index_name: string }> => { const index = CONNECTORS_INDEX; - const document: Connector = { + const document: ConnectorDocument = { api_key_id: null, configuration: {}, - created_at: null, index_name: input.index_name, last_seen: null, last_synced: null, scheduling: { enabled: false, interval: '* * * * *' }, service_type: null, - status: 'not connected', + status: ConnectorStatus.CREATED, sync_error: null, sync_now: false, sync_status: null, diff --git a/x-pack/plugins/enterprise_search/server/lib/connectors/fetch_connectors.ts b/x-pack/plugins/enterprise_search/server/lib/connectors/fetch_connectors.ts index 6c33baa1064c2..eaeeaff88003a 100644 --- a/x-pack/plugins/enterprise_search/server/lib/connectors/fetch_connectors.ts +++ b/x-pack/plugins/enterprise_search/server/lib/connectors/fetch_connectors.ts @@ -8,18 +8,18 @@ import { IScopedClusterClient } from '@kbn/core/server'; import { CONNECTORS_INDEX } from '../..'; +import { Connector, ConnectorDocument } from '../../../common/types/connectors'; import { isNotNullish } from '../../../common/utils/is_not_nullish'; import { setupConnectorsIndices } from '../../index_management/setup_indices'; -import { Connector, ConnectorWithId } from '../../types/connector'; import { isIndexNotFoundException } from '../../utils/identify_exceptions'; export const fetchConnectorById = async ( client: IScopedClusterClient, connectorId: string -): Promise => { +): Promise => { try { - const connectorResult = await client.asCurrentUser.get({ + const connectorResult = await client.asCurrentUser.get({ id: connectorId, index: CONNECTORS_INDEX, }); @@ -37,9 +37,9 @@ export const fetchConnectorById = async ( export const fetchConnectorByIndexName = async ( client: IScopedClusterClient, indexName: string -): Promise => { +): Promise => { try { - const connectorResult = await client.asCurrentUser.search({ + const connectorResult = await client.asCurrentUser.search({ index: CONNECTORS_INDEX, query: { term: { 'index_name.keyword': indexName } }, }); @@ -58,9 +58,9 @@ export const fetchConnectorByIndexName = async ( } }; -export const fetchConnectors = async (client: IScopedClusterClient): Promise => { +export const fetchConnectors = async (client: IScopedClusterClient): Promise => { try { - const connectorResult = await client.asCurrentUser.search({ + const connectorResult = await client.asCurrentUser.search({ from: 0, index: CONNECTORS_INDEX, query: { match_all: {} }, @@ -69,7 +69,7 @@ export const fetchConnectors = async (client: IScopedClusterClient): Promise= 1000) { - const newConnectorResult = await client.asCurrentUser.search({ + const newConnectorResult = await client.asCurrentUser.search({ from: 0, index: CONNECTORS_INDEX, query: { match_all: {} }, diff --git a/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_configuration.ts b/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_configuration.ts index 4ad3b0c993c2a..77feda4b7ff5b 100644 --- a/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_configuration.ts +++ b/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_configuration.ts @@ -10,21 +10,29 @@ import { i18n } from '@kbn/i18n'; import { CONNECTORS_INDEX } from '../..'; -import { Connector, ConnectorConfiguration } from '../../types/connector'; +import { + ConnectorConfiguration, + ConnectorDocument, + ConnectorStatus, +} from '../../../common/types/connectors'; export const updateConnectorConfiguration = async ( client: IScopedClusterClient, connectorId: string, configuration: ConnectorConfiguration ) => { - const connectorResult = await client.asCurrentUser.get({ + const connectorResult = await client.asCurrentUser.get({ id: connectorId, index: CONNECTORS_INDEX, }); const connector = connectorResult._source; if (connector) { - return await client.asCurrentUser.index({ - document: { ...connector, configuration }, + const status = + connector.status === ConnectorStatus.NEEDS_CONFIGURATION + ? ConnectorStatus.CONFIGURED + : connector.status; + return await client.asCurrentUser.index({ + document: { ...connector, configuration, status }, id: connectorId, index: CONNECTORS_INDEX, }); diff --git a/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_scheduling.ts b/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_scheduling.ts index 4fde352d4030e..3fe7e602148b5 100644 --- a/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_scheduling.ts +++ b/x-pack/plugins/enterprise_search/server/lib/connectors/update_connector_scheduling.ts @@ -10,20 +10,20 @@ import { i18n } from '@kbn/i18n'; import { CONNECTORS_INDEX } from '../..'; -import { Connector, ConnectorScheduling } from '../../types/connector'; +import { ConnectorDocument, ConnectorScheduling } from '../../../common/types/connectors'; export const updateConnectorScheduling = async ( client: IScopedClusterClient, connectorId: string, scheduling: ConnectorScheduling ) => { - const connectorResult = await client.asCurrentUser.get({ + const connectorResult = await client.asCurrentUser.get({ id: connectorId, index: CONNECTORS_INDEX, }); const connector = connectorResult._source; if (connector) { - return await client.asCurrentUser.index({ + return await client.asCurrentUser.index({ document: { ...connector, scheduling }, id: connectorId, index: CONNECTORS_INDEX, diff --git a/x-pack/plugins/enterprise_search/server/lib/indices/generate_api_key.ts b/x-pack/plugins/enterprise_search/server/lib/indices/generate_api_key.ts index dfa2558449cdd..a38ea61e9e36e 100644 --- a/x-pack/plugins/enterprise_search/server/lib/indices/generate_api_key.ts +++ b/x-pack/plugins/enterprise_search/server/lib/indices/generate_api_key.ts @@ -8,7 +8,7 @@ import { IScopedClusterClient } from '@kbn/core/server'; import { CONNECTORS_INDEX } from '../..'; -import { Connector } from '../../types/connector'; +import { ConnectorDocument } from '../../../common/types/connectors'; export const generateApiKey = async (client: IScopedClusterClient, indexName: string) => { const apiKeyResult = await client.asCurrentUser.security.createApiKey({ @@ -25,7 +25,7 @@ export const generateApiKey = async (client: IScopedClusterClient, indexName: st }, }, }); - const connectorResult = await client.asCurrentUser.search({ + const connectorResult = await client.asCurrentUser.search({ index: CONNECTORS_INDEX, query: { term: { 'index_name.keyword': indexName } }, }); diff --git a/x-pack/plugins/enterprise_search/server/routes/enterprise_search/connectors.ts b/x-pack/plugins/enterprise_search/server/routes/enterprise_search/connectors.ts index 9e6337211c5e3..8ee32ab55b688 100644 --- a/x-pack/plugins/enterprise_search/server/routes/enterprise_search/connectors.ts +++ b/x-pack/plugins/enterprise_search/server/routes/enterprise_search/connectors.ts @@ -45,7 +45,7 @@ export function registerConnectorRoutes({ router }: RouteDependencies) { validate: { body: schema.recordOf( schema.string(), - schema.object({ label: schema.string(), value: schema.nullable(schema.string()) }) + schema.object({ label: schema.string(), value: schema.string() }) ), params: schema.object({ connectorId: schema.string(), From 3055fbe69c84cbb5aab15bfe796badda27a45be8 Mon Sep 17 00:00:00 2001 From: Cristina Amico Date: Thu, 14 Jul 2022 11:31:06 +0200 Subject: [PATCH 011/111] [Fleet] Configure source URI in global settings and in agent policy settings (#136263) * [Fleet] Configure source URI in global settings and in agent policy settings * Add some tests and data-test-subj * Test getCountsForDownloadSource * Fix default artifacts URI * Add default column and fix required parameter in openapi specs --- .../fleet/common/constants/download_source.ts | 5 +- .../components/schemas/download_sources.yaml | 1 - .../plugins/fleet/common/services/routes.ts | 12 ++ .../types/rest_spec/download_sources.ts | 11 +- .../agent_policy_advanced_fields/hooks.tsx | 54 +++++- .../agent_policy_advanced_fields/index.tsx | 50 ++++- .../components/settings/index.tsx | 3 + .../download_source_flyout/confirm_update.tsx | 75 ++++++++ .../download_source_flyout/index.test.tsx | 52 +++++ .../download_source_flyout/index.tsx | 179 ++++++++++++++++++ .../services/get_count.test.tsx | 74 ++++++++ .../services/get_count.tsx | 45 +++++ .../use_delete_download_source.tsx | 118 ++++++++++++ .../use_download_source_flyout_form.test.tsx | 48 +++++ .../use_download_source_flyout_form.tsx | 144 ++++++++++++++ .../download_source_table/index.tsx | 140 ++++++++++++++ .../settings_page/agent_binary_section.tsx | 62 ++++++ .../components/settings_page/index.tsx | 12 +- .../fleet/sections/settings/index.tsx | 41 +++- .../fleet/public/constants/page_paths.ts | 17 +- .../hooks/use_request/download_source.ts | 55 ++++++ .../fleet/public/hooks/use_request/index.ts | 1 + x-pack/plugins/fleet/public/services/index.ts | 1 + x-pack/plugins/fleet/public/types/index.ts | 4 + .../plugins/fleet/server/constants/index.ts | 2 +- .../cloud_preconfiguration.test.ts.snap | 2 +- .../fleet/server/services/download_source.ts | 6 +- .../apis/download_sources/crud.ts | 8 +- 28 files changed, 1196 insertions(+), 26 deletions(-) create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/confirm_update.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.test.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.test.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_delete_download_source.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.test.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_table/index.tsx create mode 100644 x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/agent_binary_section.tsx create mode 100644 x-pack/plugins/fleet/public/hooks/use_request/download_source.ts diff --git a/x-pack/plugins/fleet/common/constants/download_source.ts b/x-pack/plugins/fleet/common/constants/download_source.ts index 22959ed7023bb..76b6f2ce397ab 100644 --- a/x-pack/plugins/fleet/common/constants/download_source.ts +++ b/x-pack/plugins/fleet/common/constants/download_source.ts @@ -5,8 +5,9 @@ * 2.0. */ -// Default URL used to download Elastic Agent -export const DEFAULT_DOWNLOAD_SOURCE = 'https://artifacts.elastic.co'; +// Default source URI used to download Elastic Agent +export const DEFAULT_DOWNLOAD_SOURCE_URI = + 'https://artifacts.elastic.co/downloads/beats/elastic-agent'; export const DOWNLOAD_SOURCE_SAVED_OBJECT_TYPE = 'ingest-download-sources'; diff --git a/x-pack/plugins/fleet/common/openapi/components/schemas/download_sources.yaml b/x-pack/plugins/fleet/common/openapi/components/schemas/download_sources.yaml index d963e82089303..969f5851294d8 100644 --- a/x-pack/plugins/fleet/common/openapi/components/schemas/download_sources.yaml +++ b/x-pack/plugins/fleet/common/openapi/components/schemas/download_sources.yaml @@ -10,7 +10,6 @@ properties: host: type: string required: - - id - is_default - name - host diff --git a/x-pack/plugins/fleet/common/services/routes.ts b/x-pack/plugins/fleet/common/services/routes.ts index 9e6b27703bd2f..faadef1a95c9e 100644 --- a/x-pack/plugins/fleet/common/services/routes.ts +++ b/x-pack/plugins/fleet/common/services/routes.ts @@ -20,6 +20,7 @@ import { APP_API_ROUTES, K8S_API_ROUTES, PRECONFIGURATION_API_ROUTES, + DOWNLOAD_SOURCE_API_ROUTES, } from '../constants'; export const epmRouteService = { @@ -231,3 +232,14 @@ export const enrollmentAPIKeyRouteService = { export const setupRouteService = { getSetupPath: () => SETUP_API_ROUTE, }; + +export const downloadSourceRoutesService = { + getInfoPath: (downloadSourceId: string) => + DOWNLOAD_SOURCE_API_ROUTES.INFO_PATTERN.replace('{sourceId}', downloadSourceId), + getUpdatePath: (downloadSourceId: string) => + DOWNLOAD_SOURCE_API_ROUTES.UPDATE_PATTERN.replace('{sourceId}', downloadSourceId), + getListPath: () => DOWNLOAD_SOURCE_API_ROUTES.LIST_PATTERN, + getDeletePath: (downloadSourceId: string) => + DOWNLOAD_SOURCE_API_ROUTES.DELETE_PATTERN.replace('{sourceId}', downloadSourceId), + getCreatePath: () => DOWNLOAD_SOURCE_API_ROUTES.CREATE_PATTERN, +}; diff --git a/x-pack/plugins/fleet/common/types/rest_spec/download_sources.ts b/x-pack/plugins/fleet/common/types/rest_spec/download_sources.ts index 13af84f372c2f..bb66908b3bddd 100644 --- a/x-pack/plugins/fleet/common/types/rest_spec/download_sources.ts +++ b/x-pack/plugins/fleet/common/types/rest_spec/download_sources.ts @@ -5,7 +5,7 @@ * 2.0. */ -import type { DownloadSourceBase } from '../models'; +import type { DownloadSourceBase, DownloadSource } from '../models'; import type { ListResult } from './common'; @@ -28,18 +28,17 @@ export interface PutDownloadSourceRequest { outputId: string; }; body: { - id: string; name: string; - hosts: string; + host: string; is_default?: boolean; }; } export interface PostDownloadSourceRequest { body: { - id: string; + id?: string; name: string; - hosts: string; + host: string; is_default?: boolean; }; } @@ -48,4 +47,4 @@ export interface PutDownloadSourceResponse { item: DownloadSourceBase; } -export type GetDownloadSourceResponse = ListResult; +export type GetDownloadSourceResponse = ListResult; diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/hooks.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/hooks.tsx index 47c2db3db05a9..ba8d0bf5d568f 100644 --- a/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/hooks.tsx +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/hooks.tsx @@ -10,7 +10,7 @@ import { i18n } from '@kbn/i18n'; import { FormattedMessage } from '@kbn/i18n-react'; import { EuiText, EuiSpacer } from '@elastic/eui'; -import { useGetOutputs, useLicense } from '../../../../hooks'; +import { useGetOutputs, useLicense, useGetDownloadSources } from '../../../../hooks'; import { LICENCE_FOR_PER_POLICY_OUTPUT, FLEET_APM_PACKAGE, @@ -20,6 +20,7 @@ import type { NewAgentPolicy, AgentPolicy } from '../../../../types'; // The super select component do not support null or '' as a value export const DEFAULT_OUTPUT_VALUE = '@@##DEFAULT_OUTPUT_VALUE##@@'; +export const DEFAULT_DOWNLOAD_SOURCE_VALUE = '@@##DEFAULT_DOWNLOAD_SOURCE_VALUE##@@'; function getOutputLabel(name: string, disabledMessage?: React.ReactNode) { if (!disabledMessage) { @@ -136,3 +137,54 @@ export function useOutputOptions(agentPolicy: Partial) { + const downloadSourcesRequest = useGetDownloadSources(); + + const dataDownloadSourceOptions = useMemo(() => { + if (downloadSourcesRequest.isLoading || !downloadSourcesRequest.data) { + return []; + } + + const defaultDownloadSource = downloadSourcesRequest.data.items.find((item) => item.is_default); + const defaultDownloadSourceName = defaultDownloadSource?.name; + + return [ + getDefaultDownloadSource(defaultDownloadSourceName), + ...downloadSourcesRequest.data.items + .filter((item) => !item.is_default) + .map((item) => { + return { + value: item.id, + inputDisplay: item.name, + }; + }), + ]; + }, [downloadSourcesRequest]); + + return useMemo( + () => ({ + dataDownloadSourceOptions, + isLoading: downloadSourcesRequest.isLoading, + }), + [dataDownloadSourceOptions, downloadSourcesRequest.isLoading] + ); +} + +function getDefaultDownloadSource( + defaultDownloadSourceName?: string, + defaultDownloadSourceDisabled?: boolean, + defaultDownloadSourceDisabledMessage?: React.ReactNode +) { + return { + inputDisplay: getOutputLabel( + i18n.translate('xpack.fleet.agentPolicy.downloadSourcesOptions.defaultOutputText', { + defaultMessage: 'Default (currently {defaultDownloadSourceName})', + values: { defaultDownloadSourceName }, + }), + defaultDownloadSourceDisabledMessage + ), + value: DEFAULT_DOWNLOAD_SOURCE_VALUE, + disabled: defaultDownloadSourceDisabled, + }; +} diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/index.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/index.tsx index e1c6bbafa21a7..3662465054c49 100644 --- a/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/index.tsx +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/components/agent_policy_advanced_fields/index.tsx @@ -33,7 +33,12 @@ import type { ValidationResults } from '../agent_policy_validation'; import { policyHasFleetServer } from '../../../../services'; -import { useOutputOptions, DEFAULT_OUTPUT_VALUE } from './hooks'; +import { + useOutputOptions, + useDownloadSourcesOptions, + DEFAULT_OUTPUT_VALUE, + DEFAULT_DOWNLOAD_SOURCE_VALUE, +} from './hooks'; interface Props { agentPolicy: Partial; @@ -57,6 +62,8 @@ export const AgentPolicyAdvancedOptionsContent: React.FunctionComponent = monitoringOutputOptions, isLoading: isLoadingOptions, } = useOutputOptions(agentPolicy); + const { dataDownloadSourceOptions, isLoading: isLoadingDownloadSources } = + useDownloadSourcesOptions(agentPolicy); // agent monitoring checkbox group can appear multiple times in the DOM, ids have to be unique to work correctly const monitoringCheckboxIdSuffix = Date.now(); @@ -361,6 +368,46 @@ export const AgentPolicyAdvancedOptionsContent: React.FunctionComponent = /> + + + + } + description={ + + } + > + + { + updateAgentPolicy({ + download_source_id: e !== DEFAULT_DOWNLOAD_SOURCE_VALUE ? e : null, + }); + }} + options={dataDownloadSourceOptions} + data-test-subj="agentPolicyForm.downloadSource.select" + /> + + {isEditing && 'id' in agentPolicy && !agentPolicy.is_managed ? ( = {(deleteAgentPolicyPrompt) => { return ( deleteAgentPolicyPrompt(agentPolicy.id!, onDelete)} > diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/details_page/components/settings/index.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/details_page/components/settings/index.tsx index 13b7135d0c095..87614fc6413c8 100644 --- a/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/details_page/components/settings/index.tsx +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/agent_policy/details_page/components/settings/index.tsx @@ -85,6 +85,8 @@ export const SettingsView = memo<{ agentPolicy: AgentPolicy }>( data_output_id, // eslint-disable-next-line @typescript-eslint/naming-convention monitoring_output_id, + // eslint-disable-next-line @typescript-eslint/naming-convention + download_source_id, } = agentPolicy; const { data, error } = await sendUpdateAgentPolicy(agentPolicy.id, { name, @@ -94,6 +96,7 @@ export const SettingsView = memo<{ agentPolicy: AgentPolicy }>( unenroll_timeout, data_output_id, monitoring_output_id, + download_source_id, }); if (data) { notifications.toasts.addSuccess( diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/confirm_update.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/confirm_update.tsx new file mode 100644 index 0000000000000..cdc2e00736333 --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/confirm_update.tsx @@ -0,0 +1,75 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import React from 'react'; +import { FormattedMessage } from '@kbn/i18n-react'; + +import type { DownloadSource } from '../../../../types'; + +import type { useConfirmModal } from '../../hooks/use_confirm_modal'; + +import { getCountsForDownloadSource } from './services/get_count'; + +interface ConfirmDescriptionProps { + downloadSource: DownloadSource; + agentCount: number; + agentPolicyCount: number; +} + +const ConfirmDescription: React.FunctionComponent = ({ + downloadSource, + agentCount, + agentPolicyCount, +}) => ( + {downloadSource.name}, + agents: ( + + + + ), + policies: ( + + + + ), + }} + /> +); + +export async function confirmUpdate( + downloadSource: DownloadSource, + confirm: ReturnType['confirm'] +) { + const { agentCount, agentPolicyCount } = await getCountsForDownloadSource(downloadSource); + return confirm( + , + + ); +} diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.test.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.test.tsx new file mode 100644 index 0000000000000..464d0601ced2b --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.test.tsx @@ -0,0 +1,52 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; + +import type { DownloadSource } from '../../../../types'; +import { createFleetTestRendererMock } from '../../../../../../mock'; + +import { EditDownloadSourceFlyout } from '.'; + +jest.mock('../../../../../../hooks/use_fleet_status', () => ({ + FleetStatusProvider: (props: any) => { + return props.children; + }, + useFleetStatus: jest.fn().mockReturnValue({}), +})); + +function renderFlyout(downloadSource?: DownloadSource) { + const renderer = createFleetTestRendererMock(); + + const comp = renderer.render( + {}} /> + ); + + return { comp }; +} +describe('EditOutputFlyout', () => { + it('should render the flyout if there is no download source provided', async () => { + const { comp } = renderFlyout(); + expect(comp.queryByLabelText('Name')).not.toBeNull(); + expect(comp.queryByLabelText('Host')).not.toBeNull(); + expect(comp.queryByPlaceholderText('Specify name')).not.toBeNull(); + expect(comp.queryByPlaceholderText('Specify host')).not.toBeNull(); + }); + + it('should render the flyout if the provided download source is valid', async () => { + const { comp } = renderFlyout({ + name: 'New Host', + host: 'https://test-registry.co/path', + id: 'test-ds-1', + is_default: false, + }); + expect(comp.queryByLabelText('Name')).not.toBeNull(); + expect(comp.queryByLabelText('Host')).not.toBeNull(); + expect(comp.queryByDisplayValue('New Host')).not.toBeNull(); + expect(comp.queryByDisplayValue('https://test-registry.co/path')).not.toBeNull(); + }); +}); diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.tsx new file mode 100644 index 0000000000000..2ede5f992bc02 --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/index.tsx @@ -0,0 +1,179 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { FormattedMessage } from '@kbn/i18n-react'; +import { + EuiFlyout, + EuiFlyoutBody, + EuiFlyoutHeader, + EuiTitle, + EuiFlyoutFooter, + EuiFlexGroup, + EuiFlexItem, + EuiButtonEmpty, + EuiButton, + EuiForm, + EuiFormRow, + EuiFieldText, + EuiLink, + EuiSwitch, + EuiSpacer, +} from '@elastic/eui'; +import { i18n } from '@kbn/i18n'; + +import type { DownloadSource } from '../../../../types'; +import { FLYOUT_MAX_WIDTH } from '../../constants'; +import { useBreadcrumbs, useStartServices } from '../../../../hooks'; + +import { useDowloadSourceFlyoutForm } from './use_download_source_flyout_form'; + +export interface EditDownloadSourceFlyoutProps { + downloadSource?: DownloadSource; + onClose: () => void; +} + +export const EditDownloadSourceFlyout: React.FunctionComponent = ({ + onClose, + downloadSource, +}) => { + useBreadcrumbs('settings'); + const form = useDowloadSourceFlyoutForm(onClose, downloadSource); + const inputs = form.inputs; + const { docLinks } = useStartServices(); + + return ( + + + +

+ {!downloadSource ? ( + + ) : ( + + )} +

+ + + + + + } + {...inputs.nameInput.formRowProps} + > + + + + + + ), + }} + /> + } + label={ + + } + > + + + + + + } + /> + + + + + + + + + + + + + + + + + + + ); +}; diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.test.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.test.tsx new file mode 100644 index 0000000000000..fb40dcce75945 --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.test.tsx @@ -0,0 +1,74 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { DownloadSource } from '../../../../../types'; +import { sendGetAgents, sendGetAgentPolicies } from '../../../../../hooks'; + +import { getCountsForDownloadSource } from './get_count'; + +jest.mock('../../../../../hooks', () => ({ + ...jest.requireActual('../../../../../hooks'), + sendGetAgents: jest.fn(), + sendGetAgentPolicies: jest.fn(), +})); + +const mockedSendGetAgents = sendGetAgents as jest.Mock; +const mockedSendGetAgentPolicies = sendGetAgentPolicies as jest.Mock; + +describe('getCountsForDownloadSource', () => { + const downloadSource: DownloadSource = { + name: 'New Host', + host: 'https://test-registry.co/path', + id: 'test-ds-1', + is_default: false, + }; + + beforeEach(async () => { + const mapAgents = (ids: string[]) => + ids.map((agent) => ({ + id: agent, + active: true, + policy_id: 'policy1', + local_metadata: { host: { hostname: agent } }, + })); + mockedSendGetAgents.mockResolvedValueOnce({ + data: { + items: mapAgents(['agent1', 'agent2', 'agent3', 'agent4', 'agent5']), + total: 6, + totalInactive: 0, + }, + }); + + mockedSendGetAgentPolicies.mockResolvedValueOnce({ + data: { + items: [ + { + name: 'Agent policy 1', + namespace: 'default', + description: '', + monitoring_enabled: ['logs', 'metrics'], + download_source_id: 'test-ds-1', + }, + { + name: 'Agent policy 2', + namespace: 'default', + description: '', + monitoring_enabled: ['logs', 'metrics'], + download_source_id: 'test-ds-1', + }, + ], + }, + }); + }); + + it('return agentPolicyCount and agentCount', async () => { + expect(await getCountsForDownloadSource(downloadSource)).toEqual({ + agentCount: 6, + agentPolicyCount: 2, + }); + }); +}); diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.tsx new file mode 100644 index 0000000000000..ce9428771c0e4 --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/services/get_count.tsx @@ -0,0 +1,45 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { sendGetAgentPolicies, sendGetAgents } from '../../../../../hooks'; +import type { DownloadSource } from '../../../../../types'; +import { AGENT_POLICY_SAVED_OBJECT_TYPE, SO_SEARCH_LIMIT } from '../../../../../constants'; + +export async function getCountsForDownloadSource(downloadSource: DownloadSource) { + let kuery = `${AGENT_POLICY_SAVED_OBJECT_TYPE}.download_source_id:"${downloadSource.id}"`; + if (downloadSource.is_default) { + kuery += ` or (not ${AGENT_POLICY_SAVED_OBJECT_TYPE}.download_source_id:*)`; + } + const agentPolicies = await sendGetAgentPolicies({ + kuery, + page: 1, + perPage: SO_SEARCH_LIMIT, + }); + + if (agentPolicies.error) { + throw agentPolicies.error; + } + const agentPolicyCount = agentPolicies.data?.items?.length ?? 0; + + let agentCount = 0; + if (agentPolicyCount > 0) { + const agents = await sendGetAgents({ + page: 1, + perPage: 0, + showInactive: false, + kuery: agentPolicies.data?.items.map((policy) => `policy_id:"${policy.id}"`).join(' or '), + }); + + if (agents.error) { + throw agents.error; + } + + agentCount = agents.data?.total ?? 0; + } + + return { agentPolicyCount, agentCount }; +} diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_delete_download_source.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_delete_download_source.tsx new file mode 100644 index 0000000000000..ecd3130499572 --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_delete_download_source.tsx @@ -0,0 +1,118 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React, { useCallback } from 'react'; +import { FormattedMessage } from '@kbn/i18n-react'; +import { i18n } from '@kbn/i18n'; + +import { sendDeleteDownloadSource, useStartServices } from '../../../../hooks'; +import type { DownloadSource } from '../../../../types'; + +import { useConfirmModal } from '../../hooks/use_confirm_modal'; + +import { getCountsForDownloadSource } from './services/get_count'; + +const ConfirmTitle = () => ( + +); + +interface ConfirmDeleteDescriptionProps { + downloadSource: DownloadSource; + agentCount: number; + agentPolicyCount: number; +} + +const ConfirmDeleteDescription: React.FunctionComponent = ({ + downloadSource, + agentCount, + agentPolicyCount, +}) => ( + {downloadSource.name}, + agents: ( + + + + ), + policies: ( + + + + ), + }} + /> +); + +export function useDeleteDownloadSource(onSuccess: () => void) { + const { confirm } = useConfirmModal(); + const { notifications } = useStartServices(); + const deleteDownloadSource = useCallback( + async (downloadSource: DownloadSource) => { + try { + const { agentCount, agentPolicyCount } = await getCountsForDownloadSource(downloadSource); + + const isConfirmed = await confirm( + , + , + { + buttonColor: 'danger', + confirmButtonText: i18n.translate( + 'xpack.fleet.settings.deleteDownloadSource.confirmButtonLabel', + { + defaultMessage: 'Delete and deploy', + } + ), + } + ); + + if (!isConfirmed) { + return; + } + + const res = await sendDeleteDownloadSource(downloadSource.id); + + if (res.error) { + throw res.error; + } + + onSuccess(); + } catch (err) { + notifications.toasts.addError(err, { + title: i18n.translate('xpack.fleet.settings.deleteDownloadSource.errorToastTitle', { + defaultMessage: 'Error deleting agent binary source.', + }), + }); + } + }, + [confirm, notifications.toasts, onSuccess] + ); + + return { deleteDownloadSource }; +} diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.test.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.test.tsx new file mode 100644 index 0000000000000..25136b0cb16db --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.test.tsx @@ -0,0 +1,48 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { validateHost } from './use_download_source_flyout_form'; + +describe('Download source form validation', () => { + describe('validateHost', () => { + it('should not work without any urls', () => { + const res = validateHost(''); + + expect(res).toEqual(['Host is required']); + }); + + it('should work with valid url with https protocol', () => { + const res = validateHost('https://test.co:9200'); + + expect(res).toBeUndefined(); + }); + + it('should work with valid url with http protocol', () => { + const res = validateHost('http://test.co'); + + expect(res).toBeUndefined(); + }); + + it('should work with valid url with path', () => { + const res = validateHost('http://test.co/download'); + + expect(res).toBeUndefined(); + }); + + it('should return an error with invalid url', () => { + const res = validateHost('toto'); + + expect(res).toEqual(['Invalid URL']); + }); + + it('should return an error with url with invalid port', () => { + const res = validateHost('https://test.fr:qwerty9200'); + + expect(res).toEqual(['Invalid URL']); + }); + }); +}); diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.tsx new file mode 100644 index 0000000000000..ea965646cd6be --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_flyout/use_download_source_flyout_form.tsx @@ -0,0 +1,144 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useCallback, useState } from 'react'; + +import { i18n } from '@kbn/i18n'; + +import { + sendPostDownloadSource, + useInput, + useSwitchInput, + useStartServices, + sendPutDownloadSource, +} from '../../../../hooks'; +import type { DownloadSource, PostDownloadSourceRequest } from '../../../../types'; +import { useConfirmModal } from '../../hooks/use_confirm_modal'; + +import { confirmUpdate } from './confirm_update'; + +export function useDowloadSourceFlyoutForm(onSuccess: () => void, downloadSource?: DownloadSource) { + const [isLoading, setIsloading] = useState(false); + const { notifications } = useStartServices(); + const { confirm } = useConfirmModal(); + + const nameInput = useInput(downloadSource?.name ?? '', validateName); + + const defaultDownloadSourceInput = useSwitchInput( + downloadSource?.is_default ?? false, + downloadSource?.is_default + ); + + const hostInput = useInput(downloadSource?.host ?? '', validateHost); + + const inputs = { + nameInput, + hostInput, + defaultDownloadSourceInput, + }; + + const hasChanged = Object.values(inputs).some((input) => input.hasChanged); + + const validate = useCallback(() => { + const nameInputValid = nameInput.validate(); + const hostValid = hostInput.validate(); + + return nameInputValid && hostValid; + }, [nameInput, hostInput]); + + const submit = useCallback(async () => { + try { + if (!validate()) { + return; + } + setIsloading(true); + + const data: PostDownloadSourceRequest['body'] = { + name: nameInput.value, + host: hostInput.value, + is_default: defaultDownloadSourceInput.value, + }; + + if (downloadSource) { + // Update + if (!(await confirmUpdate(downloadSource, confirm))) { + setIsloading(false); + return; + } + + const res = await sendPutDownloadSource(downloadSource.id, data); + if (res.error) { + throw res.error; + } + } else { + // Create + const res = await sendPostDownloadSource(data); + if (res.error) { + throw res.error; + } + } + + onSuccess(); + setIsloading(false); + } catch (err) { + setIsloading(false); + notifications.toasts.addError(err, { + title: i18n.translate('xpack.fleet.settings.dowloadSourceFlyoutForm.errorToastTitle', { + defaultMessage: 'Error while saving binary source', + }), + }); + } + }, [ + confirm, + defaultDownloadSourceInput.value, + downloadSource, + hostInput.value, + nameInput.value, + notifications.toasts, + onSuccess, + validate, + ]); + + return { + inputs, + submit, + isLoading, + isDisabled: isLoading || (downloadSource && !hasChanged), + }; +} + +function validateName(value: string) { + if (!value || value === '') { + return [ + i18n.translate('xpack.fleet.settings.dowloadSourceFlyoutForm.nameIsRequiredErrorMessage', { + defaultMessage: 'Name is required', + }), + ]; + } +} + +export function validateHost(value: string) { + try { + if (!value || value === '') { + return [ + i18n.translate('xpack.fleet.settings.dowloadSourceFlyoutForm.HostIsRequiredErrorMessage', { + defaultMessage: 'Host is required', + }), + ]; + } + const urlParsed = new URL(value); + if (!['http:', 'https:'].includes(urlParsed.protocol)) { + throw new Error('Invalid protocol'); + } + } catch (error) { + return [ + i18n.translate('xpack.fleet.settings.dowloadSourceFlyoutForm.hostError', { + defaultMessage: 'Invalid URL', + }), + ]; + } +} diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_table/index.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_table/index.tsx new file mode 100644 index 0000000000000..87034bf900fda --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/download_source_table/index.tsx @@ -0,0 +1,140 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React, { useMemo } from 'react'; +import styled from 'styled-components'; +import { EuiBasicTable, EuiButtonIcon, EuiFlexGroup, EuiFlexItem, EuiCheckbox } from '@elastic/eui'; +import type { EuiBasicTableColumn } from '@elastic/eui'; +import { i18n } from '@kbn/i18n'; + +import { useLink } from '../../../../hooks'; +import type { DownloadSource } from '../../../../types'; + +export interface DownloadSourceTableProps { + downloadSources: DownloadSource[]; + deleteDownloadSource: (ds: DownloadSource) => void; +} + +const NameFlexItemWithMaxWidth = styled(EuiFlexItem)` + max-width: 250px; +`; + +// Allow child to be truncated +const FlexGroupWithMinWidth = styled(EuiFlexGroup)` + min-width: 0px; +`; + +export const DownloadSourceTable: React.FunctionComponent = ({ + downloadSources, + deleteDownloadSource, +}) => { + const { getHref } = useLink(); + + const columns = useMemo((): Array> => { + return [ + { + render: (downloadSource: DownloadSource) => ( + + +

+ {downloadSource.name} +

+
+
+ ), + width: '288px', + name: i18n.translate('xpack.fleet.settings.downloadSourcesTable.nameColumnTitle', { + defaultMessage: 'Name', + }), + }, + { + truncateText: true, + render: (downloadSource: DownloadSource) => ( + + +

+ {downloadSource.host} +

+
+
+ ), + name: i18n.translate('xpack.fleet.settings.downloadSourcesTable.hostColumnTitle', { + defaultMessage: 'Host', + }), + }, + { + render: (downloadSource: DownloadSource) => ( + undefined} + /> + ), + width: '200px', + name: i18n.translate('xpack.fleet.settings.downloadSourcesTable.defaultColumnTitle', { + defaultMessage: 'Default', + }), + }, + { + width: '68px', + render: (downloadSource: DownloadSource) => { + const isDeleteVisible = !downloadSource.is_default; + + return ( + + + {isDeleteVisible && ( + deleteDownloadSource(downloadSource)} + title={i18n.translate( + 'xpack.fleet.settings.downloadSourceSection.deleteButtonTitle', + { + defaultMessage: 'Delete', + } + )} + data-test-subj="editDownloadSourceTable.delete.btn" + /> + )} + + + + + + ); + }, + name: i18n.translate('xpack.fleet.settings.downloadSourceSection.actionsColumnTitle', { + defaultMessage: 'Actions', + }), + }, + ]; + }, [deleteDownloadSource, getHref]); + + return ; +}; diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/agent_binary_section.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/agent_binary_section.tsx new file mode 100644 index 0000000000000..ae9a42a7b2144 --- /dev/null +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/agent_binary_section.tsx @@ -0,0 +1,62 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { EuiTitle, EuiText, EuiSpacer, EuiButtonEmpty } from '@elastic/eui'; +import { FormattedMessage } from '@kbn/i18n-react'; + +import { useLink } from '../../../../hooks'; +import type { DownloadSource } from '../../../../types'; +import { DownloadSourceTable } from '../download_source_table'; + +export interface AgentBinarySectionProps { + downloadSources: DownloadSource[]; + deleteDownloadSource: (ds: DownloadSource) => void; +} + +export const AgentBinarySection: React.FunctionComponent = ({ + downloadSources, + deleteDownloadSource, +}) => { + const { getHref } = useLink(); + + return ( + <> + +

+ +

+
+ + + + + + + + + + + + ); +}; diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/index.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/index.tsx index 7749e3304a6ea..4c5db21725639 100644 --- a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/index.tsx +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/components/settings_page/index.tsx @@ -8,21 +8,26 @@ import React from 'react'; import { EuiSpacer } from '@elastic/eui'; -import type { Output, Settings } from '../../../../types'; +import type { Output, Settings, DownloadSource } from '../../../../types'; import { SettingsSection } from './settings_section'; import { OutputSection } from './output_section'; +import { AgentBinarySection } from './agent_binary_section'; export interface SettingsPageProps { settings: Settings; outputs: Output[]; deleteOutput: (output: Output) => void; + downloadSources: DownloadSource[]; + deleteDownloadSource: (ds: DownloadSource) => void; } export const SettingsPage: React.FunctionComponent = ({ settings, outputs, deleteOutput, + downloadSources, + deleteDownloadSource, }) => { return ( <> @@ -30,6 +35,11 @@ export const SettingsPage: React.FunctionComponent = ({ + + ); }; diff --git a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/index.tsx b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/index.tsx index c586e88261940..7a94d9ef4bc79 100644 --- a/x-pack/plugins/fleet/public/applications/fleet/sections/settings/index.tsx +++ b/x-pack/plugins/fleet/public/applications/fleet/sections/settings/index.tsx @@ -9,7 +9,7 @@ import React, { useCallback } from 'react'; import { EuiPortal } from '@elastic/eui'; import { Router, Route, Switch, useHistory, Redirect } from 'react-router-dom'; -import { useBreadcrumbs, useGetOutputs, useGetSettings } from '../../hooks'; +import { useBreadcrumbs, useGetOutputs, useGetSettings, useGetDownloadSources } from '../../hooks'; import { FLEET_ROUTING_PATHS, pagePathGetters } from '../../constants'; import { DefaultLayout } from '../../layouts'; import { Loading } from '../../components'; @@ -19,6 +19,8 @@ import { withConfirmModalProvider } from './hooks/use_confirm_modal'; import { FleetServerHostsFlyout } from './components/fleet_server_hosts_flyout'; import { EditOutputFlyout } from './components/edit_output_flyout'; import { useDeleteOutput } from './hooks/use_delete_output'; +import { EditDownloadSourceFlyout } from './components/download_source_flyout'; +import { useDeleteDownloadSource } from './components/download_source_flyout/use_delete_download_source'; export const SettingsApp = withConfirmModalProvider(() => { useBreadcrumbs('settings'); @@ -26,23 +28,29 @@ export const SettingsApp = withConfirmModalProvider(() => { const settings = useGetSettings(); const outputs = useGetOutputs(); + const downloadSources = useGetDownloadSources(); const { deleteOutput } = useDeleteOutput(outputs.resendRequest); + const { deleteDownloadSource } = useDeleteDownloadSource(downloadSources.resendRequest); const resendSettingsRequest = settings.resendRequest; const resendOutputRequest = outputs.resendRequest; + const resendDownloadSourceRequest = downloadSources.resendRequest; const onCloseCallback = useCallback(() => { resendSettingsRequest(); resendOutputRequest(); + resendDownloadSourceRequest(); history.replace(pagePathGetters.settings()[1]); - }, [history, resendSettingsRequest, resendOutputRequest]); + }, [resendSettingsRequest, resendOutputRequest, resendDownloadSourceRequest, history]); if ( (settings.isLoading && settings.isInitialRequest) || !settings.data?.item || (outputs.isLoading && outputs.isInitialRequest) || - !outputs.data?.items + !outputs.data?.items || + (downloadSources.isLoading && downloadSources.isInitialRequest) || + !downloadSources.data?.items ) { return ( @@ -71,7 +79,6 @@ export const SettingsApp = withConfirmModalProvider(() => { {(route: { match: { params: { outputId: string } } }) => { const output = outputs.data?.items.find((o) => route.match.params.outputId === o.id); - if (!output) { return ; } @@ -83,12 +90,38 @@ export const SettingsApp = withConfirmModalProvider(() => { ); }} + + + + + + + {(route: { match: { params: { downloadSourceId: string } } }) => { + const downloadSource = downloadSources.data?.items.find( + (o) => route.match.params.downloadSourceId === o.id + ); + if (!downloadSource) { + return ; + } + + return ( + + + + ); + }} + ); diff --git a/x-pack/plugins/fleet/public/constants/page_paths.ts b/x-pack/plugins/fleet/public/constants/page_paths.ts index e7134f8549e27..479110f2f0142 100644 --- a/x-pack/plugins/fleet/public/constants/page_paths.ts +++ b/x-pack/plugins/fleet/public/constants/page_paths.ts @@ -18,6 +18,7 @@ export type StaticPage = | 'settings' | 'settings_edit_fleet_server_hosts' | 'settings_create_outputs' + | 'settings_create_download_sources' | 'debug'; export type DynamicPage = @@ -38,7 +39,8 @@ export type DynamicPage = | 'agent_list' | 'agent_details' | 'agent_details_logs' - | 'settings_edit_outputs'; + | 'settings_edit_outputs' + | 'settings_edit_download_sources'; export type Page = StaticPage | DynamicPage; @@ -68,6 +70,8 @@ export const FLEET_ROUTING_PATHS = { settings_edit_fleet_server_hosts: '/settings/edit-fleet-server-hosts', settings_create_outputs: '/settings/create-outputs', settings_edit_outputs: '/settings/outputs/:outputId', + settings_create_download_sources: '/settings/create-download-sources', + settings_edit_download_sources: '/settings/downloadSources/:downloadSourceId', debug: '/_debug', // TODO: Move this to the integrations app @@ -191,6 +195,17 @@ export const pagePathGetters: { FLEET_BASE_PATH, FLEET_ROUTING_PATHS.settings_edit_outputs.replace(':outputId', outputId as string), ], + settings_edit_download_sources: ({ downloadSourceId }) => [ + FLEET_BASE_PATH, + FLEET_ROUTING_PATHS.settings_edit_download_sources.replace( + ':downloadSourceId', + downloadSourceId as string + ), + ], settings_create_outputs: () => [FLEET_BASE_PATH, FLEET_ROUTING_PATHS.settings_create_outputs], + settings_create_download_sources: () => [ + FLEET_BASE_PATH, + FLEET_ROUTING_PATHS.settings_create_download_sources, + ], debug: () => [FLEET_BASE_PATH, FLEET_ROUTING_PATHS.debug], }; diff --git a/x-pack/plugins/fleet/public/hooks/use_request/download_source.ts b/x-pack/plugins/fleet/public/hooks/use_request/download_source.ts new file mode 100644 index 0000000000000..2b213501170e1 --- /dev/null +++ b/x-pack/plugins/fleet/public/hooks/use_request/download_source.ts @@ -0,0 +1,55 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { downloadSourceRoutesService } from '../../services'; +import type { + GetDownloadSourceResponse, + PostDownloadSourceRequest, + PutDownloadSourceRequest, +} from '../../types'; + +import { useRequest, sendRequest } from './use_request'; + +export function useGetDownloadSources() { + return useRequest({ + method: 'get', + path: downloadSourceRoutesService.getListPath(), + }); +} + +export function useDefaultDownloadSource() { + const downloadSourcesRequest = useGetDownloadSources(); + const downloadSource = downloadSourcesRequest.data?.items.find((o) => o.is_default); + + return { downloadSource, refresh: downloadSourcesRequest.resendRequest }; +} + +export function sendPutDownloadSource( + downloadSourceId: string, + body: PutDownloadSourceRequest['body'] +) { + return sendRequest({ + method: 'put', + path: downloadSourceRoutesService.getUpdatePath(downloadSourceId), + body, + }); +} + +export function sendPostDownloadSource(body: PostDownloadSourceRequest['body']) { + return sendRequest({ + method: 'post', + path: downloadSourceRoutesService.getCreatePath(), + body, + }); +} + +export function sendDeleteDownloadSource(downloadSourceId: string) { + return sendRequest({ + method: 'delete', + path: downloadSourceRoutesService.getDeletePath(downloadSourceId), + }); +} diff --git a/x-pack/plugins/fleet/public/hooks/use_request/index.ts b/x-pack/plugins/fleet/public/hooks/use_request/index.ts index 2f700052acd7b..1ca5297cb22a2 100644 --- a/x-pack/plugins/fleet/public/hooks/use_request/index.ts +++ b/x-pack/plugins/fleet/public/hooks/use_request/index.ts @@ -17,3 +17,4 @@ export * from './settings'; export * from './setup'; export * from './app'; export * from './ingest_pipelines'; +export * from './download_source'; diff --git a/x-pack/plugins/fleet/public/services/index.ts b/x-pack/plugins/fleet/public/services/index.ts index 094fe2b66c6c9..b7760134172a9 100644 --- a/x-pack/plugins/fleet/public/services/index.ts +++ b/x-pack/plugins/fleet/public/services/index.ts @@ -40,6 +40,7 @@ export { validationHasErrors, countValidationErrors, getStreamsForInputType, + downloadSourceRoutesService, } from '../../common'; export * from './package_verification'; export * from './pkg_key_from_package_info'; diff --git a/x-pack/plugins/fleet/public/types/index.ts b/x-pack/plugins/fleet/public/types/index.ts index 2cd27e81be9d8..3b02839957b33 100644 --- a/x-pack/plugins/fleet/public/types/index.ts +++ b/x-pack/plugins/fleet/public/types/index.ts @@ -23,6 +23,7 @@ export type { PackagePolicyConfigRecordEntry, PackagePolicyPackage, Output, + DownloadSource, DataStream, Settings, CurrentUpgrade, @@ -121,6 +122,9 @@ export type { PackageSpecCategory, UpdatePackageRequest, UpdatePackageResponse, + GetDownloadSourceResponse, + PostDownloadSourceRequest, + PutDownloadSourceRequest, } from '../../common'; export { entries, ElasticsearchAssetType, KibanaAssetType, InstallStatus } from '../../common'; diff --git a/x-pack/plugins/fleet/server/constants/index.ts b/x-pack/plugins/fleet/server/constants/index.ts index 3123f2910ed54..b86b636059152 100644 --- a/x-pack/plugins/fleet/server/constants/index.ts +++ b/x-pack/plugins/fleet/server/constants/index.ts @@ -61,7 +61,7 @@ export { USER_SETTINGS_TEMPLATE_SUFFIX, PACKAGE_TEMPLATE_SUFFIX, // Download sources - DEFAULT_DOWNLOAD_SOURCE, + DEFAULT_DOWNLOAD_SOURCE_URI, DOWNLOAD_SOURCE_SAVED_OBJECT_TYPE, DEFAULT_DOWNLOAD_SOURCE_ID, } from '../../common'; diff --git a/x-pack/plugins/fleet/server/integration_tests/__snapshots__/cloud_preconfiguration.test.ts.snap b/x-pack/plugins/fleet/server/integration_tests/__snapshots__/cloud_preconfiguration.test.ts.snap index fc2ce4eb7145e..ff918248ffb57 100644 --- a/x-pack/plugins/fleet/server/integration_tests/__snapshots__/cloud_preconfiguration.test.ts.snap +++ b/x-pack/plugins/fleet/server/integration_tests/__snapshots__/cloud_preconfiguration.test.ts.snap @@ -4,7 +4,7 @@ exports[`Fleet preconfiguration reset Preconfigured cloud policy With a full pre Object { "agent": Object { "download": Object { - "source_uri": "https://artifacts.elastic.co", + "source_uri": "https://artifacts.elastic.co/downloads/beats/elastic-agent", }, "monitoring": Object { "enabled": false, diff --git a/x-pack/plugins/fleet/server/services/download_source.ts b/x-pack/plugins/fleet/server/services/download_source.ts index c189ac1a23019..7a6df1d67a7f8 100644 --- a/x-pack/plugins/fleet/server/services/download_source.ts +++ b/x-pack/plugins/fleet/server/services/download_source.ts @@ -8,7 +8,7 @@ import type { SavedObjectsClientContract, SavedObject } from '@kbn/core/server'; import { DOWNLOAD_SOURCE_SAVED_OBJECT_TYPE, - DEFAULT_DOWNLOAD_SOURCE, + DEFAULT_DOWNLOAD_SOURCE_URI, DEFAULT_DOWNLOAD_SOURCE_ID, } from '../constants'; @@ -151,9 +151,9 @@ class DownloadSourceService { if (!defaultDS) { const newDefaultDS: DownloadSourceBase = { - name: 'default', + name: 'Elastic Artifacts', is_default: true, - host: DEFAULT_DOWNLOAD_SOURCE, + host: DEFAULT_DOWNLOAD_SOURCE_URI, }; return await this.create(soClient, newDefaultDS, { diff --git a/x-pack/test/fleet_api_integration/apis/download_sources/crud.ts b/x-pack/test/fleet_api_integration/apis/download_sources/crud.ts index af9a109ed62ce..e8afeec2632c5 100644 --- a/x-pack/test/fleet_api_integration/apis/download_sources/crud.ts +++ b/x-pack/test/fleet_api_integration/apis/download_sources/crud.ts @@ -50,9 +50,9 @@ export default function (providerContext: FtrProviderContext) { expect(downloadSource.items[0]).to.eql({ id: 'fleet-default-download-source', - name: 'default', + name: 'Elastic Artifacts', is_default: true, - host: 'https://artifacts.elastic.co', + host: 'https://artifacts.elastic.co/downloads/beats/elastic-agent', }); }); }); @@ -66,9 +66,9 @@ export default function (providerContext: FtrProviderContext) { expect(downloadSource).to.eql({ item: { id: 'fleet-default-download-source', - name: 'default', + name: 'Elastic Artifacts', is_default: true, - host: 'https://artifacts.elastic.co', + host: 'https://artifacts.elastic.co/downloads/beats/elastic-agent', }, }); }); From a410ec9aafe552aa59e34dd2f40dd71cf41599e0 Mon Sep 17 00:00:00 2001 From: Tre Date: Thu, 14 Jul 2022 10:33:12 +0100 Subject: [PATCH 012/111] [Archive Migrations] x-pack..kibana_scripted_fields_on_logstash (#136264) * [Archive Migrations] x-pack..kibana_scripted_fields_on_logstash Replaces the old es archive with kbn archive. Change test to use new archive. Helps with: https://github.com/elastic/kibana/issues/102552 * Drop --- .../apps/discover/async_scripted_fields.js | 6 +- .../data.json.gz | Bin 2803 -> 0 bytes .../mappings.json | 2717 ----------------- .../kibana_scripted_fields_on_logstash.json | 35 + 4 files changed, 38 insertions(+), 2720 deletions(-) delete mode 100644 x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash/data.json.gz delete mode 100644 x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash/mappings.json create mode 100644 x-pack/test/functional/fixtures/kbn_archiver/kibana_scripted_fields_on_logstash.json diff --git a/x-pack/test/functional/apps/discover/async_scripted_fields.js b/x-pack/test/functional/apps/discover/async_scripted_fields.js index 2c18051405964..ba670ad78aa32 100644 --- a/x-pack/test/functional/apps/discover/async_scripted_fields.js +++ b/x-pack/test/functional/apps/discover/async_scripted_fields.js @@ -23,8 +23,8 @@ export default function ({ getService, getPageObjects }) { this.tags(['skipFirefox']); before(async function () { - await esArchiver.load( - 'x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash' + await kibanaServer.importExport.load( + 'x-pack/test/functional/fixtures/kbn_archiver/kibana_scripted_fields_on_logstash' ); await esArchiver.loadIfNeeded('x-pack/test/functional/es_archives/logstash_functional'); await security.testUser.setRoles(['test_logstash_reader', 'global_discover_read']); @@ -39,7 +39,7 @@ export default function ({ getService, getPageObjects }) { await kibanaServer.uiSettings.replace({}); await kibanaServer.uiSettings.update({}); await esArchiver.unload('x-pack/test/functional/es_archives/logstash_functional'); - await esArchiver.load('x-pack/test/functional/es_archives/empty_kibana'); + await kibanaServer.savedObjects.cleanStandardList(); await security.testUser.restoreDefaults(); }); diff --git a/x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash/data.json.gz b/x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash/data.json.gz deleted file mode 100644 index 1e57c64f2d7df50ea09c021584b890c953d78cb6..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2803 zcmd6p`9Bj51INkD+{Ys2zHc?gzC`k6Gb1Exa^ECGsOGB3mboG$M2#pEqGA|1rx0?? z)!b)Bj?Cu!eO}Km&!6yoUa!wD@1H)uy+1NoZkGS#6z`^M@NJ5L1f$43aTG{FVVCGR z(DK5_T1w#XR>;&HKZSHoc{v_$QzwzP^D)0?fhIxRBY<7PDT(d+nX_ZRZrhxGp5Ge*j$MG-1$NOE(P7 zhajfD1)Q}UOU5M42}u=!9!f<5;@2ee%fb)(y%%2E^;bkCO7N2Gs!*fX(^i+u)9gk=)-s8AGF6I-N4p^VoItzLc0g=1Bl3|XRaIh zduvG{KP{4u^%N=LE*!W;jeX+%y|tg6fzO)Eo6;S1n0!i2*3Zt`j#awby{|rIxGcl@ zff+(iFKh2GDk|>o3>qkBXL&!s8S06DrJ-jXpQFLmX%7C8m@9Lw*leM!gA6XZ=Y_n^ z_jb@PeEL!!f1B*D4h+dE@! z^x+ET6TS*J$Qw0+IlJq>*V2sLoQ(S7fTQw*UrUWYsi;nW{t{Hj>t!&e;N+y!CI$(8 z%Alh8<%1!o%<}V8VXG~zyQ$5WCV%-^maqGD#I@G+nQTLD2e zvkVM{&di+YXPsjIghiEi-lr*PYz8dKp74bUIwRk=&2&8-d2FpKH_n%FrpvU*Yax9? z25!t~%+eBd85F?|$EN#d$TOwQmdQQC+jOGggr)86*4oaZHl%ytt3kW0ONd^9BPxFV zrSx4vpx0RjG;>_h&oCXl(J`-s3M-b1=8)7v-d^S&Sb9~nAiiyv)gcbLS<&2KdhbqE zIXvQbIn>9zKlGdXH_B^NuX&==0v#Hexm<{K>`#!U}kFpnbZ3KQT zf{1^S#@dP%b2h*25I~gI`#BcL3`MnmXkf30j-4QATcy{t>Goy8=vUfg_zl%3nJt!2Ao)pTbTpo8+dc)(m>d6wb*U0Ww8E5^?UVIq(iLCcqlqjUBow44^0 zU;z!}7|w>=i6#|4VHQ32UJFKw&|;?7L0P9ACT+LyU-+!h0iQ!T`D06?;X8{!n5-i@ zcBJuj!BB_Xx&T#j6TaLLUmYy*C?+>dt#tNEyQu^UxDpt20MP7xxAx^B3)4s5N-}DIEgIf&6-@r>Gz%*JtQ;vwfF&da_=p zsI*7KF9}DcX}er`%2zxvJ55c>*ZiG^8o0?zUMkr2B&J z)u=-sBJimNGM)$*x2Tog&1iRM@OQCa?9*G}$nh3X)AWVn z0wpoXIHX+=d{YRo{-A25x)PSGECclkI)n39B~HM-wttoW{^1d8zFMwwa`F7pZfm`E ziR*#C80&T$ldayzHn6HhDY@k+LBj04PNKR7=b?Zq?hUfK6k6MVHHG({$i?e#Ci|{C z->@yie(PVa0b#QW=TQOO|CcmQ1?L8vBqV{OvC>JI2Rq?UX4U?mt z(7Bi*fe6I64D{*P{;Nw<2Q+_a_U*n5pD-pDL9fMzq%)S__v~0|kkc`q-xPnuaae@l zVk9bG^o;NgkeG%h?G`i94CbV`L`KXz4c&fQ@n4$N%Rvelei5ye1tRr!OAMt2w zub0g1VE8GcSD~OZHf@NYdP5Dw1a$|a8GMIg8%aThC`?+R9uy!?E}9wmRmHz!VfhD< CVon19 diff --git a/x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash/mappings.json b/x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash/mappings.json deleted file mode 100644 index e0dd6d90eacb4..0000000000000 --- a/x-pack/test/functional/es_archives/kibana_scripted_fields_on_logstash/mappings.json +++ /dev/null @@ -1,2717 +0,0 @@ -{ - "type": "index", - "value": { - "aliases": { - ".kibana": { - } - }, - "index": ".kibana_1", - "mappings": { - "_meta": { - "migrationMappingPropertyHashes": { - "action": "6e96ac5e648f57523879661ea72525b7", - "action_task_params": "a9d49f184ee89641044be0ca2950fa3a", - "alert": "7b44fba6773e37c806ce290ea9b7024e", - "apm-indices": "9bb9b2bf1fa636ed8619cbab5ce6a1dd", - "apm-telemetry": "3525d7c22c42bc80f5e6e9cb3f2b26a2", - "application_usage_totals": "c897e4310c5f24b07caaff3db53ae2c1", - "application_usage_transactional": "965839e75f809fefe04f92dc4d99722a", - "canvas-element": "7390014e1091044523666d97247392fc", - "canvas-workpad": "b0a1706d356228dbdcb4a17e6b9eb231", - "cases": "08b8b110dbca273d37e8aef131ecab61", - "cases-comments": "c2061fb929f585df57425102fa928b4b", - "cases-configure": "42711cbb311976c0687853f4c1354572", - "cases-user-actions": "32277330ec6b721abe3b846cfd939a71", - "config": "ae24d22d5986d04124cc6568f771066f", - "dashboard": "d00f614b29a80360e1190193fd333bab", - "file-upload-telemetry": "0ed4d3e1983d1217a30982630897092e", - "graph-workspace": "cd7ba1330e6682e9cc00b78850874be1", - "index-pattern": "66eccb05066c5a89924f48a9e9736499", - "infrastructure-ui-source": "ddc0ecb18383f6b26101a2fadb2dab0c", - "inventory-view": "5299b67717e96502c77babf1c16fd4d3", - "kql-telemetry": "d12a98a6f19a2d273696597547e064ee", - "lens": "21c3ea0763beb1ecb0162529706b88c5", - "lens-ui-telemetry": "509bfa5978586998e05f9e303c07a327", - "maps-telemetry": "268da3a48066123fc5baf35abaa55014", - "metrics-explorer-view": "53c5365793677328df0ccb6138bf3cdd", - "migrationVersion": "4a1746014a75ade3a714e1db5763276f", - "ml-telemetry": "257fd1d4b4fdbb9cb4b8a3b27da201e9", - "namespace": "2f4316de49999235636386fe51dc06c1", - "namespaces": "2f4316de49999235636386fe51dc06c1", - "query": "11aaeb7f5f7fa5bb43f25e18ce26e7d9", - "references": "7997cf5a56cc02bdc9c93361bde732b0", - "sample-data-telemetry": "7d3cfeb915303c9641c59681967ffeb4", - "search": "181661168bbadd1eff5902361e2a0d5c", - "server": "ec97f1c5da1a19609a60874e5af1100c", - "siem-detection-engine-rule-actions": "6569b288c169539db10cb262bf79de18", - "siem-detection-engine-rule-status": "ae783f41c6937db6b7a2ef5c93a9e9b0", - "siem-ui-timeline": "f2d929253ecd06ffbac78b4047f45a86", - "siem-ui-timeline-note": "8874706eedc49059d4cf0f5094559084", - "siem-ui-timeline-pinned-event": "20638091112f0e14f0e443d512301c29", - "space": "c5ca8acafa0beaa4d08d014a97b6bc6b", - "telemetry": "36a616f7026dfa617d6655df850fe16d", - "tsvb-validation-telemetry": "3a37ef6c8700ae6fc97d5c7da00e9215", - "type": "2f4316de49999235636386fe51dc06c1", - "ui-metric": "0d409297dc5ebe1e3a1da691c6ee32e3", - "updated_at": "00da57df13e94e9d98437d13ace4bfe0", - "upgrade-assistant-reindex-operation": "296a89039fc4260292be36b1b005d8f2", - "upgrade-assistant-telemetry": "56702cec857e0a9dacfb696655b4ff7b", - "uptime-dynamic-settings": "a6f3af21b612339cbe6eecc1e5a60871", - "url": "b675c3be8d76ecf029294d51dc7ec65d", - "visualization": "52d7a13ad68a150c4525b292d23e12cc" - } - }, - "dynamic": "strict", - "properties": { - "action": { - "properties": { - "actionTypeId": { - "type": "keyword" - }, - "config": { - "enabled": false, - "type": "object" - }, - "name": { - "fields": { - "keyword": { - "type": "keyword" - } - }, - "type": "text" - }, - "secrets": { - "type": "binary" - } - } - }, - "action_task_params": { - "properties": { - "actionId": { - "type": "keyword" - }, - "apiKey": { - "type": "binary" - }, - "params": { - "enabled": false, - "type": "object" - } - } - }, - "alert": { - "properties": { - "actions": { - "properties": { - "actionRef": { - "type": "keyword" - }, - "actionTypeId": { - "type": "keyword" - }, - "group": { - "type": "keyword" - }, - "params": { - "enabled": false, - "type": "object" - } - }, - "type": "nested" - }, - "alertTypeId": { - "type": "keyword" - }, - "apiKey": { - "type": "binary" - }, - "apiKeyOwner": { - "type": "keyword" - }, - "consumer": { - "type": "keyword" - }, - "createdAt": { - "type": "date" - }, - "createdBy": { - "type": "keyword" - }, - "enabled": { - "type": "boolean" - }, - "muteAll": { - "type": "boolean" - }, - "mutedInstanceIds": { - "type": "keyword" - }, - "name": { - "fields": { - "keyword": { - "type": "keyword" - } - }, - "type": "text" - }, - "params": { - "enabled": false, - "type": "object" - }, - "schedule": { - "properties": { - "interval": { - "type": "keyword" - } - } - }, - "scheduledTaskId": { - "type": "keyword" - }, - "tags": { - "type": "keyword" - }, - "throttle": { - "type": "keyword" - }, - "updatedBy": { - "type": "keyword" - } - } - }, - "apm-indices": { - "properties": { - "error": { - "type": "keyword" - }, - "metric": { - "type": "keyword" - }, - "onboarding": { - "type": "keyword" - }, - "sourcemap": { - "type": "keyword" - }, - "span": { - "type": "keyword" - }, - "transaction": { - "type": "keyword" - } - } - }, - "apm-telemetry": { - "properties": { - "agents": { - "properties": { - "dotnet": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - }, - "go": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - }, - "java": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - }, - "js-base": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - }, - "nodejs": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - }, - "python": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - }, - "ruby": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - }, - "rum-js": { - "properties": { - "agent": { - "properties": { - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "service": { - "properties": { - "framework": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "language": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - }, - "runtime": { - "properties": { - "composite": { - "ignore_above": 1024, - "type": "keyword" - }, - "name": { - "ignore_above": 1024, - "type": "keyword" - }, - "version": { - "ignore_above": 1024, - "type": "keyword" - } - } - } - } - } - } - } - } - }, - "cardinality": { - "properties": { - "transaction": { - "properties": { - "name": { - "properties": { - "all_agents": { - "properties": { - "1d": { - "type": "long" - } - } - }, - "rum": { - "properties": { - "1d": { - "type": "long" - } - } - } - } - } - } - }, - "user_agent": { - "properties": { - "original": { - "properties": { - "all_agents": { - "properties": { - "1d": { - "type": "long" - } - } - }, - "rum": { - "properties": { - "1d": { - "type": "long" - } - } - } - } - } - } - } - } - }, - "counts": { - "properties": { - "agent_configuration": { - "properties": { - "all": { - "type": "long" - } - } - }, - "error": { - "properties": { - "1d": { - "type": "long" - }, - "all": { - "type": "long" - } - } - }, - "max_error_groups_per_service": { - "properties": { - "1d": { - "type": "long" - } - } - }, - "max_transaction_groups_per_service": { - "properties": { - "1d": { - "type": "long" - } - } - }, - "metric": { - "properties": { - "1d": { - "type": "long" - }, - "all": { - "type": "long" - } - } - }, - "onboarding": { - "properties": { - "1d": { - "type": "long" - }, - "all": { - "type": "long" - } - } - }, - "services": { - "properties": { - "1d": { - "type": "long" - } - } - }, - "sourcemap": { - "properties": { - "1d": { - "type": "long" - }, - "all": { - "type": "long" - } - } - }, - "span": { - "properties": { - "1d": { - "type": "long" - }, - "all": { - "type": "long" - } - } - }, - "traces": { - "properties": { - "1d": { - "type": "long" - } - } - }, - "transaction": { - "properties": { - "1d": { - "type": "long" - }, - "all": { - "type": "long" - } - } - } - } - }, - "has_any_services": { - "type": "boolean" - }, - "indices": { - "properties": { - "all": { - "properties": { - "total": { - "properties": { - "docs": { - "properties": { - "count": { - "type": "long" - } - } - }, - "store": { - "properties": { - "size_in_bytes": { - "type": "long" - } - } - } - } - } - } - }, - "shards": { - "properties": { - "total": { - "type": "long" - } - } - } - } - }, - "integrations": { - "properties": { - "ml": { - "properties": { - "all_jobs_count": { - "type": "long" - } - } - } - } - }, - "retainment": { - "properties": { - "error": { - "properties": { - "ms": { - "type": "long" - } - } - }, - "metric": { - "properties": { - "ms": { - "type": "long" - } - } - }, - "onboarding": { - "properties": { - "ms": { - "type": "long" - } - } - }, - "span": { - "properties": { - "ms": { - "type": "long" - } - } - }, - "transaction": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "services_per_agent": { - "properties": { - "dotnet": { - "null_value": 0, - "type": "long" - }, - "go": { - "null_value": 0, - "type": "long" - }, - "java": { - "null_value": 0, - "type": "long" - }, - "js-base": { - "null_value": 0, - "type": "long" - }, - "nodejs": { - "null_value": 0, - "type": "long" - }, - "python": { - "null_value": 0, - "type": "long" - }, - "ruby": { - "null_value": 0, - "type": "long" - }, - "rum-js": { - "null_value": 0, - "type": "long" - } - } - }, - "tasks": { - "properties": { - "agent_configuration": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "agents": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "cardinality": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "groupings": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "indices_stats": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "integrations": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "processor_events": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "services": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - }, - "versions": { - "properties": { - "took": { - "properties": { - "ms": { - "type": "long" - } - } - } - } - } - } - }, - "version": { - "properties": { - "apm_server": { - "properties": { - "major": { - "type": "long" - }, - "minor": { - "type": "long" - }, - "patch": { - "type": "long" - } - } - } - } - } - } - }, - "application_usage_totals": { - "properties": { - "appId": { - "type": "keyword" - }, - "minutesOnScreen": { - "type": "float" - }, - "numberOfClicks": { - "type": "long" - } - } - }, - "application_usage_transactional": { - "properties": { - "appId": { - "type": "keyword" - }, - "minutesOnScreen": { - "type": "float" - }, - "numberOfClicks": { - "type": "long" - }, - "timestamp": { - "type": "date" - } - } - }, - "canvas-element": { - "dynamic": "false", - "properties": { - "@created": { - "type": "date" - }, - "@timestamp": { - "type": "date" - }, - "content": { - "type": "text" - }, - "help": { - "type": "text" - }, - "image": { - "type": "text" - }, - "name": { - "fields": { - "keyword": { - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "canvas-workpad": { - "dynamic": "false", - "properties": { - "@created": { - "type": "date" - }, - "@timestamp": { - "type": "date" - }, - "name": { - "fields": { - "keyword": { - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "cases": { - "properties": { - "closed_at": { - "type": "date" - }, - "closed_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - }, - "created_at": { - "type": "date" - }, - "created_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - }, - "description": { - "type": "text" - }, - "external_service": { - "properties": { - "connector_id": { - "type": "keyword" - }, - "connector_name": { - "type": "keyword" - }, - "external_id": { - "type": "keyword" - }, - "external_title": { - "type": "text" - }, - "external_url": { - "type": "text" - }, - "pushed_at": { - "type": "date" - }, - "pushed_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - } - } - }, - "status": { - "type": "keyword" - }, - "tags": { - "type": "keyword" - }, - "title": { - "type": "keyword" - }, - "updated_at": { - "type": "date" - }, - "updated_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - } - } - }, - "cases-comments": { - "properties": { - "comment": { - "type": "text" - }, - "created_at": { - "type": "date" - }, - "created_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - }, - "pushed_at": { - "type": "date" - }, - "pushed_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - }, - "updated_at": { - "type": "date" - }, - "updated_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - } - } - }, - "cases-configure": { - "properties": { - "closure_type": { - "type": "keyword" - }, - "connector_id": { - "type": "keyword" - }, - "connector_name": { - "type": "keyword" - }, - "created_at": { - "type": "date" - }, - "created_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - }, - "updated_at": { - "type": "date" - }, - "updated_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - } - } - }, - "cases-user-actions": { - "properties": { - "action": { - "type": "keyword" - }, - "action_at": { - "type": "date" - }, - "action_by": { - "properties": { - "email": { - "type": "keyword" - }, - "full_name": { - "type": "keyword" - }, - "username": { - "type": "keyword" - } - } - }, - "action_field": { - "type": "keyword" - }, - "new_value": { - "type": "text" - }, - "old_value": { - "type": "text" - } - } - }, - "config": { - "dynamic": "true", - "properties": { - "accessibility:disableAnimations": { - "type": "boolean" - }, - "buildNum": { - "type": "keyword" - }, - "dateFormat:tz": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "defaultIndex": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "timepicker:quickRanges": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "dashboard": { - "properties": { - "description": { - "type": "text" - }, - "hits": { - "type": "integer" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "type": "text" - } - } - }, - "optionsJSON": { - "type": "text" - }, - "panelsJSON": { - "type": "text" - }, - "refreshInterval": { - "properties": { - "display": { - "type": "keyword" - }, - "pause": { - "type": "boolean" - }, - "section": { - "type": "integer" - }, - "value": { - "type": "integer" - } - } - }, - "timeFrom": { - "type": "keyword" - }, - "timeRestore": { - "type": "boolean" - }, - "timeTo": { - "type": "keyword" - }, - "title": { - "type": "text" - }, - "version": { - "type": "integer" - } - } - }, - "file-upload-telemetry": { - "properties": { - "filesUploadedTotalCount": { - "type": "long" - } - } - }, - "graph-workspace": { - "properties": { - "description": { - "type": "text" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "type": "text" - } - } - }, - "numLinks": { - "type": "integer" - }, - "numVertices": { - "type": "integer" - }, - "title": { - "type": "text" - }, - "version": { - "type": "integer" - }, - "wsState": { - "type": "text" - } - } - }, - "index-pattern": { - "properties": { - "fieldFormatMap": { - "type": "text" - }, - "fields": { - "type": "text" - }, - "intervalName": { - "type": "keyword" - }, - "notExpandable": { - "type": "boolean" - }, - "sourceFilters": { - "type": "text" - }, - "timeFieldName": { - "type": "keyword" - }, - "title": { - "type": "text" - }, - "type": { - "type": "keyword" - }, - "typeMeta": { - "type": "keyword" - } - } - }, - "infrastructure-ui-source": { - "properties": { - "description": { - "type": "text" - }, - "fields": { - "properties": { - "container": { - "type": "keyword" - }, - "host": { - "type": "keyword" - }, - "pod": { - "type": "keyword" - }, - "tiebreaker": { - "type": "keyword" - }, - "timestamp": { - "type": "keyword" - } - } - }, - "logAlias": { - "type": "keyword" - }, - "logColumns": { - "properties": { - "fieldColumn": { - "properties": { - "field": { - "type": "keyword" - }, - "id": { - "type": "keyword" - } - } - }, - "messageColumn": { - "properties": { - "id": { - "type": "keyword" - } - } - }, - "timestampColumn": { - "properties": { - "id": { - "type": "keyword" - } - } - } - }, - "type": "nested" - }, - "metricAlias": { - "type": "keyword" - }, - "name": { - "type": "text" - } - } - }, - "inventory-view": { - "properties": { - "accountId": { - "type": "keyword" - }, - "autoBounds": { - "type": "boolean" - }, - "autoReload": { - "type": "boolean" - }, - "boundsOverride": { - "properties": { - "max": { - "type": "integer" - }, - "min": { - "type": "integer" - } - } - }, - "customMetrics": { - "properties": { - "aggregation": { - "type": "keyword" - }, - "field": { - "type": "keyword" - }, - "id": { - "type": "keyword" - }, - "label": { - "type": "keyword" - }, - "type": { - "type": "keyword" - } - }, - "type": "nested" - }, - "customOptions": { - "properties": { - "field": { - "type": "keyword" - }, - "text": { - "type": "keyword" - } - }, - "type": "nested" - }, - "filterQuery": { - "properties": { - "expression": { - "type": "keyword" - }, - "kind": { - "type": "keyword" - } - } - }, - "groupBy": { - "properties": { - "field": { - "type": "keyword" - }, - "label": { - "type": "keyword" - } - }, - "type": "nested" - }, - "metric": { - "properties": { - "aggregation": { - "type": "keyword" - }, - "field": { - "type": "keyword" - }, - "id": { - "type": "keyword" - }, - "label": { - "type": "keyword" - }, - "type": { - "type": "keyword" - } - } - }, - "name": { - "type": "keyword" - }, - "nodeType": { - "type": "keyword" - }, - "region": { - "type": "keyword" - }, - "time": { - "type": "long" - }, - "view": { - "type": "keyword" - } - } - }, - "kql-telemetry": { - "properties": { - "optInCount": { - "type": "long" - }, - "optOutCount": { - "type": "long" - } - } - }, - "lens": { - "properties": { - "expression": { - "index": false, - "type": "keyword" - }, - "state": { - "type": "flattened" - }, - "title": { - "type": "text" - }, - "visualizationType": { - "type": "keyword" - } - } - }, - "lens-ui-telemetry": { - "properties": { - "count": { - "type": "integer" - }, - "date": { - "type": "date" - }, - "name": { - "type": "keyword" - }, - "type": { - "type": "keyword" - } - } - }, - "map": { - "properties": { - "bounds": { - "dynamic": false, - "properties": {} - }, - "description": { - "type": "text" - }, - "layerListJSON": { - "type": "text" - }, - "mapStateJSON": { - "type": "text" - }, - "title": { - "type": "text" - }, - "uiStateJSON": { - "type": "text" - }, - "version": { - "type": "integer" - } - } - }, - "maps-telemetry": { - "properties": { - "attributesPerMap": { - "properties": { - "dataSourcesCount": { - "properties": { - "avg": { - "type": "long" - }, - "max": { - "type": "long" - }, - "min": { - "type": "long" - } - } - }, - "emsVectorLayersCount": { - "dynamic": "true", - "type": "object" - }, - "layerTypesCount": { - "dynamic": "true", - "type": "object" - }, - "layersCount": { - "properties": { - "avg": { - "type": "long" - }, - "max": { - "type": "long" - }, - "min": { - "type": "long" - } - } - } - } - }, - "indexPatternsWithGeoFieldCount": { - "type": "long" - }, - "mapsTotalCount": { - "type": "long" - }, - "settings": { - "properties": { - "showMapVisualizationTypes": { - "type": "boolean" - } - } - }, - "timeCaptured": { - "type": "date" - } - } - }, - "metrics-explorer-view": { - "properties": { - "chartOptions": { - "properties": { - "stack": { - "type": "boolean" - }, - "type": { - "type": "keyword" - }, - "yAxisMode": { - "type": "keyword" - } - } - }, - "currentTimerange": { - "properties": { - "from": { - "type": "keyword" - }, - "interval": { - "type": "keyword" - }, - "to": { - "type": "keyword" - } - } - }, - "name": { - "type": "keyword" - }, - "options": { - "properties": { - "aggregation": { - "type": "keyword" - }, - "filterQuery": { - "type": "keyword" - }, - "groupBy": { - "type": "keyword" - }, - "limit": { - "type": "integer" - }, - "metrics": { - "properties": { - "aggregation": { - "type": "keyword" - }, - "color": { - "type": "keyword" - }, - "field": { - "type": "keyword" - }, - "label": { - "type": "keyword" - } - }, - "type": "nested" - } - } - } - } - }, - "migrationVersion": { - "dynamic": "true", - "properties": { - "index-pattern": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "space": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "ml-telemetry": { - "properties": { - "file_data_visualizer": { - "properties": { - "index_creation_count": { - "type": "long" - } - } - } - } - }, - "namespace": { - "type": "keyword" - }, - "namespaces": { - "type": "keyword" - }, - "query": { - "properties": { - "description": { - "type": "text" - }, - "filters": { - "enabled": false, - "type": "object" - }, - "query": { - "properties": { - "language": { - "type": "keyword" - }, - "query": { - "index": false, - "type": "keyword" - } - } - }, - "timefilter": { - "enabled": false, - "type": "object" - }, - "title": { - "type": "text" - } - } - }, - "references": { - "properties": { - "id": { - "type": "keyword" - }, - "name": { - "type": "keyword" - }, - "type": { - "type": "keyword" - } - }, - "type": "nested" - }, - "sample-data-telemetry": { - "properties": { - "installCount": { - "type": "long" - }, - "unInstallCount": { - "type": "long" - } - } - }, - "search": { - "properties": { - "columns": { - "type": "keyword" - }, - "description": { - "type": "text" - }, - "hits": { - "type": "integer" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "type": "text" - } - } - }, - "sort": { - "type": "keyword" - }, - "title": { - "type": "text" - }, - "version": { - "type": "integer" - } - } - }, - "server": { - "properties": { - "uuid": { - "type": "keyword" - } - } - }, - "siem-detection-engine-rule-actions": { - "properties": { - "actions": { - "properties": { - "action_type_id": { - "type": "keyword" - }, - "group": { - "type": "keyword" - }, - "id": { - "type": "keyword" - }, - "params": { - "enabled": false, - "type": "object" - } - } - }, - "alertThrottle": { - "type": "keyword" - }, - "ruleAlertId": { - "type": "keyword" - }, - "ruleThrottle": { - "type": "keyword" - } - } - }, - "siem-detection-engine-rule-status": { - "properties": { - "alertId": { - "type": "keyword" - }, - "bulkCreateTimeDurations": { - "type": "float" - }, - "gap": { - "type": "text" - }, - "lastFailureAt": { - "type": "date" - }, - "lastFailureMessage": { - "type": "text" - }, - "lastLookBackDate": { - "type": "date" - }, - "lastSuccessAt": { - "type": "date" - }, - "lastSuccessMessage": { - "type": "text" - }, - "searchAfterTimeDurations": { - "type": "float" - }, - "status": { - "type": "keyword" - }, - "statusDate": { - "type": "date" - } - } - }, - "siem-ui-timeline": { - "properties": { - "columns": { - "properties": { - "aggregatable": { - "type": "boolean" - }, - "category": { - "type": "keyword" - }, - "columnHeaderType": { - "type": "keyword" - }, - "description": { - "type": "text" - }, - "example": { - "type": "text" - }, - "id": { - "type": "keyword" - }, - "indexes": { - "type": "keyword" - }, - "name": { - "type": "text" - }, - "placeholder": { - "type": "text" - }, - "searchable": { - "type": "boolean" - }, - "type": { - "type": "keyword" - } - } - }, - "created": { - "type": "date" - }, - "createdBy": { - "type": "text" - }, - "dataProviders": { - "properties": { - "and": { - "properties": { - "enabled": { - "type": "boolean" - }, - "excluded": { - "type": "boolean" - }, - "id": { - "type": "keyword" - }, - "kqlQuery": { - "type": "text" - }, - "name": { - "type": "text" - }, - "queryMatch": { - "properties": { - "displayField": { - "type": "text" - }, - "displayValue": { - "type": "text" - }, - "field": { - "type": "text" - }, - "operator": { - "type": "text" - }, - "value": { - "type": "text" - } - } - } - } - }, - "enabled": { - "type": "boolean" - }, - "excluded": { - "type": "boolean" - }, - "id": { - "type": "keyword" - }, - "kqlQuery": { - "type": "text" - }, - "name": { - "type": "text" - }, - "queryMatch": { - "properties": { - "displayField": { - "type": "text" - }, - "displayValue": { - "type": "text" - }, - "field": { - "type": "text" - }, - "operator": { - "type": "text" - }, - "value": { - "type": "text" - } - } - } - } - }, - "dateRange": { - "properties": { - "end": { - "type": "date" - }, - "start": { - "type": "date" - } - } - }, - "description": { - "type": "text" - }, - "eventType": { - "type": "keyword" - }, - "favorite": { - "properties": { - "favoriteDate": { - "type": "date" - }, - "fullName": { - "type": "text" - }, - "keySearch": { - "type": "text" - }, - "userName": { - "type": "text" - } - } - }, - "filters": { - "properties": { - "exists": { - "type": "text" - }, - "match_all": { - "type": "text" - }, - "meta": { - "properties": { - "alias": { - "type": "text" - }, - "controlledBy": { - "type": "text" - }, - "disabled": { - "type": "boolean" - }, - "field": { - "type": "text" - }, - "formattedValue": { - "type": "text" - }, - "index": { - "type": "keyword" - }, - "key": { - "type": "keyword" - }, - "negate": { - "type": "boolean" - }, - "params": { - "type": "text" - }, - "type": { - "type": "keyword" - }, - "value": { - "type": "text" - } - } - }, - "missing": { - "type": "text" - }, - "query": { - "type": "text" - }, - "range": { - "type": "text" - }, - "script": { - "type": "text" - } - } - }, - "kqlMode": { - "type": "keyword" - }, - "kqlQuery": { - "properties": { - "filterQuery": { - "properties": { - "kuery": { - "properties": { - "expression": { - "type": "text" - }, - "kind": { - "type": "keyword" - } - } - }, - "serializedQuery": { - "type": "text" - } - } - } - } - }, - "savedQueryId": { - "type": "keyword" - }, - "sort": { - "properties": { - "columnId": { - "type": "keyword" - }, - "sortDirection": { - "type": "keyword" - } - } - }, - "templateTimelineId": { - "type": "text" - }, - "templateTimelineVersion": { - "type": "integer" - }, - "timelineType": { - "type": "keyword" - }, - "title": { - "type": "text" - }, - "updated": { - "type": "date" - }, - "updatedBy": { - "type": "text" - } - } - }, - "siem-ui-timeline-note": { - "properties": { - "created": { - "type": "date" - }, - "createdBy": { - "type": "text" - }, - "eventId": { - "type": "keyword" - }, - "note": { - "type": "text" - }, - "timelineId": { - "type": "keyword" - }, - "updated": { - "type": "date" - }, - "updatedBy": { - "type": "text" - } - } - }, - "siem-ui-timeline-pinned-event": { - "properties": { - "created": { - "type": "date" - }, - "createdBy": { - "type": "text" - }, - "eventId": { - "type": "keyword" - }, - "timelineId": { - "type": "keyword" - }, - "updated": { - "type": "date" - }, - "updatedBy": { - "type": "text" - } - } - }, - "space": { - "properties": { - "_reserved": { - "type": "boolean" - }, - "color": { - "type": "keyword" - }, - "description": { - "type": "text" - }, - "disabledFeatures": { - "type": "keyword" - }, - "imageUrl": { - "index": false, - "type": "text" - }, - "initials": { - "type": "keyword" - }, - "name": { - "fields": { - "keyword": { - "ignore_above": 2048, - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "spaceId": { - "type": "keyword" - }, - "telemetry": { - "properties": { - "allowChangingOptInStatus": { - "type": "boolean" - }, - "enabled": { - "type": "boolean" - }, - "lastReported": { - "type": "date" - }, - "lastVersionChecked": { - "type": "keyword" - }, - "reportFailureCount": { - "type": "integer" - }, - "reportFailureVersion": { - "type": "keyword" - }, - "sendUsageFrom": { - "type": "keyword" - }, - "userHasSeenNotice": { - "type": "boolean" - } - } - }, - "tsvb-validation-telemetry": { - "properties": { - "failedRequests": { - "type": "long" - } - } - }, - "type": { - "type": "keyword" - }, - "ui-metric": { - "properties": { - "count": { - "type": "integer" - } - } - }, - "updated_at": { - "type": "date" - }, - "upgrade-assistant-reindex-operation": { - "properties": { - "errorMessage": { - "type": "keyword" - }, - "indexName": { - "type": "keyword" - }, - "lastCompletedStep": { - "type": "integer" - }, - "locked": { - "type": "date" - }, - "newIndexName": { - "type": "keyword" - }, - "reindexOptions": { - "properties": { - "openAndClose": { - "type": "boolean" - }, - "queueSettings": { - "properties": { - "queuedAt": { - "type": "long" - }, - "startedAt": { - "type": "long" - } - } - } - } - }, - "reindexTaskId": { - "type": "keyword" - }, - "reindexTaskPercComplete": { - "type": "float" - }, - "runningReindexCount": { - "type": "integer" - }, - "status": { - "type": "integer" - } - } - }, - "upgrade-assistant-telemetry": { - "properties": { - "features": { - "properties": { - "deprecation_logging": { - "properties": { - "enabled": { - "null_value": true, - "type": "boolean" - } - } - } - } - }, - "ui_open": { - "properties": { - "cluster": { - "null_value": 0, - "type": "long" - }, - "indices": { - "null_value": 0, - "type": "long" - }, - "overview": { - "null_value": 0, - "type": "long" - } - } - }, - "ui_reindex": { - "properties": { - "close": { - "null_value": 0, - "type": "long" - }, - "open": { - "null_value": 0, - "type": "long" - }, - "start": { - "null_value": 0, - "type": "long" - }, - "stop": { - "null_value": 0, - "type": "long" - } - } - } - } - }, - "uptime-dynamic-settings": { - "properties": { - "certThresholds": { - "properties": { - "age": { - "type": "long" - }, - "expiration": { - "type": "long" - } - } - }, - "heartbeatIndices": { - "type": "keyword" - } - } - }, - "url": { - "properties": { - "accessCount": { - "type": "long" - }, - "accessDate": { - "type": "date" - }, - "createDate": { - "type": "date" - }, - "url": { - "fields": { - "keyword": { - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "visualization": { - "properties": { - "description": { - "type": "text" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "type": "text" - } - } - }, - "savedSearchRefName": { - "type": "keyword" - }, - "title": { - "type": "text" - }, - "uiStateJSON": { - "type": "text" - }, - "version": { - "type": "integer" - }, - "visState": { - "type": "text" - } - } - } - } - }, - "settings": { - "index": { - "auto_expand_replicas": "0-1", - "number_of_replicas": "0", - "number_of_shards": "1" - } - } - } -} diff --git a/x-pack/test/functional/fixtures/kbn_archiver/kibana_scripted_fields_on_logstash.json b/x-pack/test/functional/fixtures/kbn_archiver/kibana_scripted_fields_on_logstash.json new file mode 100644 index 0000000000000..b9316cd311b19 --- /dev/null +++ b/x-pack/test/functional/fixtures/kbn_archiver/kibana_scripted_fields_on_logstash.json @@ -0,0 +1,35 @@ +{ + "attributes": { + "fieldFormatMap": "{\"sharedFail\":{\"id\":\"string\",\"params\":{\"parsedUrl\":{\"origin\":\"http://localhost:5620\",\"pathname\":\"/app/kibana\",\"basePath\":\"\"}}}}", + "fields": "[{\"name\":\"@message\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@message.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@message\"}}},{\"name\":\"@tags\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@tags.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@tags\"}}},{\"name\":\"@timestamp\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"_id\",\"type\":\"string\",\"esTypes\":[\"_id\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_index\",\"type\":\"string\",\"esTypes\":[\"_index\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_score\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_source\",\"type\":\"_source\",\"esTypes\":[\"_source\"],\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_type\",\"type\":\"string\",\"esTypes\":[\"_type\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"agent\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"agent.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"agent\"}}},{\"name\":\"bytes\",\"type\":\"number\",\"esTypes\":[\"long\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"clientip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"extension\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"extension.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"extension\"}}},{\"name\":\"geo.coordinates\",\"type\":\"geo_point\",\"esTypes\":[\"geo_point\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.dest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.src\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.srcdest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"headings\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"headings.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"headings\"}}},{\"name\":\"host\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"host.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"host\"}}},{\"name\":\"id\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"index\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"index.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"index\"}}},{\"name\":\"ip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"links\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"links.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"links\"}}},{\"name\":\"machine.os\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"machine.os.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"machine.os\"}}},{\"name\":\"machine.ram\",\"type\":\"number\",\"esTypes\":[\"long\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"memory\",\"type\":\"number\",\"esTypes\":[\"double\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.char\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.related\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.firstname\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.lastname\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"phpmemory\",\"type\":\"number\",\"esTypes\":[\"long\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"referer\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:modified_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:published_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:section\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:section.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:section\"}}},{\"name\":\"relatedContent.article:tag\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:tag.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:tag\"}}},{\"name\":\"relatedContent.og:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:description\"}}},{\"name\":\"relatedContent.og:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image\"}}},{\"name\":\"relatedContent.og:image:height\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:height.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:height\"}}},{\"name\":\"relatedContent.og:image:width\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:width.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:width\"}}},{\"name\":\"relatedContent.og:site_name\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:site_name.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:site_name\"}}},{\"name\":\"relatedContent.og:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:title\"}}},{\"name\":\"relatedContent.og:type\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:type.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:type\"}}},{\"name\":\"relatedContent.og:url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:url\"}}},{\"name\":\"relatedContent.twitter:card\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:card.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:card\"}}},{\"name\":\"relatedContent.twitter:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:description\"}}},{\"name\":\"relatedContent.twitter:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:image\"}}},{\"name\":\"relatedContent.twitter:site\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:site.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:site\"}}},{\"name\":\"relatedContent.twitter:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:title\"}}},{\"name\":\"relatedContent.url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.url\"}}},{\"name\":\"request\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"request.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"request\"}}},{\"name\":\"response\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"response.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"response\"}}},{\"name\":\"spaces\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"spaces.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"spaces\"}}},{\"name\":\"type\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"url\"}}},{\"name\":\"utc_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"xss\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"xss.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"xss\"}}},{\"name\":\"sharedFail\",\"type\":\"string\",\"count\":1,\"scripted\":true,\"script\":\"if (doc['response.raw'].value == '200') { return 'good ' + doc['url.raw'].value } else { return 'bad ' + doc['machine.os.raw'].value } \",\"lang\":\"painless\",\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false}]", + "timeFieldName": "@timestamp", + "title": "logsta*" + }, + "coreMigrationVersion": "8.4.0", + "id": "da2aebe0-913d-11ea-bf44-c796fb3350db", + "migrationVersion": { + "index-pattern": "8.0.0" + }, + "references": [], + "type": "index-pattern", + "updated_at": "2020-05-08T15:09:15.796Z", + "version": "WzE1LDJd" +} + +{ + "attributes": { + "fieldFormatMap": "{\"goodScript\":{\"id\":\"string\",\"params\":{\"parsedUrl\":{\"origin\":\"http://localhost:5620\",\"pathname\":\"/app/kibana\",\"basePath\":\"\"}}},\"goodScript2\":{\"id\":\"string\",\"params\":{\"parsedUrl\":{\"origin\":\"http://localhost:5620\",\"pathname\":\"/app/kibana\",\"basePath\":\"\"}}}}", + "fields": "[{\"name\":\"@message\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@message.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@message\"}}},{\"name\":\"@tags\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@tags.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@tags\"}}},{\"name\":\"@timestamp\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"_id\",\"type\":\"string\",\"esTypes\":[\"_id\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_index\",\"type\":\"string\",\"esTypes\":[\"_index\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_score\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_source\",\"type\":\"_source\",\"esTypes\":[\"_source\"],\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_type\",\"type\":\"string\",\"esTypes\":[\"_type\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"agent\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"agent.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"agent\"}}},{\"name\":\"bytes\",\"type\":\"number\",\"esTypes\":[\"long\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"clientip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"extension\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"extension.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"extension\"}}},{\"name\":\"geo.coordinates\",\"type\":\"geo_point\",\"esTypes\":[\"geo_point\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.dest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.src\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.srcdest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"headings\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"headings.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"headings\"}}},{\"name\":\"host\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"host.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"host\"}}},{\"name\":\"id\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"index\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"index.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"index\"}}},{\"name\":\"ip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"links\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"links.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"links\"}}},{\"name\":\"machine.os\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"machine.os.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"machine.os\"}}},{\"name\":\"machine.ram\",\"type\":\"number\",\"esTypes\":[\"long\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"memory\",\"type\":\"number\",\"esTypes\":[\"double\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.char\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.related\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.firstname\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.lastname\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"phpmemory\",\"type\":\"number\",\"esTypes\":[\"long\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"referer\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:modified_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:published_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:section\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:section.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:section\"}}},{\"name\":\"relatedContent.article:tag\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:tag.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:tag\"}}},{\"name\":\"relatedContent.og:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:description\"}}},{\"name\":\"relatedContent.og:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image\"}}},{\"name\":\"relatedContent.og:image:height\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:height.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:height\"}}},{\"name\":\"relatedContent.og:image:width\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:width.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:width\"}}},{\"name\":\"relatedContent.og:site_name\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:site_name.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:site_name\"}}},{\"name\":\"relatedContent.og:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:title\"}}},{\"name\":\"relatedContent.og:type\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:type.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:type\"}}},{\"name\":\"relatedContent.og:url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:url\"}}},{\"name\":\"relatedContent.twitter:card\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:card.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:card\"}}},{\"name\":\"relatedContent.twitter:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:description\"}}},{\"name\":\"relatedContent.twitter:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:image\"}}},{\"name\":\"relatedContent.twitter:site\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:site.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:site\"}}},{\"name\":\"relatedContent.twitter:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:title\"}}},{\"name\":\"relatedContent.url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.url\"}}},{\"name\":\"request\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"request.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"request\"}}},{\"name\":\"response\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"response.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"response\"}}},{\"name\":\"spaces\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"spaces.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"spaces\"}}},{\"name\":\"type\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"url\"}}},{\"name\":\"utc_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"xss\",\"type\":\"string\",\"esTypes\":[\"text\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"xss.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"xss\"}}},{\"name\":\"goodScript\",\"type\":\"string\",\"count\":1,\"scripted\":true,\"script\":\"if (doc['response.raw'].value == '200') { if (doc['url.raw'].size() > 0) { return 'good ' + doc['url.raw'].value } else { return 'good' } } else { if (doc['machine.os.raw'].size() > 0) { return 'bad ' + doc['machine.os.raw'].value } else { return 'bad' } }\",\"lang\":\"painless\",\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"goodScript2\",\"type\":\"string\",\"count\":1,\"scripted\":true,\"script\":\"if (doc['url.raw'].size() > 0) { String tempString = \\\"\\\"; for ( int i = (doc['url.raw'].value.length() - 1); i >= 0 ; i--) { tempString = tempString + (doc['url.raw'].value).charAt(i); } return tempString; } else { return \\\"emptyUrl\\\"; }\",\"lang\":\"painless\",\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false}]", + "timeFieldName": "@timestamp", + "title": "logstash-*" + }, + "coreMigrationVersion": "8.4.0", + "id": "eddf62c0-85bb-11ea-a555-0b6139dddc19", + "migrationVersion": { + "index-pattern": "8.0.0" + }, + "references": [], + "type": "index-pattern", + "updated_at": "2020-04-23T23:41:56.266Z", + "version": "WzksMl0=" +} \ No newline at end of file From 818b0ca4590502d8345d28cf01b2bd1690d21fe0 Mon Sep 17 00:00:00 2001 From: Pablo Machado Date: Thu, 14 Jul 2022 11:33:44 +0200 Subject: [PATCH 013/111] [Security Solution] Refactor timerange to use global query string (#135998) * Refactor timerange to use global query string --- .../ml/ml_conditional_links.spec.ts | 26 +- .../cypress/integration/urls/state.spec.ts | 12 +- .../public/app/home/index.test.tsx | 230 +++++++++++++++++- .../public/app/home/index.tsx | 7 +- .../navigation/breadcrumbs/index.test.ts | 38 +-- .../components/navigation/helpers.test.tsx | 73 ++++++ .../common/components/navigation/helpers.ts | 15 +- .../components/navigation/index.test.tsx | 22 -- .../common/components/navigation/index.tsx | 1 - .../navigation/tab_navigation/index.test.tsx | 23 -- .../navigation/tab_navigation/types.ts | 2 - .../navigation/use_get_url_search.tsx | 11 +- .../__snapshots__/index.test.tsx.snap | 44 ++-- .../index.test.tsx | 4 +- .../index.tsx | 1 - .../use_primary_navigation.tsx | 2 - .../components/search_bar/index.test.tsx | 103 +++++++- .../common/components/search_bar/index.tsx | 3 +- .../common/components/url_state/helpers.ts | 35 --- .../components/url_state/index.test.tsx | 145 +---------- .../url_state/index_mocked.test.tsx | 178 +------------- .../url_state/initialize_redux_by_url.tsx | 98 +------- .../components/url_state/test_dependencies.ts | 94 ------- .../common/components/url_state/types.ts | 4 +- .../components/url_state/use_url_state.tsx | 14 -- .../use_init_search_bar_url_params.ts | 14 +- .../use_init_timerange_url_params.ts | 129 ++++++++++ .../use_sync_timerange_url_param.ts | 34 +++ .../use_update_timerange_on_page_change.ts | 75 ++++++ .../public/common/hooks/use_url_state.ts | 18 ++ .../field_renderers.test.tsx.snap | 4 +- 31 files changed, 742 insertions(+), 717 deletions(-) create mode 100644 x-pack/plugins/security_solution/public/common/components/navigation/helpers.test.tsx create mode 100644 x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_timerange_url_params.ts create mode 100644 x-pack/plugins/security_solution/public/common/hooks/search_bar/use_sync_timerange_url_param.ts create mode 100644 x-pack/plugins/security_solution/public/common/hooks/search_bar/use_update_timerange_on_page_change.ts create mode 100644 x-pack/plugins/security_solution/public/common/hooks/use_url_state.ts diff --git a/x-pack/plugins/security_solution/cypress/integration/ml/ml_conditional_links.spec.ts b/x-pack/plugins/security_solution/cypress/integration/ml/ml_conditional_links.spec.ts index c016a6bf45e1c..8e2bd7ba2bb4d 100644 --- a/x-pack/plugins/security_solution/cypress/integration/ml/ml_conditional_links.spec.ts +++ b/x-pack/plugins/security_solution/cypress/integration/ml/ml_conditional_links.spec.ts @@ -97,7 +97,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlNetworkSingleIpNullKqlQuery); cy.url().should( 'include', - 'app/security/network/ip/127.0.0.1/source?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))' + 'app/security/network/ip/127.0.0.1/source?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))' ); }); @@ -105,7 +105,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlNetworkSingleIpKqlQuery); cy.url().should( 'include', - '/app/security/network/ip/127.0.0.1/source?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)' + '/app/security/network/ip/127.0.0.1/source?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))' ); }); @@ -113,7 +113,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlNetworkMultipleIpNullKqlQuery); cy.url().should( 'include', - 'app/security/network/flows?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27((source.ip:%20%22127.0.0.1%22%20or%20destination.ip:%20%22127.0.0.1%22)%20or%20(source.ip:%20%22127.0.0.2%22%20or%20destination.ip:%20%22127.0.0.2%22))%27)' + 'app/security/network/flows?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27((source.ip:%20%22127.0.0.1%22%20or%20destination.ip:%20%22127.0.0.1%22)%20or%20(source.ip:%20%22127.0.0.2%22%20or%20destination.ip:%20%22127.0.0.2%22))%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))' ); }); @@ -121,7 +121,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlNetworkMultipleIpKqlQuery); cy.url().should( 'include', - '/app/security/network/flows?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27((source.ip:%20%22127.0.0.1%22%20or%20destination.ip:%20%22127.0.0.1%22)%20or%20(source.ip:%20%22127.0.0.2%22%20or%20destination.ip:%20%22127.0.0.2%22))%20and%20((process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22))%27)' + '/app/security/network/flows?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27((source.ip:%20%22127.0.0.1%22%20or%20destination.ip:%20%22127.0.0.1%22)%20or%20(source.ip:%20%22127.0.0.2%22%20or%20destination.ip:%20%22127.0.0.2%22))%20and%20((process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22))%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))' ); }); @@ -129,7 +129,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlNetworkNullKqlQuery); cy.url().should( 'include', - '/app/security/network/flows?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))' + '/app/security/network/flows?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))' ); }); @@ -138,7 +138,7 @@ describe('ml conditional links', () => { cy.url().should( 'include', - `/app/security/network/flows?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)` + `/app/security/network/flows?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-08-28T11:00:00.000Z%27,kind:absolute,to:%272019-08-28T13:59:59.999Z%27)))` ); }); @@ -146,7 +146,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlHostSingleHostNullKqlQuery); cy.url().should( 'include', - '/app/security/hosts/siem-windows/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))' + '/app/security/hosts/siem-windows/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))' ); }); @@ -154,7 +154,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlHostSingleHostKqlQueryVariable); cy.url().should( 'include', - '/app/security/hosts/siem-windows/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))' + '/app/security/hosts/siem-windows/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))' ); }); @@ -162,7 +162,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlHostSingleHostKqlQuery); cy.url().should( 'include', - '/app/security/hosts/siem-windows/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)' + '/app/security/hosts/siem-windows/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))' ); }); @@ -170,7 +170,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlHostMultiHostNullKqlQuery); cy.url().should( 'include', - '/app/security/hosts/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(host.name:%20%22siem-windows%22%20or%20host.name:%20%22siem-suricata%22)%27)' + '/app/security/hosts/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(host.name:%20%22siem-windows%22%20or%20host.name:%20%22siem-suricata%22)%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))' ); }); @@ -178,7 +178,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlHostMultiHostKqlQuery); cy.url().should( 'include', - '/app/security/hosts/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(host.name:%20%22siem-windows%22%20or%20host.name:%20%22siem-suricata%22)%20and%20((process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22))%27)' + '/app/security/hosts/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(host.name:%20%22siem-windows%22%20or%20host.name:%20%22siem-suricata%22)%20and%20((process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22))%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))' ); }); @@ -186,7 +186,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlHostVariableHostNullKqlQuery); cy.url().should( 'include', - '/app/security/hosts/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))' + '/app/security/hosts/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))' ); }); @@ -194,7 +194,7 @@ describe('ml conditional links', () => { visitWithoutDateRange(mlHostVariableHostKqlQuery); cy.url().should( 'include', - '/app/security/hosts/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)' + '/app/security/hosts/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!(%27auditbeat-*%27)))&query=(language:kuery,query:%27(process.name:%20%22conhost.exe%22%20or%20process.name:%20%22sc.exe%22)%27)&timerange=(global:(linkTo:!(timeline),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)),timeline:(linkTo:!(global),timerange:(from:%272019-06-06T06:00:00.000Z%27,kind:absolute,to:%272019-06-07T05:59:59.999Z%27)))' ); }); }); diff --git a/x-pack/plugins/security_solution/cypress/integration/urls/state.spec.ts b/x-pack/plugins/security_solution/cypress/integration/urls/state.spec.ts index 16cbacae403c3..f30816d455070 100644 --- a/x-pack/plugins/security_solution/cypress/integration/urls/state.spec.ts +++ b/x-pack/plugins/security_solution/cypress/integration/urls/state.spec.ts @@ -216,7 +216,7 @@ describe('url state', () => { cy.get(NETWORK).should( 'have.attr', 'href', - `/app/security/network?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2019-08-01T20:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2019-08-01T20:33:29.186Z')))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'source.ip:%20%2210.142.0.9%22%20')` + `/app/security/network?sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'source.ip:%20%2210.142.0.9%22%20')&timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2019-08-01T20:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2019-08-01T20:33:29.186Z')))` ); }); @@ -229,12 +229,12 @@ describe('url state', () => { cy.get(HOSTS).should( 'have.attr', 'href', - `/app/security/hosts?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'host.name:%20%22siem-kibana%22%20')` + `/app/security/hosts?sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'host.name:%20%22siem-kibana%22%20')&timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))` ); cy.get(NETWORK).should( 'have.attr', 'href', - `/app/security/network?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'host.name:%20%22siem-kibana%22%20')` + `/app/security/network?sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'host.name:%20%22siem-kibana%22%20')&timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))` ); cy.get(HOSTS_NAMES).first().should('have.text', 'siem-kibana'); @@ -245,7 +245,7 @@ describe('url state', () => { cy.get(ANOMALIES_TAB).should( 'have.attr', 'href', - "/app/security/hosts/siem-kibana/anomalies?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'agent.type:%20%22auditbeat%22%20')" + "/app/security/hosts/siem-kibana/anomalies?sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))&query=(language:kuery,query:'agent.type:%20%22auditbeat%22%20')" ); cy.get(BREADCRUMBS) @@ -253,14 +253,14 @@ describe('url state', () => { .should( 'have.attr', 'href', - `/app/security/hosts?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'agent.type:%20%22auditbeat%22%20')` + `/app/security/hosts?sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'agent.type:%20%22auditbeat%22%20')&timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))` ); cy.get(BREADCRUMBS) .eq(2) .should( 'have.attr', 'href', - `/app/security/hosts/siem-kibana?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))&sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'agent.type:%20%22auditbeat%22%20')` + `/app/security/hosts/siem-kibana?sourcerer=(default:(id:security-solution-default,selectedPatterns:!('auditbeat-*')))&query=(language:kuery,query:'agent.type:%20%22auditbeat%22%20')&timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')),timeline:(linkTo:!(global),timerange:(from:'2019-08-01T20:03:29.186Z',kind:absolute,to:'2023-01-01T21:33:29.186Z')))` ); }); diff --git a/x-pack/plugins/security_solution/public/app/home/index.test.tsx b/x-pack/plugins/security_solution/public/app/home/index.test.tsx index 851f72a71c475..a81b6069381c2 100644 --- a/x-pack/plugins/security_solution/public/app/home/index.test.tsx +++ b/x-pack/plugins/security_solution/public/app/home/index.test.tsx @@ -20,13 +20,25 @@ import { TestProviders, } from '../../common/mock'; import { inputsActions } from '../../common/store/inputs'; -import { setSearchBarFilter } from '../../common/store/inputs/actions'; +import { + setSearchBarFilter, + setAbsoluteRangeDatePicker, + setRelativeRangeDatePicker, +} from '../../common/store/inputs/actions'; import { coreMock } from '@kbn/core/public/mocks'; import type { Filter } from '@kbn/es-query'; import { createStore } from '../../common/store'; +import type { TimeRange, UrlInputsModel } from '../../common/store/inputs/model'; +import { SecurityPageName } from '../types'; jest.mock('../../common/store/inputs/actions'); +const mockRouteSpy = jest.fn().mockReturnValue([{ pageName: 'hosts' }]); + +jest.mock('../../common/utils/route/use_route_spy', () => ({ + useRouteSpy: () => mockRouteSpy(), +})); + const DummyComponent = ({ children }: { children: React.ReactNode }) => <>{children}; const mockedUseInitializeUrlParam = jest.fn(); @@ -51,9 +63,14 @@ jest.mock('../../common/utils/global_query_string', () => { jest.mock('../../common/components/drag_and_drop/drag_drop_context_wrapper', () => ({ DragDropContextWrapper: DummyComponent, })); + jest.mock('./template_wrapper', () => ({ SecuritySolutionTemplateWrapper: DummyComponent, })); +const DATE_TIME_NOW = '2020-01-01T00:00:00.000Z'; +jest.mock('../../common/components/super_date_picker', () => ({ + formatDate: (date: string) => DATE_TIME_NOW, +})); jest.mock('react-router-dom', () => { const original = jest.requireActual('react-router-dom'); @@ -102,6 +119,9 @@ jest.mock('../../common/lib/kibana', () => { }, }, }), + KibanaServices: { + get: jest.fn(() => ({ uiSettings: { get: () => ({ from: 'now-24h', to: 'now' }) } })), + }, }; }); @@ -118,6 +138,7 @@ jest.mock('react-redux', () => { describe('HomePage', () => { beforeEach(() => { jest.clearAllMocks(); + mockedUseInitializeUrlParam.mockImplementation(jest.fn()); mockedFilterManager.setFilters([]); }); @@ -291,4 +312,211 @@ describe('HomePage', () => { ]); }); }); + + describe('Timerange', () => { + it('sets global absolute timerange initial value in the store', () => { + const timerange: TimeRange = { + from: '2020-07-07T08:20:18.966Z', + fromStr: undefined, + kind: 'absolute', + to: '2020-07-08T08:20:18.966Z', + toStr: undefined, + }; + + const state: UrlInputsModel = { + global: { + [CONSTANTS.timerange]: timerange, + linkTo: ['timeline'], + }, + timeline: { + [CONSTANTS.timerange]: timerange, + linkTo: ['global'], + }, + }; + + mockUseInitializeUrlParam(CONSTANTS.timerange, state); + + render( + + + + + + ); + + expect(setAbsoluteRangeDatePicker).toHaveBeenCalledWith({ + from: timerange.from, + to: timerange.to, + kind: timerange.kind, + id: 'global', + }); + + expect(setAbsoluteRangeDatePicker).toHaveBeenCalledWith({ + from: timerange.from, + to: timerange.to, + kind: timerange.kind, + id: 'timeline', + }); + }); + + it('sets updated relative timerange initial value in the store', () => { + const timerange: TimeRange = { + from: '2019-01-01T00:00:00.000Z', + fromStr: 'now-1d/d', + kind: 'relative', + to: '2019-01-01T00:00:00.000Z', + toStr: 'now-1d/d', + }; + + const state: UrlInputsModel = { + global: { + [CONSTANTS.timerange]: timerange, + linkTo: ['timeline'], + }, + timeline: { + [CONSTANTS.timerange]: timerange, + linkTo: ['global'], + }, + }; + + mockUseInitializeUrlParam(CONSTANTS.timerange, state); + + render( + + + + + + ); + + expect(setRelativeRangeDatePicker).toHaveBeenCalledWith({ + ...timerange, + to: DATE_TIME_NOW, + from: DATE_TIME_NOW, + id: 'global', + }); + + expect(setRelativeRangeDatePicker).toHaveBeenCalledWith({ + ...timerange, + to: DATE_TIME_NOW, + from: DATE_TIME_NOW, + id: 'timeline', + }); + }); + + it('update timerange when navigating to alerts page', () => { + const timerange: TimeRange = { + from: '2019-01-01T00:00:00.000Z', + fromStr: 'now-1d/d', + kind: 'relative', + to: '2019-01-01T00:00:00.000Z', + toStr: 'now-1d/d', + }; + + const mockstate = { + ...mockGlobalState, + inputs: { + ...mockGlobalState.inputs, + global: { + ...mockGlobalState.inputs.global, + timerange, + }, + timeline: { + ...mockGlobalState.inputs.timeline, + timerange, + }, + }, + }; + + const { storage } = createSecuritySolutionStorageMock(); + const mockStore = createStore(mockstate, SUB_PLUGINS_REDUCER, kibanaObservable, storage); + + const TestComponent = () => ( + + + + + + ); + + const { rerender } = render(); + jest.clearAllMocks(); + + // simulate page navigation + mockRouteSpy.mockReturnValueOnce([{ pageName: SecurityPageName.alerts }]); + rerender(); + + expect(setRelativeRangeDatePicker).toHaveBeenCalledWith({ + ...timerange, + to: DATE_TIME_NOW, + from: DATE_TIME_NOW, + id: 'global', + }); + + expect(setRelativeRangeDatePicker).toHaveBeenCalledWith({ + ...timerange, + to: DATE_TIME_NOW, + from: DATE_TIME_NOW, + id: 'timeline', + }); + }); + + it('does not update timerange when navigating to hosts page', () => { + const timerange: TimeRange = { + from: '2019-01-01T00:00:00.000Z', + fromStr: 'now-1d/d', + kind: 'relative', + to: '2019-01-01T00:00:00.000Z', + toStr: 'now-1d/d', + }; + + const mockstate = { + ...mockGlobalState, + inputs: { + ...mockGlobalState.inputs, + global: { + ...mockGlobalState.inputs.global, + timerange, + }, + timeline: { + ...mockGlobalState.inputs.timeline, + timerange, + }, + }, + }; + + const { storage } = createSecuritySolutionStorageMock(); + const mockStore = createStore(mockstate, SUB_PLUGINS_REDUCER, kibanaObservable, storage); + + const TestComponent = () => ( + + + + + + ); + + // mockedUseInitializeUrlParam.mockImplementation(jest.fn()); + const { rerender } = render(); + jest.clearAllMocks(); + + // simulate page navigation + mockRouteSpy.mockReturnValueOnce([{ pageName: SecurityPageName.hosts }]); + rerender(); + + expect(setRelativeRangeDatePicker).not.toHaveBeenCalledWith({ + ...timerange, + to: DATE_TIME_NOW, + from: DATE_TIME_NOW, + id: 'global', + }); + + expect(setRelativeRangeDatePicker).not.toHaveBeenCalledWith({ + ...timerange, + to: DATE_TIME_NOW, + from: DATE_TIME_NOW, + id: 'timeline', + }); + }); + }); }); diff --git a/x-pack/plugins/security_solution/public/app/home/index.tsx b/x-pack/plugins/security_solution/public/app/home/index.tsx index e0827887a7ebc..da3cb0c92ab9a 100644 --- a/x-pack/plugins/security_solution/public/app/home/index.tsx +++ b/x-pack/plugins/security_solution/public/app/home/index.tsx @@ -11,6 +11,7 @@ import { useLocation } from 'react-router-dom'; import type { AppLeaveHandler, AppMountParameters } from '@kbn/core/public'; import { DragDropContextWrapper } from '../../common/components/drag_and_drop/drag_drop_context_wrapper'; import { SecuritySolutionAppWrapper } from '../../common/components/page'; + import { HelpMenu } from '../../common/components/help_menu'; import { UseUrlState } from '../../common/components/url_state'; import { navTabs } from './home_navigations'; @@ -23,8 +24,7 @@ import { useUpgradeSecurityPackages } from '../../common/hooks/use_upgrade_secur import { GlobalHeader } from './global_header'; import { SecuritySolutionTemplateWrapper } from './template_wrapper'; import { ConsoleManager } from '../../management/components/console/components/console_manager'; -import { useSyncGlobalQueryString } from '../../common/utils/global_query_string'; -import { useInitSearchBarUrlParams } from '../../common/hooks/search_bar/use_init_search_bar_url_params'; +import { useUrlState } from '../../common/hooks/use_url_state'; interface HomePageProps { children: React.ReactNode; @@ -38,9 +38,8 @@ const HomePageComponent: React.FC = ({ setHeaderActionMenu, }) => { const { pathname } = useLocation(); - useSyncGlobalQueryString(); useInitSourcerer(getScopeFromPath(pathname)); - useInitSearchBarUrlParams(); + useUrlState(); const { browserFields, indexPattern } = useSourcererDataView(getScopeFromPath(pathname)); // side effect: this will attempt to upgrade the endpoint package if it is not up to date diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/breadcrumbs/index.test.ts b/x-pack/plugins/security_solution/public/common/components/navigation/breadcrumbs/index.test.ts index c67bcc4ab1051..674a609e7f71a 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/breadcrumbs/index.test.ts +++ b/x-pack/plugins/security_solution/public/common/components/navigation/breadcrumbs/index.test.ts @@ -79,28 +79,6 @@ const getMockObject = ( isOpen: false, graphEventId: '', }, - timerange: { - global: { - linkTo: ['timeline'], - timerange: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - }, - timeline: { - linkTo: ['global'], - timerange: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - }, - }, }, }; }); @@ -470,17 +448,17 @@ describe('Navigation Breadcrumbs', () => { expect(setBreadcrumbsMock).toBeCalledWith([ expect.objectContaining({ text: 'Security', - href: "securitySolutionUI/get_started?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))", + href: 'securitySolutionUI/get_started', onClick: expect.any(Function), }), expect.objectContaining({ text: 'Hosts', - href: "securitySolutionUI/hosts?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))", + href: 'securitySolutionUI/hosts', onClick: expect.any(Function), }), expect.objectContaining({ text: 'siem-kibana', - href: "securitySolutionUI/hosts/siem-kibana?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))", + href: 'securitySolutionUI/hosts/siem-kibana', onClick: expect.any(Function), }), { @@ -790,28 +768,26 @@ describe('Navigation Breadcrumbs', () => { chromeMock, navigateToUrlMock ); - const searchString = - "?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))"; expect(setBreadcrumbsMock).toBeCalledWith([ expect.objectContaining({ text: 'Security', - href: `securitySolutionUI/get_started${searchString}`, + href: 'securitySolutionUI/get_started', onClick: expect.any(Function), }), expect.objectContaining({ text: 'Explore', - href: `securitySolutionUI/explore`, + href: 'securitySolutionUI/explore', onClick: expect.any(Function), }), expect.objectContaining({ text: 'Hosts', - href: `securitySolutionUI/hosts${searchString}`, + href: 'securitySolutionUI/hosts', onClick: expect.any(Function), }), expect.objectContaining({ text: 'siem-kibana', - href: `securitySolutionUI/hosts/siem-kibana${searchString}`, + href: 'securitySolutionUI/hosts/siem-kibana', onClick: expect.any(Function), }), { diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/helpers.test.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/helpers.test.tsx new file mode 100644 index 0000000000000..bb9fa228fb018 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/components/navigation/helpers.test.tsx @@ -0,0 +1,73 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { CONSTANTS } from '../url_state/constants'; +import type { SearchNavTab } from './types'; +import { TimelineTabs } from '../../../../common/types/timeline'; +import { getSearch } from './helpers'; + +describe('helpers', () => { + it('returns the search string', () => { + const serachNavTab: SearchNavTab = { urlKey: 'host', isDetailPage: false }; + const globalQueryString = 'test=123'; + const urlState = { + [CONSTANTS.timeline]: { + activeTab: TimelineTabs.query, + id: '123', + isOpen: false, + }, + }; + + expect(getSearch(serachNavTab, urlState, globalQueryString)).toEqual( + "?timeline=(activeTab:query,id:'123',isOpen:!f)&test=123" + ); + }); + + it('returns an empty string when global globalQueryString and urlState are empty', () => { + const serachNavTab: SearchNavTab = { urlKey: 'host', isDetailPage: false }; + const globalQueryString = ''; + const urlState = { + [CONSTANTS.timeline]: { + activeTab: TimelineTabs.query, + id: '', + isOpen: false, + }, + }; + + expect(getSearch(serachNavTab, urlState, globalQueryString)).toEqual(''); + }); + + it('returns the search string when global globalQueryString is empty', () => { + const serachNavTab: SearchNavTab = { urlKey: 'host', isDetailPage: false }; + const globalQueryString = ''; + const urlState = { + [CONSTANTS.timeline]: { + activeTab: TimelineTabs.query, + id: '123', + isOpen: false, + }, + }; + + expect(getSearch(serachNavTab, urlState, globalQueryString)).toEqual( + "?timeline=(activeTab:query,id:'123',isOpen:!f)" + ); + }); + + it('returns the search string when global urlState is empty', () => { + const serachNavTab: SearchNavTab = { urlKey: 'host', isDetailPage: false }; + const globalQueryString = 'test=123'; + const urlState = { + [CONSTANTS.timeline]: { + activeTab: TimelineTabs.query, + id: '', + isOpen: false, + }, + }; + + expect(getSearch(serachNavTab, urlState, globalQueryString)).toEqual('?test=123'); + }); +}); diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/helpers.ts b/x-pack/plugins/security_solution/public/common/components/navigation/helpers.ts index ba42d8478e646..b0d9573008655 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/helpers.ts +++ b/x-pack/plugins/security_solution/public/common/components/navigation/helpers.ts @@ -8,6 +8,7 @@ import type { Location } from 'history'; import type { Filter, Query } from '@kbn/es-query'; +import { isEmpty } from 'lodash/fp'; import type { UrlInputsModel } from '../../store/inputs/model'; import type { TimelineUrl } from '../../../timelines/store/timeline/model'; import { CONSTANTS } from '../url_state/constants'; @@ -31,11 +32,11 @@ export const getSearch = ( ): string => { if (tab && tab.urlKey != null && !isAdministration(tab.urlKey)) { // TODO: Temporary code while we are migrating all query strings to global_query_string_manager - if (globalQueryString.length > 0) { - return `${getUrlStateSearch(urlState)}&${globalQueryString}`; - } else { - return getUrlStateSearch(urlState); - } + const urlStateSearch = getQueryStringFromLocation(getUrlStateSearch(urlState)); + const isNotEmpty = (e: string) => !isEmpty(e); + const search = [urlStateSearch, globalQueryString].filter(isNotEmpty).join('&'); + + return search.length > 0 ? `?${search}` : ''; } return ''; @@ -46,9 +47,7 @@ export const getUrlStateSearch = (urlState: UrlState): string => (myLocation: Location, urlKey: KeyUrlState) => { let urlStateToReplace: Filter[] | Query | TimelineUrl | UrlInputsModel | string = ''; - if (urlKey === CONSTANTS.timerange) { - urlStateToReplace = urlState[CONSTANTS.timerange]; - } else if (urlKey === CONSTANTS.timeline && urlState[CONSTANTS.timeline] != null) { + if (urlKey === CONSTANTS.timeline && urlState[CONSTANTS.timeline] != null) { const timeline = urlState[CONSTANTS.timeline]; if (timeline.id === '') { urlStateToReplace = ''; diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/index.test.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/index.test.tsx index b2aa13a2293ff..521f87ffd034f 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/index.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/index.test.tsx @@ -69,28 +69,6 @@ describe('SIEM Navigation', () => { tabName: HostsTableType.authentications, navTabs, urlState: { - [CONSTANTS.timerange]: { - global: { - [CONSTANTS.timerange]: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - linkTo: ['timeline'], - }, - timeline: { - [CONSTANTS.timerange]: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - linkTo: ['global'], - }, - }, [CONSTANTS.timeline]: { activeTab: TimelineTabs.query, id: '', diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/index.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/index.tsx index 3526817f9d52f..41f1dd11caf49 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/index.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/index.tsx @@ -84,7 +84,6 @@ export const TabNavigationComponent: React.FC< pathName={pathName} tabName={tabName} timeline={urlState.timeline} - timerange={urlState.timerange} /> ); } diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/index.test.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/index.test.tsx index 315b324bf7aca..adfb86cf311d2 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/index.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/index.test.tsx @@ -65,29 +65,6 @@ describe('Table Navigation', () => { hasMlUserPermissions: mockHasMlUserPermissions, isRiskyHostsEnabled: mockRiskyHostEnabled, }), - - [CONSTANTS.timerange]: { - global: { - [CONSTANTS.timerange]: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - linkTo: ['timeline'], - }, - timeline: { - [CONSTANTS.timerange]: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - linkTo: ['global'], - }, - }, [CONSTANTS.timeline]: { activeTab: TimelineTabs.query, id: '', diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/types.ts b/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/types.ts index 5b36c4fb1deef..74804bdd9ee85 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/types.ts +++ b/x-pack/plugins/security_solution/public/common/components/navigation/tab_navigation/types.ts @@ -5,7 +5,6 @@ * 2.0. */ -import type { UrlInputsModel } from '../../../store/inputs/model'; import type { CONSTANTS } from '../../url_state/constants'; import type { TimelineUrl } from '../../../../timelines/store/timeline/model'; import type { SecuritySolutionTabNavigationProps } from '../types'; @@ -15,7 +14,6 @@ export interface TabNavigationProps extends SecuritySolutionTabNavigationProps { pathName: string; pageName: string; tabName: SiemRouteType | undefined; - [CONSTANTS.timerange]: UrlInputsModel; [CONSTANTS.timeline]: TimelineUrl; } diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/use_get_url_search.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/use_get_url_search.tsx index 9e4b1612eebd0..00c8541784e51 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/use_get_url_search.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/use_get_url_search.tsx @@ -5,11 +5,12 @@ * 2.0. */ +import { isEmpty } from 'lodash/fp'; import { useCallback, useMemo } from 'react'; import { useDeepEqualSelector } from '../../hooks/use_selector'; import { useGlobalQueryString } from '../../utils/global_query_string'; -import { makeMapStateToProps } from '../url_state/helpers'; +import { getQueryStringFromLocation, makeMapStateToProps } from '../url_state/helpers'; import { getSearch, getUrlStateSearch } from './helpers'; import type { SearchNavTab } from './types'; @@ -31,11 +32,11 @@ export const useGetUrlStateQueryString = () => { const globalQueryString = useGlobalQueryString(); const getUrlStateQueryString = useCallback(() => { // TODO: Temporary code while we are migrating all query strings to global_query_string_manager - if (globalQueryString.length > 0) { - return `${getUrlStateSearch(urlState)}&${globalQueryString}`; - } + const urlStateSearch = getQueryStringFromLocation(getUrlStateSearch(urlState)); + const isNotEmpty = (e: string) => !isEmpty(e); + const search = [urlStateSearch, globalQueryString].filter(isNotEmpty).join('&'); - return getUrlStateSearch(urlState); + return search.length > 0 ? `?${search}` : ''; }, [urlState, globalQueryString]); return getUrlStateQueryString; diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/__snapshots__/index.test.tsx.snap b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/__snapshots__/index.test.tsx.snap index 8e752eccd06b9..22de526739c17 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/__snapshots__/index.test.tsx.snap +++ b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/__snapshots__/index.test.tsx.snap @@ -8,10 +8,10 @@ Object { "id": "main", "items": Array [ Object { - "data-href": "securitySolutionUI/get_started?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/get_started", "data-test-subj": "navigation-get_started", "disabled": false, - "href": "securitySolutionUI/get_started?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/get_started", "id": "get_started", "isSelected": false, "name": "Get started", @@ -24,20 +24,20 @@ Object { "id": "dashboards", "items": Array [ Object { - "data-href": "securitySolutionUI/overview?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/overview", "data-test-subj": "navigation-overview", "disabled": false, - "href": "securitySolutionUI/overview?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/overview", "id": "overview", "isSelected": false, "name": "Overview", "onClick": [Function], }, Object { - "data-href": "securitySolutionUI/detection_response?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/detection_response", "data-test-subj": "navigation-detection_response", "disabled": false, - "href": "securitySolutionUI/detection_response?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/detection_response", "id": "detection_response", "isSelected": false, "name": "Detection & Response", @@ -50,30 +50,30 @@ Object { "id": "detect", "items": Array [ Object { - "data-href": "securitySolutionUI/alerts?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/alerts", "data-test-subj": "navigation-alerts", "disabled": false, - "href": "securitySolutionUI/alerts?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/alerts", "id": "alerts", "isSelected": false, "name": "Alerts", "onClick": [Function], }, Object { - "data-href": "securitySolutionUI/rules?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/rules", "data-test-subj": "navigation-rules", "disabled": false, - "href": "securitySolutionUI/rules?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/rules", "id": "rules", "isSelected": false, "name": "Rules", "onClick": [Function], }, Object { - "data-href": "securitySolutionUI/exceptions?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/exceptions", "data-test-subj": "navigation-exceptions", "disabled": false, - "href": "securitySolutionUI/exceptions?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/exceptions", "id": "exceptions", "isSelected": false, "name": "Exception lists", @@ -86,30 +86,30 @@ Object { "id": "explore", "items": Array [ Object { - "data-href": "securitySolutionUI/hosts?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/hosts", "data-test-subj": "navigation-hosts", "disabled": false, - "href": "securitySolutionUI/hosts?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/hosts", "id": "hosts", "isSelected": true, "name": "Hosts", "onClick": [Function], }, Object { - "data-href": "securitySolutionUI/network?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/network", "data-test-subj": "navigation-network", "disabled": false, - "href": "securitySolutionUI/network?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/network", "id": "network", "isSelected": false, "name": "Network", "onClick": [Function], }, Object { - "data-href": "securitySolutionUI/users?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/users", "data-test-subj": "navigation-users", "disabled": false, - "href": "securitySolutionUI/users?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/users", "id": "users", "isSelected": false, "name": "Users", @@ -122,20 +122,20 @@ Object { "id": "investigate", "items": Array [ Object { - "data-href": "securitySolutionUI/timelines?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/timelines", "data-test-subj": "navigation-timelines", "disabled": false, - "href": "securitySolutionUI/timelines?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/timelines", "id": "timelines", "isSelected": false, "name": "Timelines", "onClick": [Function], }, Object { - "data-href": "securitySolutionUI/cases?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/cases", "data-test-subj": "navigation-cases", "disabled": false, - "href": "securitySolutionUI/cases?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/cases", "id": "cases", "isSelected": false, "name": "Cases", diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx index bc81b788a5880..0c545ec83a6ef 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx @@ -169,10 +169,10 @@ describe('useSecuritySolutionNavigation', () => { ); expect(caseNavItem).toMatchInlineSnapshot(` Object { - "data-href": "securitySolutionUI/cases?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "data-href": "securitySolutionUI/cases", "data-test-subj": "navigation-cases", "disabled": false, - "href": "securitySolutionUI/cases?timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))", + "href": "securitySolutionUI/cases", "id": "cases", "isSelected": false, "name": "Cases", diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.tsx index 4dd00b1efc218..0243c0c926a94 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.tsx @@ -76,6 +76,5 @@ export const useSecuritySolutionNavigation = () => { pageName, tabName, timeline: urlState.timeline, - timerange: urlState.timerange, }); }; diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/use_primary_navigation.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/use_primary_navigation.tsx index 538163acb6009..b71cd8caee292 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/use_primary_navigation.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/use_primary_navigation.tsx @@ -23,7 +23,6 @@ export const usePrimaryNavigation = ({ pageName, tabName, timeline, - timerange, }: PrimaryNavigationProps): KibanaPageTemplateProps['solutionNav'] => { const isGroupedNavigationEnabled = useIsGroupedNavigationEnabled(); const mapLocationToTab = useCallback( @@ -47,7 +46,6 @@ export const usePrimaryNavigation = ({ navTabs, selectedTabId, timeline, - timerange, }); return { diff --git a/x-pack/plugins/security_solution/public/common/components/search_bar/index.test.tsx b/x-pack/plugins/security_solution/public/common/components/search_bar/index.test.tsx index 81a12d77b39b0..f33b5b57912dd 100644 --- a/x-pack/plugins/security_solution/public/common/components/search_bar/index.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/search_bar/index.test.tsx @@ -186,7 +186,7 @@ describe('SearchBarComponent', () => { expect(mockUpdateUrlParam).toHaveBeenCalledWith(savedQuery.id); }); - it('calls useUpdateUrlParam when query state changes', async () => { + it('calls useUpdateUrlParam when query query changes', async () => { const { storage } = createSecuritySolutionStorageMock(); const store = createStore(mockGlobalState, SUB_PLUGINS_REDUCER, kibanaObservable, storage); @@ -278,4 +278,105 @@ describe('SearchBarComponent', () => { expect(mockUpdateUrlParam).toHaveBeenCalledWith(savedQuery.id); }); }); + + describe('Timerange', () => { + it('calls useUpdateUrlParam when global timerange changes', async () => { + const { storage } = createSecuritySolutionStorageMock(); + const store = createStore(mockGlobalState, SUB_PLUGINS_REDUCER, kibanaObservable, storage); + + render( + + + + ); + + jest.clearAllMocks(); + + const newTimerange = { + from: '2020-07-07T08:20:18.966Z', + fromStr: 'now-24h', + kind: 'relative', + to: '2020-07-08T08:20:18.966Z', + toStr: 'now', + }; + + store.dispatch( + inputsActions.setRelativeRangeDatePicker({ id: 'global' as InputsModelId, ...newTimerange }) + ); + + await waitFor(() => { + expect(mockUpdateUrlParam).toHaveBeenCalledWith( + expect.objectContaining({ + global: { + linkTo: ['timeline'], + timerange: newTimerange, + }, + }) + ); + }); + }); + + it('calls useUpdateUrlParam when timeline timerange changes', async () => { + const { storage } = createSecuritySolutionStorageMock(); + const store = createStore(mockGlobalState, SUB_PLUGINS_REDUCER, kibanaObservable, storage); + + render( + + + + ); + + jest.clearAllMocks(); + + const newTimerange = { + from: '2020-07-07T08:20:18.966Z', + fromStr: 'now-24h', + kind: 'relative', + to: '2020-07-08T08:20:18.966Z', + toStr: 'now', + }; + + store.dispatch( + inputsActions.setRelativeRangeDatePicker({ + id: 'timeline' as InputsModelId, + ...newTimerange, + }) + ); + + await waitFor(() => { + expect(mockUpdateUrlParam).toHaveBeenCalledWith( + expect.objectContaining({ + timeline: { + linkTo: ['global'], + timerange: newTimerange, + }, + }) + ); + }); + }); + + it('initializes timerange URL param with redux date on mount', async () => { + const { storage } = createSecuritySolutionStorageMock(); + const store = createStore(mockGlobalState, SUB_PLUGINS_REDUCER, kibanaObservable, storage); + jest.clearAllMocks(); + render( + + + + ); + + expect(mockUpdateUrlParam.mock.calls[3]).toEqual([ + { + global: { + timerange: mockGlobalState.inputs.global.timerange, + linkTo: mockGlobalState.inputs.global.linkTo, + }, + timeline: { + timerange: mockGlobalState.inputs.timeline.timerange, + linkTo: mockGlobalState.inputs.timeline.linkTo, + }, + }, + ]); + }); + }); }); diff --git a/x-pack/plugins/security_solution/public/common/components/search_bar/index.tsx b/x-pack/plugins/security_solution/public/common/components/search_bar/index.tsx index c2e367aed59ab..e833f1f1a5dbd 100644 --- a/x-pack/plugins/security_solution/public/common/components/search_bar/index.tsx +++ b/x-pack/plugins/security_solution/public/common/components/search_bar/index.tsx @@ -19,7 +19,6 @@ import type { FilterManager, SavedQuery } from '@kbn/data-plugin/public'; import type { DataView } from '@kbn/data-views-plugin/public'; import type { OnTimeChangeProps } from '@elastic/eui'; - import { inputsActions } from '../../store/inputs'; import type { InputsRange } from '../../store/inputs/model'; import type { InputsModelId } from '../../store/inputs/constants'; @@ -41,6 +40,7 @@ import { usersActions } from '../../../users/store'; import { hostsActions } from '../../../hosts/store'; import { networkActions } from '../../../network/store'; import { useSyncSearchBarUrlParams } from '../../hooks/search_bar/use_sync_search_bar_url_param'; +import { useSyncTimerangeUrlParam } from '../../hooks/search_bar/use_sync_timerange_url_param'; interface SiemSearchBarProps { id: InputsModelId; @@ -92,6 +92,7 @@ export const SearchBarComponent = memo( }, [dispatch]); useSyncSearchBarUrlParams(); + useSyncTimerangeUrlParam(); useEffect(() => { if (fromStr != null && toStr != null) { diff --git a/x-pack/plugins/security_solution/public/common/components/url_state/helpers.ts b/x-pack/plugins/security_solution/public/common/components/url_state/helpers.ts index e8719ae8d0968..f045053cd4f29 100644 --- a/x-pack/plugins/security_solution/public/common/components/url_state/helpers.ts +++ b/x-pack/plugins/security_solution/public/common/components/url_state/helpers.ts @@ -14,11 +14,8 @@ import { url } from '@kbn/kibana-utils-plugin/public'; import { TimelineId, TimelineTabs } from '../../../../common/types/timeline'; import { SecurityPageName } from '../../../app/types'; import type { State } from '../../store'; -import { inputsSelectors } from '../../store'; -import type { UrlInputsModel } from '../../store/inputs/model'; import type { TimelineUrl } from '../../../timelines/store/timeline/model'; import { timelineSelectors } from '../../../timelines/store/timeline'; -import { formatDate } from '../super_date_picker'; import type { NavTab } from '../navigation/types'; import type { UrlStateType } from './constants'; import { CONSTANTS } from './constants'; @@ -123,13 +120,8 @@ export const getTitle = (pageName: string, navTabs: Record): str }; export const makeMapStateToProps = () => { - const getInputsSelector = inputsSelectors.inputsSelector(); const getTimeline = timelineSelectors.getTimelineByIdSelector(); const mapStateToProps = (state: State) => { - const inputState = getInputsSelector(state); - const { linkTo: globalLinkTo, timerange: globalTimerange } = inputState.global; - const { linkTo: timelineLinkTo, timerange: timelineTimerange } = inputState.timeline; - const flyoutTimeline = getTimeline(state, TimelineId.active); const timeline = flyoutTimeline != null @@ -143,16 +135,6 @@ export const makeMapStateToProps = () => { return { urlState: { - [CONSTANTS.timerange]: { - global: { - [CONSTANTS.timerange]: globalTimerange, - linkTo: globalLinkTo, - }, - timeline: { - [CONSTANTS.timerange]: timelineTimerange, - linkTo: timelineLinkTo, - }, - }, [CONSTANTS.timeline]: timeline, }, }; @@ -161,23 +143,6 @@ export const makeMapStateToProps = () => { return mapStateToProps; }; -export const updateTimerangeUrl = ( - timeRange: UrlInputsModel, - isFirstPageLoad: boolean -): UrlInputsModel => { - if (timeRange.global.timerange.kind === 'relative') { - timeRange.global.timerange.from = formatDate(timeRange.global.timerange.fromStr); - timeRange.global.timerange.to = formatDate(timeRange.global.timerange.toStr, { roundUp: true }); - } - if (timeRange.timeline.timerange.kind === 'relative' && isFirstPageLoad) { - timeRange.timeline.timerange.from = formatDate(timeRange.timeline.timerange.fromStr); - timeRange.timeline.timerange.to = formatDate(timeRange.timeline.timerange.toStr, { - roundUp: true, - }); - } - return timeRange; -}; - export const isQueryStateEmpty = ( queryState: ValueUrlState | undefined | null, urlKey: KeyUrlState diff --git a/x-pack/plugins/security_solution/public/common/components/url_state/index.test.tsx b/x-pack/plugins/security_solution/public/common/components/url_state/index.test.tsx index 912ae85c048d9..88b75e88dd27a 100644 --- a/x-pack/plugins/security_solution/public/common/components/url_state/index.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/url_state/index.test.tsx @@ -12,17 +12,9 @@ import { HookWrapper } from '../../mock'; import { SecurityPageName } from '../../../app/types'; import type { RouteSpyState } from '../../utils/route/types'; import { CONSTANTS } from './constants'; -import { - getMockPropsObj, - mockHistory, - mockSetAbsoluteRangeDatePicker, - mockSetRelativeRangeDatePicker, - testCases, - getMockProps, -} from './test_dependencies'; +import { getMockPropsObj, mockHistory, getMockProps } from './test_dependencies'; import type { UrlStateContainerPropTypes } from './types'; import { useUrlStateHooks } from './use_url_state'; -import { waitFor } from '@testing-library/react'; import { useLocation } from 'react-router-dom'; import { updateAppLinks } from '../../links'; import { links } from '../../links/app_links'; @@ -109,79 +101,6 @@ describe('UrlStateContainer', () => { }); describe('handleInitialize', () => { - describe('URL state updates redux', () => { - describe('relative timerange actions are called with correct data on component mount', () => { - test.each(testCases)( - '%o', - (page, namespaceLower, namespaceUpper, examplePath, type, pageName, detailName) => { - mockProps = getMockPropsObj({ - page, - examplePath, - namespaceLower, - pageName, - detailName, - }).relativeTimeSearch.undefinedQuery; - - (useLocation as jest.Mock).mockReturnValue({ - pathname: mockProps.pathName, - search: mockProps.search, - }); - - mount( useUrlStateHooks(args)} />); - - expect(mockSetRelativeRangeDatePicker.mock.calls[1][0]).toEqual({ - from: '2020-01-01T00:00:00.000Z', - fromStr: 'now-1d/d', - kind: 'relative', - to: '2020-01-01T00:00:00.000Z', - toStr: 'now-1d/d', - id: 'global', - }); - - expect(mockSetRelativeRangeDatePicker.mock.calls[0][0]).toEqual({ - from: '2020-01-01T00:00:00.000Z', - fromStr: 'now-15m', - kind: 'relative', - to: '2020-01-01T00:00:00.000Z', - toStr: 'now', - id: 'timeline', - }); - } - ); - }); - - describe('absolute timerange actions are called with correct data on component mount', () => { - test.each(testCases)( - '%o', - (page, namespaceLower, namespaceUpper, examplePath, type, pageName, detailName) => { - mockProps = getMockPropsObj({ page, examplePath, namespaceLower, pageName, detailName }) - .absoluteTimeSearch.undefinedQuery; - - (useLocation as jest.Mock).mockReturnValue({ - pathname: mockProps.pathName, - search: mockProps.search, - }); - - mount( useUrlStateHooks(args)} />); - - expect(mockSetAbsoluteRangeDatePicker.mock.calls[1][0]).toEqual({ - from: '2019-05-01T18:40:12.685Z', - kind: 'absolute', - to: '2019-05-02T18:40:16.082Z', - id: 'global', - }); - - expect(mockSetAbsoluteRangeDatePicker.mock.calls[0][0]).toEqual({ - from: '2019-05-01T18:40:12.685Z', - kind: 'absolute', - to: '2019-05-02T18:40:16.082Z', - id: 'timeline', - }); - } - ); - }); - }); - it("it doesn't update URL state when pathName and browserPAth are out of sync", () => { mockProps = getMockPropsObj({ page: CONSTANTS.networkPage, @@ -267,66 +186,4 @@ describe('UrlStateContainer', () => { expect(mockHistory.replace.mock.calls[0][0].search).not.toContain('timeline='); }); }); - - describe('After Initialization, keep Relative Date up to date for global only on alerts page', () => { - test.each(testCases)( - '%o', - async (page, namespaceLower, namespaceUpper, examplePath, type, pageName, detailName) => { - mockProps = getMockPropsObj({ - page, - examplePath, - namespaceLower, - pageName, - detailName, - }).relativeTimeSearch.undefinedQuery; - - (useLocation as jest.Mock).mockReturnValue({ - pathname: mockProps.pathName, - search: mockProps.search, - }); - - const wrapper = mount( - useUrlStateHooks(args)} /> - ); - - wrapper.setProps({ - hookProps: getMockPropsObj({ - page: CONSTANTS.hostsPage, - examplePath: '/hosts', - namespaceLower: 'hosts', - pageName: SecurityPageName.hosts, - detailName: undefined, - }).relativeTimeSearch.undefinedQuery, - }); - wrapper.update(); - - if (CONSTANTS.alertsPage === page) { - await waitFor(() => { - expect(mockSetRelativeRangeDatePicker.mock.calls[3][0]).toEqual({ - from: '2020-01-01T00:00:00.000Z', - fromStr: 'now-1d/d', - kind: 'relative', - to: '2020-01-01T00:00:00.000Z', - toStr: 'now-1d/d', - id: 'global', - }); - - expect(mockSetRelativeRangeDatePicker.mock.calls[2][0]).toEqual({ - from: 1558732849370, - fromStr: 'now-15m', - kind: 'relative', - to: 1558733749370, - toStr: 'now', - id: 'timeline', - }); - }); - } else { - await waitFor(() => { - // There is no change in url state, so that's expected we only have two actions - expect(mockSetRelativeRangeDatePicker.mock.calls.length).toEqual(2); - }); - } - } - ); - }); }); diff --git a/x-pack/plugins/security_solution/public/common/components/url_state/index_mocked.test.tsx b/x-pack/plugins/security_solution/public/common/components/url_state/index_mocked.test.tsx index 8d9fa294c41b1..6729b19f235d7 100644 --- a/x-pack/plugins/security_solution/public/common/components/url_state/index_mocked.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/url_state/index_mocked.test.tsx @@ -12,7 +12,7 @@ import { HookWrapper } from '../../mock/hook_wrapper'; import { SecurityPageName } from '../../../app/types'; import { CONSTANTS } from './constants'; -import { getFilterQuery, getMockPropsObj, mockHistory, testCases } from './test_dependencies'; +import { getFilterQuery, getMockPropsObj, mockHistory } from './test_dependencies'; import type { UrlStateContainerPropTypes } from './types'; import { useUrlStateHooks } from './use_url_state'; import { useLocation } from 'react-router-dom'; @@ -77,62 +77,6 @@ describe('UrlStateContainer - lodash.throttle mocked to test update url', () => }); describe('componentDidUpdate', () => { - test('timerange redux state updates the url', () => { - mockProps = getMockPropsObj({ - page: CONSTANTS.networkPage, - examplePath: '/network', - namespaceLower: 'network', - pageName: SecurityPageName.network, - detailName: undefined, - }).noSearch.definedQuery; - - (useLocation as jest.Mock).mockReturnValue({ - pathname: mockProps.pathName, - search: mockProps.search, - }); - - const wrapper = mount( - useUrlStateHooks(args)} /> - ); - - const newUrlState = { - ...mockProps.urlState, - [CONSTANTS.timerange]: { - global: { - [CONSTANTS.timerange]: { - from: '2020-07-07T08:20:18.966Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2020-07-08T08:20:18.966Z', - toStr: 'now', - }, - linkTo: ['timeline'], - }, - timeline: { - [CONSTANTS.timerange]: { - from: '2020-07-07T08:20:18.966Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2020-07-08T08:20:18.966Z', - toStr: 'now', - }, - linkTo: ['global'], - }, - }, - }; - - wrapper.setProps({ hookProps: { ...mockProps, urlState: newUrlState } }); - wrapper.update(); - expect(mockHistory.replace.mock.calls[1][0]).toStrictEqual({ - hash: '', - pathname: '/network', - search: expect.stringContaining( - "timerange=(global:(linkTo:!(timeline),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2020-07-07T08:20:18.966Z',fromStr:now-24h,kind:relative,to:'2020-07-08T08:20:18.966Z',toStr:now)))" - ), - state: '', - }); - }); - test('timelineID redux state updates the url', () => { mockProps = getMockPropsObj({ page: CONSTANTS.networkPage, @@ -163,8 +107,7 @@ describe('UrlStateContainer - lodash.throttle mocked to test update url', () => expect(mockHistory.replace.mock.calls[1][0]).toStrictEqual({ hash: '', pathname: '/network', - search: - "?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))&timeline=(id:hello_timeline_id,isOpen:!t)", + search: '?timeline=(id:hello_timeline_id,isOpen:!t)', state: '', }); }); @@ -327,121 +270,4 @@ describe('UrlStateContainer - lodash.throttle mocked to test update url', () => }); }); }); - - describe('handleInitialize', () => { - describe('Redux updates URL state', () => { - describe('Timerange url state is set when not defined on component mount', () => { - test.each(testCases)( - '%o', - (page, namespaceLower, namespaceUpper, examplePath, type, pageName, detailName) => { - mockProps = getMockPropsObj({ page, examplePath, namespaceLower, pageName, detailName }) - .noSearch.undefinedQuery; - - (useLocation as jest.Mock).mockReturnValue({ - pathname: mockProps.pathName, - search: mockProps.search, - }); - - mount( useUrlStateHooks(args)} />); - - expect(mockHistory.replace.mock.calls[0][0]).toEqual({ - hash: '', - pathname: examplePath, - search: - "?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))", - state: '', - }); - } - ); - - test('url state is set from redux data when location updates and initialization', () => { - mockProps = getMockPropsObj({ - page: CONSTANTS.hostsPage, - examplePath: '/hosts', - namespaceLower: 'hosts', - pageName: SecurityPageName.hosts, - detailName: undefined, - }).noSearch.undefinedQuery; - const updatedProps = getMockPropsObj({ - page: CONSTANTS.networkPage, - examplePath: '/network', - namespaceLower: 'network', - pageName: SecurityPageName.network, - detailName: undefined, - }).noSearch.definedQuery; - - (useLocation as jest.Mock).mockReturnValue({ - pathname: mockProps.pathName, - search: mockProps.search, - }); - - const wrapper = mount( - useUrlStateHooks(args)} /> - ); - - expect(mockHistory.replace.mock.calls[0][0].search).toEqual( - "?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))" - ); - - (useLocation as jest.Mock).mockReturnValue({ - pathname: updatedProps.pathName, - search: mockProps.search, - }); - - wrapper.setProps({ hookProps: updatedProps }); - - wrapper.update(); - - expect(mockHistory.replace.mock.calls[1][0].search).toEqual( - "?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))" - ); - }); - - test("doesn't update url state on administration page", () => { - mockProps = getMockPropsObj({ - page: CONSTANTS.hostsPage, - examplePath: '/hosts', - namespaceLower: 'hosts', - pageName: SecurityPageName.hosts, - detailName: undefined, - }).noSearch.undefinedQuery; - - const updatedMockProps = { - ...getMockPropsObj({ - ...mockProps, - page: CONSTANTS.unknown, - examplePath: MANAGEMENT_PATH, - namespaceLower: 'administration', - pageName: SecurityPageName.administration, - detailName: undefined, - }).noSearch.definedQuery, - }; - - (useLocation as jest.Mock).mockReturnValue({ - pathname: mockProps.pathName, - search: mockProps.search, - }); - - const wrapper = mount( - useUrlStateHooks(args)} /> - ); - - expect(mockHistory.replace.mock.calls[0][0].search).toEqual( - "?timerange=(global:(linkTo:!(timeline),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)),timeline:(linkTo:!(global),timerange:(from:'2019-05-16T23:10:43.696Z',fromStr:now-24h,kind:relative,to:'2019-05-17T23:10:43.697Z',toStr:now)))" - ); - - (useLocation as jest.Mock).mockReturnValue({ - pathname: updatedMockProps.pathName, - search: mockProps.search, - }); - - wrapper.setProps({ hookProps: updatedMockProps }); - - wrapper.update(); - - expect(mockHistory.replace.mock.calls[1][0].search).toEqual('?'); - }); - }); - }); - }); }); diff --git a/x-pack/plugins/security_solution/public/common/components/url_state/initialize_redux_by_url.tsx b/x-pack/plugins/security_solution/public/common/components/url_state/initialize_redux_by_url.tsx index 187b1aadedcd4..7d404cf687f91 100644 --- a/x-pack/plugins/security_solution/public/common/components/url_state/initialize_redux_by_url.tsx +++ b/x-pack/plugins/security_solution/public/common/components/url_state/initialize_redux_by_url.tsx @@ -5,23 +5,11 @@ * 2.0. */ -import { get, isEmpty } from 'lodash/fp'; -import type { Dispatch } from 'redux'; - import { useCallback, useMemo } from 'react'; import { useDispatch } from 'react-redux'; -import { inputsActions } from '../../store/actions'; -import type { InputsModelId, TimeRangeKinds } from '../../store/inputs/constants'; -import type { - UrlInputsModel, - LinkTo, - AbsoluteTimeRange, - RelativeTimeRange, -} from '../../store/inputs/model'; import type { TimelineUrl } from '../../../timelines/store/timeline/model'; import { CONSTANTS } from './constants'; import { decodeRisonUrlState } from './helpers'; -import { normalizeTimeRange } from './normalize_time_range'; import type { SetInitialStateFromUrl } from './types'; import { queryTimelineById, @@ -31,7 +19,6 @@ import { timelineActions } from '../../../timelines/store/timeline'; export const useSetInitialStateFromUrl = () => { const dispatch = useDispatch(); - const updateTimeline = useMemo(() => dispatchUpdateTimeline(dispatch), [dispatch]); const updateTimelineIsLoading = useMemo( @@ -43,10 +30,6 @@ export const useSetInitialStateFromUrl = () => { const setInitialStateFromUrl = useCallback( ({ urlStateToUpdate }: SetInitialStateFromUrl) => { urlStateToUpdate.forEach(({ urlKey, newUrlStateString }) => { - if (urlKey === CONSTANTS.timerange) { - updateTimerange(newUrlStateString, dispatch); - } - if (urlKey === CONSTANTS.timeline) { const timeline = decodeRisonUrlState(newUrlStateString); if (timeline != null && timeline.id !== '') { @@ -63,87 +46,8 @@ export const useSetInitialStateFromUrl = () => { } }); }, - [dispatch, updateTimeline, updateTimelineIsLoading] + [updateTimeline, updateTimelineIsLoading] ); return Object.freeze({ setInitialStateFromUrl, updateTimeline, updateTimelineIsLoading }); }; - -const updateTimerange = (newUrlStateString: string, dispatch: Dispatch) => { - const timerangeStateData = decodeRisonUrlState(newUrlStateString); - - const globalId: InputsModelId = 'global'; - const globalLinkTo: LinkTo = { linkTo: get('global.linkTo', timerangeStateData) }; - const globalType: TimeRangeKinds = get('global.timerange.kind', timerangeStateData); - - const timelineId: InputsModelId = 'timeline'; - const timelineLinkTo: LinkTo = { linkTo: get('timeline.linkTo', timerangeStateData) }; - const timelineType: TimeRangeKinds = get('timeline.timerange.kind', timerangeStateData); - - if (isEmpty(globalLinkTo.linkTo)) { - dispatch(inputsActions.removeGlobalLinkTo()); - } else { - dispatch(inputsActions.addGlobalLinkTo({ linkToId: 'timeline' })); - } - - if (isEmpty(timelineLinkTo.linkTo)) { - dispatch(inputsActions.removeTimelineLinkTo()); - } else { - dispatch(inputsActions.addTimelineLinkTo({ linkToId: 'global' })); - } - - if (timelineType) { - if (timelineType === 'absolute') { - const absoluteRange = normalizeTimeRange( - get('timeline.timerange', timerangeStateData) - ); - - dispatch( - inputsActions.setAbsoluteRangeDatePicker({ - ...absoluteRange, - id: timelineId, - }) - ); - } - - if (timelineType === 'relative') { - const relativeRange = normalizeTimeRange( - get('timeline.timerange', timerangeStateData) - ); - - dispatch( - inputsActions.setRelativeRangeDatePicker({ - ...relativeRange, - id: timelineId, - }) - ); - } - } - - if (globalType) { - if (globalType === 'absolute') { - const absoluteRange = normalizeTimeRange( - get('global.timerange', timerangeStateData) - ); - - dispatch( - inputsActions.setAbsoluteRangeDatePicker({ - ...absoluteRange, - id: globalId, - }) - ); - } - if (globalType === 'relative') { - const relativeRange = normalizeTimeRange( - get('global.timerange', timerangeStateData) - ); - - dispatch( - inputsActions.setRelativeRangeDatePicker({ - ...relativeRange, - id: globalId, - }) - ); - } - } -}; diff --git a/x-pack/plugins/security_solution/public/common/components/url_state/test_dependencies.ts b/x-pack/plugins/security_solution/public/common/components/url_state/test_dependencies.ts index 2e7b1b4b99a4b..9a3dd5f7d2896 100644 --- a/x-pack/plugins/security_solution/public/common/components/url_state/test_dependencies.ts +++ b/x-pack/plugins/security_solution/public/common/components/url_state/test_dependencies.ts @@ -12,8 +12,6 @@ import { inputsActions } from '../../store/actions'; import { CONSTANTS } from './constants'; import type { UrlStateContainerPropTypes, LocationTypes } from './types'; -import { networkModel } from '../../../network/store'; -import { hostsModel } from '../../../hosts/store'; import { HostsTableType } from '../../../hosts/store/model'; import { TimelineTabs } from '../../../../common/types/timeline'; @@ -91,28 +89,6 @@ export const defaultProps: UrlStateContainerPropTypes = { title: 'filebeat-*,packetbeat-*', }, urlState: { - [CONSTANTS.timerange]: { - global: { - [CONSTANTS.timerange]: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - linkTo: ['timeline'], - }, - timeline: { - [CONSTANTS.timerange]: { - from: '2019-05-16T23:10:43.696Z', - fromStr: 'now-24h', - kind: 'relative', - to: '2019-05-17T23:10:43.697Z', - toStr: 'now', - }, - linkTo: ['global'], - }, - }, [CONSTANTS.timeline]: { activeTab: TimelineTabs.query, id: '', @@ -262,73 +238,3 @@ export const getMockPropsObj = ({ page, examplePath, pageName, detailName }: Get ), }, }); - -// silly that this needs to be an array and not an object -// https://jestjs.io/docs/en/api#testeachtable-name-fn-timeout -export const testCases: Array< - [LocationTypes, string, string, string, string | null, SecurityPageName, undefined | string] -> = [ - [ - /* page */ CONSTANTS.networkPage, - /* namespaceLower */ 'network', - /* namespaceUpper */ 'Network', - /* pathName */ '/network', - /* type */ networkModel.NetworkType.page, - /* pageName */ SecurityPageName.network, - /* detailName */ undefined, - ], - [ - /* page */ CONSTANTS.hostsPage, - /* namespaceLower */ 'hosts', - /* namespaceUpper */ 'Hosts', - /* pathName */ '/hosts', - /* type */ hostsModel.HostsType.page, - /* pageName */ SecurityPageName.hosts, - /* detailName */ undefined, - ], - [ - /* page */ CONSTANTS.hostsDetails, - /* namespaceLower */ 'hosts', - /* namespaceUpper */ 'Hosts', - /* pathName */ '/hosts/siem-es', - /* type */ hostsModel.HostsType.details, - /* pageName */ SecurityPageName.hosts, - /* detailName */ 'host-test', - ], - [ - /* page */ CONSTANTS.networkDetails, - /* namespaceLower */ 'network', - /* namespaceUpper */ 'Network', - /* pathName */ '/network/ip/100.90.80', - /* type */ networkModel.NetworkType.details, - /* pageName */ SecurityPageName.network, - /* detailName */ '100.90.80', - ], - [ - /* page */ CONSTANTS.overviewPage, - /* namespaceLower */ 'overview', - /* namespaceUpper */ 'Overview', - /* pathName */ '/overview', - /* type */ null, - /* pageName */ SecurityPageName.overview, - /* detailName */ undefined, - ], - [ - /* page */ CONSTANTS.timelinePage, - /* namespaceLower */ 'timeline', - /* namespaceUpper */ 'Timeline', - /* pathName */ '/timeline', - /* type */ null, - /* pageName */ SecurityPageName.timelines, - /* detailName */ undefined, - ], - [ - /* page */ CONSTANTS.kubernetesPage, - /* namespaceLower */ 'kubernetes', - /* namespaceUpper */ 'Kubernetes', - /* pathName */ '/kubernetes', - /* type */ null, - /* pageName */ SecurityPageName.kubernetes, - /* detailName */ undefined, - ], -]; diff --git a/x-pack/plugins/security_solution/public/common/components/url_state/types.ts b/x-pack/plugins/security_solution/public/common/components/url_state/types.ts index 01aa4fdd2c410..6c74320ce237c 100644 --- a/x-pack/plugins/security_solution/public/common/components/url_state/types.ts +++ b/x-pack/plugins/security_solution/public/common/components/url_state/types.ts @@ -7,7 +7,6 @@ import type { DataViewBase } from '@kbn/es-query'; import type { FilterManager, SavedQueryService } from '@kbn/data-plugin/public'; -import type { UrlInputsModel } from '../../store/inputs/model'; import type { TimelineUrl } from '../../../timelines/store/timeline/model'; import type { RouteSpyState } from '../../utils/route/types'; import type { SecurityNav } from '../navigation/types'; @@ -15,7 +14,7 @@ import type { SecurityNav } from '../navigation/types'; import type { UrlStateType } from './constants'; import { CONSTANTS } from './constants'; -export const ALL_URL_STATE_KEYS: KeyUrlState[] = [CONSTANTS.timerange, CONSTANTS.timeline]; +export const ALL_URL_STATE_KEYS: KeyUrlState[] = [CONSTANTS.timeline]; export const isAdministration = (urlKey: UrlStateType): boolean => 'administration' === urlKey; @@ -33,7 +32,6 @@ export type LocationTypes = | CONSTANTS.unknown; export interface UrlState { - [CONSTANTS.timerange]: UrlInputsModel; [CONSTANTS.timeline]: TimelineUrl; } export type KeyUrlState = keyof UrlState; diff --git a/x-pack/plugins/security_solution/public/common/components/url_state/use_url_state.tsx b/x-pack/plugins/security_solution/public/common/components/url_state/use_url_state.tsx index 2cb24c4430427..0be72ef931101 100644 --- a/x-pack/plugins/security_solution/public/common/components/url_state/use_url_state.tsx +++ b/x-pack/plugins/security_solution/public/common/components/url_state/use_url_state.tsx @@ -25,7 +25,6 @@ import { isDetectionsPages, encodeRisonUrlState, isQueryStateEmpty, - updateTimerangeUrl, } from './helpers'; import type { UrlStateContainerPropTypes, @@ -38,7 +37,6 @@ import type { } from './types'; import { ALL_URL_STATE_KEYS, isAdministration } from './types'; import type { TimelineUrl } from '../../../timelines/store/timeline/model'; -import type { UrlInputsModel } from '../../store/inputs/model'; import { queryTimelineByIdOnUrlChange } from './query_timeline_by_id_on_url_change'; import { getLinkInfo } from '../../links'; import { useIsGroupedNavigationEnabled } from '../navigation/helpers'; @@ -97,7 +95,6 @@ export const useUrlStateHooks = ({ const stateToUpdate = getUpdateToFormatUrlStateString({ isFirstPageLoad, newUrlStateString, - updateTimerange: isDetectionsPages(pageName) || isFirstPageLoad, urlKey, }); @@ -227,12 +224,10 @@ const getQueryStringKeyValue = ({ search, urlKey }: { search: string; urlKey: st export const getUpdateToFormatUrlStateString = ({ isFirstPageLoad, newUrlStateString, - updateTimerange, urlKey, }: { isFirstPageLoad: boolean; newUrlStateString: string; - updateTimerange: boolean; urlKey: KeyUrlState; }): ReplaceStateInLocation | undefined => { if (isQueryStateEmpty(decodeRisonUrlState(newUrlStateString), urlKey)) { @@ -240,16 +235,7 @@ export const getUpdateToFormatUrlStateString = ({ urlStateToReplace: '', urlStateKey: urlKey, }; - } else if (urlKey === CONSTANTS.timerange && updateTimerange) { - const queryState = decodeRisonUrlState(newUrlStateString); - if (queryState != null && queryState.global != null) { - return { - urlStateToReplace: updateTimerangeUrl(queryState, isFirstPageLoad), - urlStateKey: urlKey, - }; - } } - return undefined; }; const isTimelinePresentInUrlStateString = (urlStateString: string, timeline: TimelineUrl) => { diff --git a/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_search_bar_url_params.ts b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_search_bar_url_params.ts index 0424b86619bb2..608f38b7428a9 100644 --- a/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_search_bar_url_params.ts +++ b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_search_bar_url_params.ts @@ -14,7 +14,7 @@ import { inputsActions } from '../../store/inputs'; import { useInitializeUrlParam } from '../../utils/global_query_string'; import { CONSTANTS } from '../../components/url_state/constants'; -export const useInitSearchBarUrlParams = () => { +export const useInitSearchBarFromUrlParams = () => { const dispatch = useDispatch(); const { filterManager, savedQueries } = useKibana().services.data.query; const getGlobalFiltersQuerySelector = useMemo( @@ -23,7 +23,7 @@ export const useInitSearchBarUrlParams = () => { ); const filtersFromStore = useSelector(getGlobalFiltersQuerySelector); - const onInitializeAppQueryUrlParam = useCallback( + const onInitializeAppQueryFromUrlParam = useCallback( (initialState: Query | null) => { if (initialState != null) { dispatch( @@ -38,7 +38,7 @@ export const useInitSearchBarUrlParams = () => { [dispatch] ); - const onInitializeFiltersUrlParam = useCallback( + const onInitializeFiltersFromUrlParam = useCallback( (initialState: Filter[] | null) => { if (initialState != null) { filterManager.setFilters(initialState); @@ -63,7 +63,7 @@ export const useInitSearchBarUrlParams = () => { [filterManager, dispatch, filtersFromStore] ); - const onInitializeSavedQueryUrlParam = useCallback( + const onInitializeSavedQueryFromUrlParam = useCallback( (savedQueryId: string | null) => { if (savedQueryId != null && savedQueryId !== '') { savedQueries.getSavedQuery(savedQueryId).then((savedQueryData) => { @@ -91,7 +91,7 @@ export const useInitSearchBarUrlParams = () => { [dispatch, filterManager, savedQueries] ); - useInitializeUrlParam(CONSTANTS.appQuery, onInitializeAppQueryUrlParam); - useInitializeUrlParam(CONSTANTS.filters, onInitializeFiltersUrlParam); - useInitializeUrlParam(CONSTANTS.savedQuery, onInitializeSavedQueryUrlParam); + useInitializeUrlParam(CONSTANTS.appQuery, onInitializeAppQueryFromUrlParam); + useInitializeUrlParam(CONSTANTS.filters, onInitializeFiltersFromUrlParam); + useInitializeUrlParam(CONSTANTS.savedQuery, onInitializeSavedQueryFromUrlParam); }; diff --git a/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_timerange_url_params.ts b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_timerange_url_params.ts new file mode 100644 index 0000000000000..2d5c00aa600f5 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_init_timerange_url_params.ts @@ -0,0 +1,129 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useCallback } from 'react'; +import { get, isEmpty } from 'lodash/fp'; +import { useDispatch } from 'react-redux'; +import type { Dispatch } from 'redux'; +import type { InputsModelId, TimeRangeKinds } from '../../store/inputs/constants'; +import type { + AbsoluteTimeRange, + LinkTo, + RelativeTimeRange, + UrlInputsModel, +} from '../../store/inputs/model'; +import { normalizeTimeRange } from '../../components/url_state/normalize_time_range'; +import { inputsActions } from '../../store/inputs'; +import { formatDate } from '../../components/super_date_picker'; +import { useInitializeUrlParam } from '../../utils/global_query_string'; +import { CONSTANTS } from '../../components/url_state/constants'; + +export const useInitTimerangeFromUrlParam = () => { + const dispatch = useDispatch(); + + const onInitialize = useCallback( + (initialState: UrlInputsModel | null) => + initializeTimerangeFromUrlParam(initialState, dispatch), + [dispatch] + ); + + useInitializeUrlParam(CONSTANTS.timerange, onInitialize); +}; + +const initializeTimerangeFromUrlParam = ( + initialState: UrlInputsModel | null, + dispatch: Dispatch +) => { + if (initialState != null) { + const globalId: InputsModelId = 'global'; + const globalLinkTo: LinkTo = { linkTo: get('global.linkTo', initialState) }; + const globalType: TimeRangeKinds = get('global.timerange.kind', initialState); + + const timelineId: InputsModelId = 'timeline'; + const timelineLinkTo: LinkTo = { linkTo: get('timeline.linkTo', initialState) }; + const timelineType: TimeRangeKinds = get('timeline.timerange.kind', initialState); + + if (isEmpty(globalLinkTo.linkTo)) { + dispatch(inputsActions.removeGlobalLinkTo()); + } else { + dispatch(inputsActions.addGlobalLinkTo({ linkToId: 'timeline' })); + } + + if (isEmpty(timelineLinkTo.linkTo)) { + dispatch(inputsActions.removeTimelineLinkTo()); + } else { + dispatch(inputsActions.addTimelineLinkTo({ linkToId: 'global' })); + } + + if (timelineType) { + if (timelineType === 'absolute') { + const absoluteRange = normalizeTimeRange( + get('timeline.timerange', initialState) + ); + + dispatch( + inputsActions.setAbsoluteRangeDatePicker({ + ...absoluteRange, + id: timelineId, + }) + ); + } + + if (timelineType === 'relative') { + const relativeRange = normalizeTimeRange( + get('timeline.timerange', initialState) + ); + + // Updates date values when timerange is relative + relativeRange.from = formatDate(relativeRange.fromStr); + relativeRange.to = formatDate(relativeRange.toStr, { + roundUp: true, + }); + + dispatch( + inputsActions.setRelativeRangeDatePicker({ + ...relativeRange, + id: timelineId, + }) + ); + } + } + + if (globalType) { + if (globalType === 'absolute') { + const absoluteRange = normalizeTimeRange( + get('global.timerange', initialState) + ); + + dispatch( + inputsActions.setAbsoluteRangeDatePicker({ + ...absoluteRange, + id: globalId, + }) + ); + } + if (globalType === 'relative') { + const relativeRange = normalizeTimeRange( + get('global.timerange', initialState) + ); + + // Updates date values when timerange is relative + relativeRange.from = formatDate(relativeRange.fromStr); + relativeRange.to = formatDate(relativeRange.toStr, { + roundUp: true, + }); + + dispatch( + inputsActions.setRelativeRangeDatePicker({ + ...relativeRange, + id: globalId, + }) + ); + } + } + } +}; diff --git a/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_sync_timerange_url_param.ts b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_sync_timerange_url_param.ts new file mode 100644 index 0000000000000..a14299b7f2267 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_sync_timerange_url_param.ts @@ -0,0 +1,34 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import { useEffect, useMemo } from 'react'; +import { useSelector } from 'react-redux'; +import type { UrlInputsModel } from '../../store/inputs/model'; +import { inputsSelectors } from '../../store/inputs'; +import { useUpdateUrlParam } from '../../utils/global_query_string'; +import { CONSTANTS } from '../../components/url_state/constants'; + +export const useSyncTimerangeUrlParam = () => { + const updateTimerangeUrlParam = useUpdateUrlParam(CONSTANTS.timerange); + const getInputSelector = useMemo(() => inputsSelectors.inputsSelector(), []); + const inputState = useSelector(getInputSelector); + + const { linkTo: globalLinkTo, timerange: globalTimerange } = inputState.global; + const { linkTo: timelineLinkTo, timerange: timelineTimerange } = inputState.timeline; + + useEffect(() => { + updateTimerangeUrlParam({ + global: { + [CONSTANTS.timerange]: globalTimerange, + linkTo: globalLinkTo, + }, + timeline: { + [CONSTANTS.timerange]: timelineTimerange, + linkTo: timelineLinkTo, + }, + }); + }, [updateTimerangeUrlParam, globalLinkTo, globalTimerange, timelineLinkTo, timelineTimerange]); +}; diff --git a/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_update_timerange_on_page_change.ts b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_update_timerange_on_page_change.ts new file mode 100644 index 0000000000000..79fdc5ddd2c12 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/hooks/search_bar/use_update_timerange_on_page_change.ts @@ -0,0 +1,75 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useEffect, useMemo } from 'react'; +import { useDispatch, useSelector } from 'react-redux'; +import usePrevious from 'react-use/lib/usePrevious'; +import type { SecurityPageName } from '../../../app/types'; +import { formatDate } from '../../components/super_date_picker'; +import { isDetectionsPages } from '../../components/url_state/helpers'; +import { inputsSelectors } from '../../store'; +import { inputsActions } from '../../store/inputs'; +import type { InputsModelId } from '../../store/inputs/constants'; +import { useRouteSpy } from '../../utils/route/use_route_spy'; + +const globalId: InputsModelId = 'global'; +const timelineId: InputsModelId = 'timeline'; + +/** + * Update relative time ranges when navigating between pages. + * + * Ex: When 'toStr' is 'now' and we navigate to a new page, it updates `to` with the present date-time. + * + * * It does not update the time range on the landing page. + * * It only updates the time range when navigating to detection pages for performance reasons. + */ +export const useUpdateTimerangeOnPageChange = () => { + const [{ pageName }] = useRouteSpy(); + const dispatch = useDispatch(); + const previousPage = usePrevious(pageName); + const getInputSelector = useMemo(() => inputsSelectors.inputsSelector(), []); + const inputState = useSelector(getInputSelector); + + const { timerange: globalTimerange } = inputState.global; + const { timerange: timelineTimerange } = inputState.timeline; + + useEffect(() => { + if (isNavigatingToDetections(pageName, previousPage)) { + if (timelineTimerange.kind === 'relative') { + dispatch( + inputsActions.setRelativeRangeDatePicker({ + ...timelineTimerange, + from: formatDate(timelineTimerange.fromStr), + to: formatDate(timelineTimerange.toStr, { + roundUp: true, + }), + id: timelineId, + }) + ); + } + + if (globalTimerange.kind === 'relative') { + dispatch( + inputsActions.setRelativeRangeDatePicker({ + ...globalTimerange, + from: formatDate(globalTimerange.fromStr), + to: formatDate(globalTimerange.toStr, { + roundUp: true, + }), + + id: globalId, + }) + ); + } + } + }, [pageName, previousPage, dispatch, timelineTimerange, globalTimerange]); +}; + +const isNavigatingToDetections = ( + pageName: SecurityPageName | undefined, + previousPage: SecurityPageName | undefined +) => pageName && previousPage && previousPage !== pageName && isDetectionsPages(pageName); diff --git a/x-pack/plugins/security_solution/public/common/hooks/use_url_state.ts b/x-pack/plugins/security_solution/public/common/hooks/use_url_state.ts new file mode 100644 index 0000000000000..f9e964fff54ed --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/hooks/use_url_state.ts @@ -0,0 +1,18 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useSyncGlobalQueryString } from '../utils/global_query_string'; +import { useInitSearchBarFromUrlParams } from './search_bar/use_init_search_bar_url_params'; +import { useInitTimerangeFromUrlParam } from './search_bar/use_init_timerange_url_params'; +import { useUpdateTimerangeOnPageChange } from './search_bar/use_update_timerange_on_page_change'; + +export const useUrlState = () => { + useSyncGlobalQueryString(); + useInitSearchBarFromUrlParams(); + useInitTimerangeFromUrlParam(); + useUpdateTimerangeOnPageChange(); +}; diff --git a/x-pack/plugins/security_solution/public/timelines/components/field_renderers/__snapshots__/field_renderers.test.tsx.snap b/x-pack/plugins/security_solution/public/timelines/components/field_renderers/__snapshots__/field_renderers.test.tsx.snap index 1d8d5322c235b..063ebe2952cc0 100644 --- a/x-pack/plugins/security_solution/public/timelines/components/field_renderers/__snapshots__/field_renderers.test.tsx.snap +++ b/x-pack/plugins/security_solution/public/timelines/components/field_renderers/__snapshots__/field_renderers.test.tsx.snap @@ -146,7 +146,7 @@ exports[`Field Renderers #hostIdRenderer it renders correctly against snapshot 1 raspberrypi @@ -201,7 +201,7 @@ exports[`Field Renderers #hostNameRenderer it renders correctly against snapshot raspberrypi From fce0739d2a5cd332ead6f14f71ed7581db82ace7 Mon Sep 17 00:00:00 2001 From: Tre Date: Thu, 14 Jul 2022 10:36:35 +0100 Subject: [PATCH 014/111] [Archive Migrations] Migrate discover for visual regression (#136222) * [Archive Migrations] Migrate discover for visual regression Add archive. Make the test use the new archive. * Drop archive. * Archive was in the wrong place. * Cr fixup. --- .../fixtures/es_archiver/discover/data.json | 64 --- .../es_archiver/discover/mappings.json | 445 ------------------ .../discover/visual_regression.json | 51 ++ .../tests/discover/chart_visualization.ts | 10 +- 4 files changed, 58 insertions(+), 512 deletions(-) delete mode 100644 test/functional/fixtures/es_archiver/discover/data.json delete mode 100644 test/functional/fixtures/es_archiver/discover/mappings.json create mode 100644 test/functional/fixtures/kbn_archiver/discover/visual_regression.json diff --git a/test/functional/fixtures/es_archiver/discover/data.json b/test/functional/fixtures/es_archiver/discover/data.json deleted file mode 100644 index 14a9f0559c6f3..0000000000000 --- a/test/functional/fixtures/es_archiver/discover/data.json +++ /dev/null @@ -1,64 +0,0 @@ -{ - "type": "doc", - "value": { - "id": "index-pattern:logstash-*", - "index": ".kibana", - "source": { - "coreMigrationVersion": "7.14.0", - "index-pattern": { - "fieldAttrs": "{\"referer\":{\"customLabel\":\"Referer custom\"}}", - "fields": "[{\"name\":\"@message\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@message.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@message\"}}},{\"name\":\"@tags\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@tags.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@tags\"}}},{\"name\":\"@timestamp\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"_id\",\"type\":\"string\",\"esTypes\":[\"_id\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_index\",\"type\":\"string\",\"esTypes\":[\"_index\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_score\",\"type\":\"number\",\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_source\",\"type\":\"_source\",\"esTypes\":[\"_source\"],\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_type\",\"type\":\"string\",\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"agent\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"agent.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"agent\"}}},{\"name\":\"bytes\",\"type\":\"number\",\"esTypes\":[\"long\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"clientip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"extension\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"extension.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"extension\"}}},{\"name\":\"geo.coordinates\",\"type\":\"geo_point\",\"esTypes\":[\"geo_point\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.dest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.src\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.srcdest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"headings\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"headings.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"headings\"}}},{\"name\":\"host\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"host.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"host\"}}},{\"name\":\"id\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"index\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"index.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"index\"}}},{\"name\":\"ip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"links\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"links.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"links\"}}},{\"name\":\"machine.os\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"machine.os.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"machine.os\"}}},{\"name\":\"machine.ram\",\"type\":\"number\",\"esTypes\":[\"long\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"memory\",\"type\":\"number\",\"esTypes\":[\"double\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.char\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.related\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.firstname\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.lastname\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"nestedField.child\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"nested\":{\"path\":\"nestedField\"}}},{\"name\":\"phpmemory\",\"type\":\"number\",\"esTypes\":[\"long\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"referer\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:modified_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:published_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:section\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:section.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:section\"}}},{\"name\":\"relatedContent.article:tag\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:tag.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:tag\"}}},{\"name\":\"relatedContent.og:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:description\"}}},{\"name\":\"relatedContent.og:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image\"}}},{\"name\":\"relatedContent.og:image:height\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:height.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:height\"}}},{\"name\":\"relatedContent.og:image:width\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:width.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:width\"}}},{\"name\":\"relatedContent.og:site_name\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:site_name.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:site_name\"}}},{\"name\":\"relatedContent.og:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:title\"}}},{\"name\":\"relatedContent.og:type\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:type.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:type\"}}},{\"name\":\"relatedContent.og:url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:url\"}}},{\"name\":\"relatedContent.twitter:card\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:card.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:card\"}}},{\"name\":\"relatedContent.twitter:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:description\"}}},{\"name\":\"relatedContent.twitter:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:image\"}}},{\"name\":\"relatedContent.twitter:site\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:site.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:site\"}}},{\"name\":\"relatedContent.twitter:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:title\"}}},{\"name\":\"relatedContent.url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.url\"}}},{\"name\":\"request\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"request.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"request\"}}},{\"name\":\"response\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"response.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"response\"}}},{\"name\":\"spaces\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"spaces.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"spaces\"}}},{\"name\":\"type\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"url\"}}},{\"name\":\"utc_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"xss\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"xss.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"xss\"}}}]", - "timeFieldName": "@timestamp", - "title": "logstash-*" - }, - "migrationVersion": { - "index-pattern": "7.11.0" - }, - "references": [ - ], - "type": "index-pattern" - }, - "type": "_doc" - } -} - -{ - "type": "doc", - "value": { - "id": "search:ab12e3c0-f231-11e6-9486-733b1ac9221a", - "index": ".kibana", - "source": { - "coreMigrationVersion": "7.14.0", - "migrationVersion": { - "search": "7.9.3" - }, - "references": [ - { - "id": "logstash-*", - "name": "kibanaSavedObjectMeta.searchSourceJSON.index", - "type": "index-pattern" - } - ], - "search": { - "columns": [ - "_source" - ], - "description": "A Saved Search Description", - "hits": 0, - "kibanaSavedObjectMeta": { - "searchSourceJSON": "{\"highlightAll\":true,\"filter\":[],\"query\":{\"query_string\":{\"query\":\"*\",\"analyze_wildcard\":true}},\"indexRefName\":\"kibanaSavedObjectMeta.searchSourceJSON.index\"}" - }, - "sort": [ - [ - "@timestamp", - "desc" - ] - ], - "title": "A Saved Search", - "version": 1 - }, - "type": "search" - }, - "type": "_doc" - } -} \ No newline at end of file diff --git a/test/functional/fixtures/es_archiver/discover/mappings.json b/test/functional/fixtures/es_archiver/discover/mappings.json deleted file mode 100644 index 33bc746c84c8c..0000000000000 --- a/test/functional/fixtures/es_archiver/discover/mappings.json +++ /dev/null @@ -1,445 +0,0 @@ -{ - "type": "index", - "value": { - "aliases": { - ".kibana_$KIBANA_PACKAGE_VERSION": {}, - ".kibana": {} - }, - "index": ".kibana_$KIBANA_PACKAGE_VERSION_001", - "mappings": { - "_meta": { - "migrationMappingPropertyHashes": { - "application_usage_daily": "43b8830d5d0df85a6823d290885fc9fd", - "application_usage_totals": "3d1b76c39bfb2cc8296b024d73854724", - "application_usage_transactional": "3d1b76c39bfb2cc8296b024d73854724", - "config": "c63748b75f39d0c54de12d12c1ccbc20", - "core-usage-stats": "3d1b76c39bfb2cc8296b024d73854724", - "coreMigrationVersion": "2f4316de49999235636386fe51dc06c1", - "dashboard": "40554caf09725935e2c02e02563a2d07", - "index-pattern": "45915a1ad866812242df474eb0479052", - "kql-telemetry": "d12a98a6f19a2d273696597547e064ee", - "legacy-url-alias": "6155300fd11a00e23d5cbaa39f0fce0a", - "migrationVersion": "4a1746014a75ade3a714e1db5763276f", - "namespace": "2f4316de49999235636386fe51dc06c1", - "namespaces": "2f4316de49999235636386fe51dc06c1", - "originId": "2f4316de49999235636386fe51dc06c1", - "query": "11aaeb7f5f7fa5bb43f25e18ce26e7d9", - "references": "7997cf5a56cc02bdc9c93361bde732b0", - "sample-data-telemetry": "7d3cfeb915303c9641c59681967ffeb4", - "search": "db2c00e39b36f40930a3b9fc71c823e1", - "search-telemetry": "3d1b76c39bfb2cc8296b024d73854724", - "telemetry": "36a616f7026dfa617d6655df850fe16d", - "type": "2f4316de49999235636386fe51dc06c1", - "ui-counter": "0d409297dc5ebe1e3a1da691c6ee32e3", - "ui-metric": "0d409297dc5ebe1e3a1da691c6ee32e3", - "updated_at": "00da57df13e94e9d98437d13ace4bfe0", - "url": "c7f66a0df8b1b52f17c28c4adb111105", - "usage-counters": "8cc260bdceffec4ffc3ad165c97dc1b4", - "visualization": "f819cf6636b75c9e76ba733a0c6ef355" - } - }, - "dynamic": "strict", - "properties": { - "application_usage_daily": { - "dynamic": "false", - "properties": { - "timestamp": { - "type": "date" - } - } - }, - "application_usage_totals": { - "dynamic": "false", - "type": "object" - }, - "application_usage_transactional": { - "dynamic": "false", - "type": "object" - }, - "config": { - "dynamic": "false", - "properties": { - "buildNum": { - "type": "keyword" - } - } - }, - "core-usage-stats": { - "dynamic": "false", - "type": "object" - }, - "coreMigrationVersion": { - "type": "keyword" - }, - "dashboard": { - "properties": { - "description": { - "type": "text" - }, - "hits": { - "doc_values": false, - "index": false, - "type": "integer" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "index": false, - "type": "text" - } - } - }, - "optionsJSON": { - "index": false, - "type": "text" - }, - "panelsJSON": { - "index": false, - "type": "text" - }, - "refreshInterval": { - "properties": { - "display": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "pause": { - "doc_values": false, - "index": false, - "type": "boolean" - }, - "section": { - "doc_values": false, - "index": false, - "type": "integer" - }, - "value": { - "doc_values": false, - "index": false, - "type": "integer" - } - } - }, - "timeFrom": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "timeRestore": { - "doc_values": false, - "index": false, - "type": "boolean" - }, - "timeTo": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "title": { - "type": "text" - }, - "version": { - "type": "integer" - } - } - }, - "index-pattern": { - "dynamic": "false", - "properties": { - "title": { - "type": "text" - }, - "type": { - "type": "keyword" - } - } - }, - "kql-telemetry": { - "properties": { - "optInCount": { - "type": "long" - }, - "optOutCount": { - "type": "long" - } - } - }, - "legacy-url-alias": { - "dynamic": "false", - "properties": { - "disabled": { - "type": "boolean" - }, - "sourceId": { - "type": "keyword" - }, - "targetType": { - "type": "keyword" - } - } - }, - "migrationVersion": { - "dynamic": "true", - "properties": { - "index-pattern": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "search": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "namespace": { - "type": "keyword" - }, - "namespaces": { - "type": "keyword" - }, - "originId": { - "type": "keyword" - }, - "query": { - "properties": { - "description": { - "type": "text" - }, - "filters": { - "enabled": false, - "type": "object" - }, - "query": { - "properties": { - "language": { - "type": "keyword" - }, - "query": { - "index": false, - "type": "keyword" - } - } - }, - "timefilter": { - "enabled": false, - "type": "object" - }, - "title": { - "type": "text" - } - } - }, - "references": { - "properties": { - "id": { - "type": "keyword" - }, - "name": { - "type": "keyword" - }, - "type": { - "type": "keyword" - } - }, - "type": "nested" - }, - "sample-data-telemetry": { - "properties": { - "installCount": { - "type": "long" - }, - "unInstallCount": { - "type": "long" - } - } - }, - "search": { - "properties": { - "columns": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "description": { - "type": "text" - }, - "grid": { - "enabled": false, - "type": "object" - }, - "hideChart": { - "doc_values": false, - "index": false, - "type": "boolean" - }, - "hits": { - "doc_values": false, - "index": false, - "type": "integer" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "index": false, - "type": "text" - } - } - }, - "sort": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "title": { - "type": "text" - }, - "version": { - "type": "integer" - } - } - }, - "search-telemetry": { - "dynamic": "false", - "type": "object" - }, - "server": { - "dynamic": "false", - "type": "object" - }, - "telemetry": { - "properties": { - "allowChangingOptInStatus": { - "type": "boolean" - }, - "enabled": { - "type": "boolean" - }, - "lastReported": { - "type": "date" - }, - "lastVersionChecked": { - "type": "keyword" - }, - "reportFailureCount": { - "type": "integer" - }, - "reportFailureVersion": { - "type": "keyword" - }, - "sendUsageFrom": { - "type": "keyword" - }, - "userHasSeenNotice": { - "type": "boolean" - } - } - }, - "type": { - "type": "keyword" - }, - "ui-counter": { - "properties": { - "count": { - "type": "integer" - } - } - }, - "ui-metric": { - "properties": { - "count": { - "type": "integer" - } - } - }, - "updated_at": { - "type": "date" - }, - "url": { - "properties": { - "accessCount": { - "type": "long" - }, - "accessDate": { - "type": "date" - }, - "createDate": { - "type": "date" - }, - "url": { - "fields": { - "keyword": { - "ignore_above": 2048, - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "usage-counters": { - "dynamic": "false", - "properties": { - "domainId": { - "type": "keyword" - } - } - }, - "visualization": { - "properties": { - "description": { - "type": "text" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "index": false, - "type": "text" - } - } - }, - "savedSearchRefName": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "title": { - "type": "text" - }, - "uiStateJSON": { - "index": false, - "type": "text" - }, - "version": { - "type": "integer" - }, - "visState": { - "index": false, - "type": "text" - } - } - } - } - }, - "settings": { - "index": { - "auto_expand_replicas": "0-1", - "number_of_replicas": "0", - "number_of_shards": "1", - "priority": "10", - "refresh_interval": "1s", - "routing_partition_size": "1" - } - } - } -} \ No newline at end of file diff --git a/test/functional/fixtures/kbn_archiver/discover/visual_regression.json b/test/functional/fixtures/kbn_archiver/discover/visual_regression.json new file mode 100644 index 0000000000000..c3782679b4809 --- /dev/null +++ b/test/functional/fixtures/kbn_archiver/discover/visual_regression.json @@ -0,0 +1,51 @@ +{ + "attributes": { + "fieldAttrs": "{\"referer\":{\"customLabel\":\"Referer custom\"}}", + "fields": "[{\"name\":\"@message\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@message.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@message\"}}},{\"name\":\"@tags\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@tags.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"@tags\"}}},{\"name\":\"@timestamp\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"_id\",\"type\":\"string\",\"esTypes\":[\"_id\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_index\",\"type\":\"string\",\"esTypes\":[\"_index\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_score\",\"type\":\"number\",\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_source\",\"type\":\"_source\",\"esTypes\":[\"_source\"],\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_type\",\"type\":\"string\",\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"agent\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"agent.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"agent\"}}},{\"name\":\"bytes\",\"type\":\"number\",\"esTypes\":[\"long\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"clientip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"extension\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"extension.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"extension\"}}},{\"name\":\"geo.coordinates\",\"type\":\"geo_point\",\"esTypes\":[\"geo_point\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.dest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.src\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.srcdest\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"headings\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"headings.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"headings\"}}},{\"name\":\"host\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"host.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"host\"}}},{\"name\":\"id\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"index\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"index.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"index\"}}},{\"name\":\"ip\",\"type\":\"ip\",\"esTypes\":[\"ip\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"links\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"links.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"links\"}}},{\"name\":\"machine.os\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"machine.os.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"machine.os\"}}},{\"name\":\"machine.ram\",\"type\":\"number\",\"esTypes\":[\"long\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"memory\",\"type\":\"number\",\"esTypes\":[\"double\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.char\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.related\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.firstname\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.lastname\",\"type\":\"number\",\"esTypes\":[\"integer\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"nestedField.child\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"nested\":{\"path\":\"nestedField\"}}},{\"name\":\"phpmemory\",\"type\":\"number\",\"esTypes\":[\"long\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"referer\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:modified_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:published_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:section\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:section.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:section\"}}},{\"name\":\"relatedContent.article:tag\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:tag.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.article:tag\"}}},{\"name\":\"relatedContent.og:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:description\"}}},{\"name\":\"relatedContent.og:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image\"}}},{\"name\":\"relatedContent.og:image:height\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:height.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:height\"}}},{\"name\":\"relatedContent.og:image:width\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:width.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:image:width\"}}},{\"name\":\"relatedContent.og:site_name\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:site_name.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:site_name\"}}},{\"name\":\"relatedContent.og:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:title\"}}},{\"name\":\"relatedContent.og:type\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:type.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:type\"}}},{\"name\":\"relatedContent.og:url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.og:url\"}}},{\"name\":\"relatedContent.twitter:card\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:card.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:card\"}}},{\"name\":\"relatedContent.twitter:description\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:description.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:description\"}}},{\"name\":\"relatedContent.twitter:image\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:image.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:image\"}}},{\"name\":\"relatedContent.twitter:site\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:site.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:site\"}}},{\"name\":\"relatedContent.twitter:title\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:title.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.twitter:title\"}}},{\"name\":\"relatedContent.url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"relatedContent.url\"}}},{\"name\":\"request\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"request.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"request\"}}},{\"name\":\"response\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"response.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"response\"}}},{\"name\":\"spaces\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"spaces.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"spaces\"}}},{\"name\":\"type\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"url\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"url.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"url\"}}},{\"name\":\"utc_time\",\"type\":\"date\",\"esTypes\":[\"date\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"xss\",\"type\":\"string\",\"esTypes\":[\"text\"],\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"xss.raw\",\"type\":\"string\",\"esTypes\":[\"keyword\"],\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true,\"subType\":{\"multi\":{\"parent\":\"xss\"}}}]", + "timeFieldName": "@timestamp", + "title": "logstash-*" + }, + "coreMigrationVersion": "8.4.0", + "id": "logstash-*", + "migrationVersion": { + "index-pattern": "8.0.0" + }, + "references": [], + "type": "index-pattern", + "version": "WzQsMV0=" +} + +{ + "attributes": { + "columns": [ + "_source" + ], + "description": "A Saved Search Description", + "hits": 0, + "kibanaSavedObjectMeta": { + "searchSourceJSON": "{\"highlightAll\":true,\"filter\":[],\"query\":{\"query_string\":{\"query\":\"*\",\"analyze_wildcard\":true}},\"indexRefName\":\"kibanaSavedObjectMeta.searchSourceJSON.index\"}" + }, + "sort": [ + [ + "@timestamp", + "desc" + ] + ], + "title": "A Saved Search", + "version": 1 + }, + "coreMigrationVersion": "8.4.0", + "id": "ab12e3c0-f231-11e6-9486-733b1ac9221a", + "migrationVersion": { + "search": "8.0.0" + }, + "references": [ + { + "id": "logstash-*", + "name": "kibanaSavedObjectMeta.searchSourceJSON.index", + "type": "index-pattern" + } + ], + "type": "search", + "version": "WzUsMV0=" +} diff --git a/test/visual_regression/tests/discover/chart_visualization.ts b/test/visual_regression/tests/discover/chart_visualization.ts index 389a0a4b6a314..f8390064732b9 100644 --- a/test/visual_regression/tests/discover/chart_visualization.ts +++ b/test/visual_regression/tests/discover/chart_visualization.ts @@ -24,7 +24,10 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { describe('discover', function describeIndexTests() { before(async function () { - await esArchiver.load('test/functional/fixtures/es_archiver/discover'); + await kibanaServer.savedObjects.cleanStandardList(); + await kibanaServer.importExport.load( + 'test/functional/fixtures/kbn_archiver/discover/visual_regression' + ); // and load a set of makelogs data await esArchiver.loadIfNeeded('test/functional/fixtures/es_archiver/logstash_functional'); @@ -33,8 +36,9 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { await PageObjects.timePicker.setDefaultAbsoluteRange(); }); - after(function unloadMakelogs() { - return esArchiver.unload('test/functional/fixtures/es_archiver/logstash_functional'); + after(async function unloadMakelogs() { + await esArchiver.unload('test/functional/fixtures/es_archiver/logstash_functional'); + await kibanaServer.savedObjects.cleanStandardList(); }); async function refreshDiscover() { From ccaa38e7f1f90efa33c742220ff2faaa47c0c753 Mon Sep 17 00:00:00 2001 From: Muhammad Ibragimov <53621505+mibragimov@users.noreply.github.com> Date: Thu, 14 Jul 2022 14:50:28 +0500 Subject: [PATCH 015/111] [Console] Close autocomplete popup when navigating away from Console (#136268) * [Console] Close autocomplete popup when navigating away from Console * Fix type checks Co-authored-by: Muhammad Ibragimov --- .../containers/editor/legacy/console_editor/editor.tsx | 2 ++ .../models/legacy_core_editor/legacy_core_editor.ts | 4 ++++ src/plugins/console/public/types/core_editor.ts | 5 +++++ 3 files changed, 11 insertions(+) diff --git a/src/plugins/console/public/application/containers/editor/legacy/console_editor/editor.tsx b/src/plugins/console/public/application/containers/editor/legacy/console_editor/editor.tsx index e999c079b490f..76e91baa8e21e 100644 --- a/src/plugins/console/public/application/containers/editor/legacy/console_editor/editor.tsx +++ b/src/plugins/console/public/application/containers/editor/legacy/console_editor/editor.tsx @@ -233,6 +233,8 @@ function EditorUI({ initialTextValue, setEditorInstance }: EditorProps) { autocompleteInfo.clearSubscriptions(); window.removeEventListener('hashchange', onHashChange); if (editorInstanceRef.current) { + // Close autocomplete popup on unmount + editorInstanceRef.current?.getCoreEditor().detachCompleter(); editorInstanceRef.current.getCoreEditor().destroy(); } }; diff --git a/src/plugins/console/public/application/models/legacy_core_editor/legacy_core_editor.ts b/src/plugins/console/public/application/models/legacy_core_editor/legacy_core_editor.ts index 2208de4a9dff3..45d6eb42a9693 100644 --- a/src/plugins/console/public/application/models/legacy_core_editor/legacy_core_editor.ts +++ b/src/plugins/console/public/application/models/legacy_core_editor/legacy_core_editor.ts @@ -228,6 +228,10 @@ export class LegacyCoreEditor implements CoreEditor { ); } + detachCompleter() { + return (this.editor as unknown as { completer: { detach(): void } }).completer.detach(); + } + private forceRetokenize() { const session = this.editor.getSession(); return new Promise((resolve) => { diff --git a/src/plugins/console/public/types/core_editor.ts b/src/plugins/console/public/types/core_editor.ts index aa048256421bb..1c9d6352914a2 100644 --- a/src/plugins/console/public/types/core_editor.ts +++ b/src/plugins/console/public/types/core_editor.ts @@ -288,4 +288,9 @@ export interface CoreEditor { * Add folds at given ranges */ addFoldsAtRanges(foldRanges: Range[]): void; + + /** + * Detach autocomplete + */ + detachCompleter(): void; } From d35a687c2977aa30d5abd0b233ff2b7c6703cacd Mon Sep 17 00:00:00 2001 From: Sergi Massaneda Date: Thu, 14 Jul 2022 12:07:50 +0200 Subject: [PATCH 016/111] [Security] Dashboards table in landing page (#136221) * dashboard landing cards * useSecurityDashboards hook implementation * useSecurityDashboards hook implementation * add savedObjectsTagging to security * tests implemented * rename section titles * remove test code * [CI] Auto-commit changed files from 'node scripts/eslint --no-cache --fix' * PR suggestions Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- x-pack/plugins/security_solution/kibana.json | 3 +- .../dashboards/dashboards_table.tsx | 36 ++++ .../containers/dashboards/translations.ts | 19 ++ .../use_security_dashboards.test.tsx | 203 ++++++++++++++++++ .../dashboards/use_security_dashboards.tsx | 121 +++++++++++ .../common/lib/kibana/__mocks__/index.ts | 5 + .../components/landing_links_images.test.tsx | 29 ++- .../components/landing_links_images.tsx | 73 ++++++- .../landing_pages/pages/dashboards.test.tsx | 128 +++++++++++ .../public/landing_pages/pages/dashboards.tsx | 25 ++- .../landing_pages/pages/translations.ts | 14 ++ .../security_solution/public/plugin.tsx | 11 +- .../plugins/security_solution/public/types.ts | 9 + 13 files changed, 663 insertions(+), 13 deletions(-) create mode 100644 x-pack/plugins/security_solution/public/common/components/dashboards/dashboards_table.tsx create mode 100644 x-pack/plugins/security_solution/public/common/containers/dashboards/translations.ts create mode 100644 x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.test.tsx create mode 100644 x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.tsx create mode 100644 x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.test.tsx diff --git a/x-pack/plugins/security_solution/kibana.json b/x-pack/plugins/security_solution/kibana.json index 756856c55c2f7..21684957598aa 100644 --- a/x-pack/plugins/security_solution/kibana.json +++ b/x-pack/plugins/security_solution/kibana.json @@ -42,7 +42,8 @@ "home", "telemetry", "dataViewFieldEditor", - "osquery" + "osquery", + "savedObjectsTaggingOss" ], "server": true, "ui": true, diff --git a/x-pack/plugins/security_solution/public/common/components/dashboards/dashboards_table.tsx b/x-pack/plugins/security_solution/public/common/components/dashboards/dashboards_table.tsx new file mode 100644 index 0000000000000..c59828002717d --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/components/dashboards/dashboards_table.tsx @@ -0,0 +1,36 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import type { Search } from '@elastic/eui'; +import { EuiInMemoryTable } from '@elastic/eui'; +import { + useSecurityDashboardsTableItems, + useDashboardsTableColumns, +} from '../../containers/dashboards/use_security_dashboards'; + +const DASHBOARDS_TABLE_SEARCH: Search = { + box: { + incremental: true, + }, +} as const; + +export const DashboardsTable: React.FC = () => { + const items = useSecurityDashboardsTableItems(); + const columns = useDashboardsTableColumns(); + + return ( + + ); +}; diff --git a/x-pack/plugins/security_solution/public/common/containers/dashboards/translations.ts b/x-pack/plugins/security_solution/public/common/containers/dashboards/translations.ts new file mode 100644 index 0000000000000..58254aa8fe9f6 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/containers/dashboards/translations.ts @@ -0,0 +1,19 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { i18n } from '@kbn/i18n'; + +export const DASHBOARD_TITLE = i18n.translate('xpack.securitySolution.dashboards.title', { + defaultMessage: 'Title', +}); + +export const DASHBOARDS_DESCRIPTION = i18n.translate( + 'xpack.securitySolution.dashboards.description', + { + defaultMessage: 'Description', + } +); diff --git a/x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.test.tsx b/x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.test.tsx new file mode 100644 index 0000000000000..e626ee8863f18 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.test.tsx @@ -0,0 +1,203 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { renderHook, act } from '@testing-library/react-hooks'; +import { render } from '@testing-library/react'; +import type { DashboardStart } from '@kbn/dashboard-plugin/public'; +import { EuiBasicTable } from '@elastic/eui'; +import { useKibana } from '../../lib/kibana'; +import { TestProviders } from '../../mock/test_providers'; +import type { DashboardTableItem } from './use_security_dashboards'; +import { + useDashboardsTableColumns, + useSecurityDashboardsTableItems, +} from './use_security_dashboards'; + +jest.mock('../../lib/kibana'); + +const TAG_ID = 'securityTagId'; +const basicResponse: DashboardTableItem[] = [ + { + id: 'dashboardId1', + type: 'dashboard', + attributes: { + title: 'title1', + description: 'description1', + }, + references: [{ type: 'tag', id: TAG_ID, name: 'tagName' }], + }, + { + id: 'dashboardId2', + type: 'dashboard', + attributes: { + title: 'title2', + description: 'description2', + }, + references: [{ type: 'tag', id: TAG_ID, name: 'tagName' }], + }, +]; + +const renderUseSecurityDashboardsTableItems = async () => { + const renderedHook = renderHook(() => useSecurityDashboardsTableItems(), { + wrapper: TestProviders, + }); + await act(async () => { + // needed to let dashboard items to be updated from saved objects response + await renderedHook.waitForNextUpdate(); + }); + return renderedHook; +}; + +const renderUseDashboardsTableColumns = () => + renderHook(() => useDashboardsTableColumns(), { + wrapper: TestProviders, + }); + +describe('Security Dashboards hooks', () => { + const mockSavedObjectsFind = useKibana().services.savedObjects.client.find as jest.Mock; + mockSavedObjectsFind.mockImplementation(async (req) => { + if (req.type === 'tag') { + return { savedObjects: [{ id: TAG_ID }] }; + } else if (req.type === 'dashboard') { + return { savedObjects: basicResponse }; + } + return { savedObjects: [] }; + }); + + const mockGetRedirectUrl = jest.fn(() => '/path'); + useKibana().services.dashboard = { + locator: { getRedirectUrl: mockGetRedirectUrl }, + } as unknown as DashboardStart; + + const mockTaggingGetTableColumnDefinition = useKibana().services.savedObjectsTagging?.ui + .getTableColumnDefinition as jest.Mock; + const tagsColumn = { + field: 'id', // set existing field to prevent test error + name: 'Tags', + 'data-test-subj': 'dashboard-tags-field', + }; + mockTaggingGetTableColumnDefinition.mockReturnValue(tagsColumn); + + afterEach(() => { + mockTaggingGetTableColumnDefinition.mockClear(); + mockGetRedirectUrl.mockClear(); + mockSavedObjectsFind.mockClear(); + }); + + describe('useSecurityDashboardsTableItems', () => { + afterEach(() => { + mockSavedObjectsFind.mockClear(); + }); + + it('should request when renders', async () => { + await renderUseSecurityDashboardsTableItems(); + + expect(mockSavedObjectsFind).toHaveBeenCalledTimes(2); + expect(mockSavedObjectsFind).toHaveBeenCalledWith( + expect.objectContaining({ type: 'tag', search: 'security' }) + ); + expect(mockSavedObjectsFind).toHaveBeenCalledWith( + expect.objectContaining({ type: 'dashboard', hasReference: { id: TAG_ID, type: 'tag' } }) + ); + }); + + it('should not re-request when re-rendered', async () => { + const { rerender } = await renderUseSecurityDashboardsTableItems(); + + expect(mockSavedObjectsFind).toHaveBeenCalledTimes(2); + act(() => rerender()); + expect(mockSavedObjectsFind).toHaveBeenCalledTimes(2); + }); + + it('returns a memoized value', async () => { + const { result, rerender } = await renderUseSecurityDashboardsTableItems(); + + const result1 = result.current; + act(() => rerender()); + const result2 = result.current; + + expect(result1).toBe(result2); + }); + + it('should return dashboard items', async () => { + const { result } = await renderUseSecurityDashboardsTableItems(); + + const [dashboard1, dashboard2] = basicResponse; + expect(result.current).toStrictEqual([ + { + ...dashboard1, + title: dashboard1.attributes.title, + description: dashboard1.attributes.description, + }, + { + ...dashboard2, + title: dashboard2.attributes.title, + description: dashboard2.attributes.description, + }, + ]); + }); + }); + + describe('useDashboardsTableColumns', () => { + it('should call getTableColumnDefinition to get tags column', () => { + renderUseDashboardsTableColumns(); + expect(mockTaggingGetTableColumnDefinition).toHaveBeenCalled(); + }); + + it('should return dashboard columns', () => { + const { result } = renderUseDashboardsTableColumns(); + + expect(result.current).toEqual([ + expect.objectContaining({ + field: 'title', + name: 'Title', + }), + expect.objectContaining({ + field: 'description', + name: 'Description', + }), + expect.objectContaining(tagsColumn), + ]); + }); + + it('returns a memoized value', async () => { + const { result, rerender } = await renderUseSecurityDashboardsTableItems(); + + const result1 = result.current; + act(() => rerender()); + const result2 = result.current; + + expect(result1).toBe(result2); + }); + }); + + it('should render a table with consistent items and columns', async () => { + const { result: itemsResult } = await renderUseSecurityDashboardsTableItems(); + const { result: columnsResult } = renderUseDashboardsTableColumns(); + + const result = render( + , + { + wrapper: TestProviders, + } + ); + + expect(result.getAllByText('Title').length).toBeGreaterThan(0); + expect(result.getAllByText('Description').length).toBeGreaterThan(0); + expect(result.getAllByText('Tags').length).toBeGreaterThan(0); + + expect(result.getByText('title1')).toBeInTheDocument(); + expect(result.getByText('description1')).toBeInTheDocument(); + expect(result.getByText('title2')).toBeInTheDocument(); + expect(result.getByText('description2')).toBeInTheDocument(); + + expect(result.queryAllByTestId('dashboard-title-field')).toHaveLength(2); + expect(result.queryAllByTestId('dashboard-description-field')).toHaveLength(2); + expect(result.queryAllByTestId('dashboard-tags-field')).toHaveLength(2); + }); +}); diff --git a/x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.tsx b/x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.tsx new file mode 100644 index 0000000000000..19f05918d5278 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/containers/dashboards/use_security_dashboards.tsx @@ -0,0 +1,121 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { MouseEventHandler } from 'react'; +import React, { useState, useEffect, useMemo, useCallback } from 'react'; +import type { EuiBasicTableColumn } from '@elastic/eui'; +import type { SavedObjectAttributes } from '@kbn/securitysolution-io-ts-alerting-types'; +import type { SavedObjectsClientContract, SavedObject } from '@kbn/core/public'; +import { LinkAnchor } from '../../components/links'; +import { useKibana, useNavigateTo } from '../../lib/kibana'; +import * as i18n from './translations'; + +export interface DashboardTableItem extends SavedObject { + title?: string; + description?: string; +} + +const SECURITY_TAG_NAME = 'security' as const; +const EMPTY_DESCRIPTION = '-' as const; + +const getSecurityDashboardItems = async ( + savedObjectsClient: SavedObjectsClientContract +): Promise => { + if (savedObjectsClient) { + const tagResponse = await savedObjectsClient.find({ + type: 'tag', + searchFields: ['name'], + search: SECURITY_TAG_NAME, + }); + + const tagId = tagResponse.savedObjects[0]?.id; + + if (tagId) { + const dashboardsResponse = await savedObjectsClient.find({ + type: 'dashboard', + hasReference: { id: tagId, type: 'tag' }, + }); + + return dashboardsResponse.savedObjects.map((item) => ({ + ...item, + title: item.attributes.title?.toString() ?? undefined, + description: item.attributes.description?.toString() ?? undefined, + })); + } + } + return []; +}; + +export const useSecurityDashboardsTableItems = () => { + const [dashboardItems, setDashboardItems] = useState([]); + + const { + savedObjects: { client: savedObjectsClient }, + } = useKibana().services; + + useEffect(() => { + let ignore = false; + const fetchDashboards = async () => { + const items = await getSecurityDashboardItems(savedObjectsClient); + if (!ignore) { + setDashboardItems(items); + } + }; + + fetchDashboards(); + return () => { + ignore = true; + }; + }, [savedObjectsClient]); + + return dashboardItems; +}; + +export const useDashboardsTableColumns = (): Array> => { + const { savedObjectsTagging, dashboard: { locator } = {} } = useKibana().services; + const { navigateTo } = useNavigateTo(); + + const getNavigationHandler = useCallback( + (href: string): MouseEventHandler => + (ev) => { + ev.preventDefault(); + navigateTo({ url: href }); + }, + [navigateTo] + ); + + const columns = useMemo( + (): Array> => [ + { + field: 'title', + name: i18n.DASHBOARD_TITLE, + 'data-test-subj': 'dashboard-title-field', + render: (title: string, { id }) => { + const href = locator?.getRedirectUrl({ dashboardId: id }); + return href ? ( + + {title} + + ) : ( + title + ); + }, + }, + { + field: 'description', + name: i18n.DASHBOARDS_DESCRIPTION, + 'data-test-subj': 'dashboard-description-field', + render: (description: string) => description || EMPTY_DESCRIPTION, + }, + // adds the tags table column based on the saved object items + ...(savedObjectsTagging ? [savedObjectsTagging.ui.getTableColumnDefinition()] : []), + ], + [getNavigationHandler, locator, savedObjectsTagging] + ); + + return columns; +}; diff --git a/x-pack/plugins/security_solution/public/common/lib/kibana/__mocks__/index.ts b/x-pack/plugins/security_solution/public/common/lib/kibana/__mocks__/index.ts index 11fdb39b5315a..ae3e7bdcef3f7 100644 --- a/x-pack/plugins/security_solution/public/common/lib/kibana/__mocks__/index.ts +++ b/x-pack/plugins/security_solution/public/common/lib/kibana/__mocks__/index.ts @@ -53,6 +53,11 @@ export const useKibana = jest.fn().mockReturnValue({ }, }, timelines: createTGridMocks(), + savedObjectsTagging: { + ui: { + getTableColumnDefinition: jest.fn(), + }, + }, }, }); export const useUiSetting = jest.fn(createUseUiSettingMock()); diff --git a/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.test.tsx b/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.test.tsx index 377c7efe0e3fe..b14e62f222576 100644 --- a/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.test.tsx +++ b/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.test.tsx @@ -10,7 +10,7 @@ import React from 'react'; import { SecurityPageName } from '../../app/types'; import type { NavLinkItem } from '../../common/components/navigation/types'; import { TestProviders } from '../../common/mock'; -import { LandingLinksImages } from './landing_links_images'; +import { LandingLinksImages, LandingImageCards } from './landing_links_images'; const DEFAULT_NAV_ITEM: NavLinkItem = { id: SecurityPageName.overview, @@ -57,3 +57,30 @@ describe('LandingLinksImages', () => { expect(getByTestId('LandingLinksImage')).toHaveAttribute('src', image); }); }); + +describe('LandingImageCards', () => { + it('renders', () => { + const title = 'test label'; + + const { queryByText } = render( + + + + ); + + expect(queryByText(title)).toBeInTheDocument(); + }); + + it('renders image', () => { + const image = 'test_image.jpeg'; + const title = 'TEST_LABEL'; + + const { getByTestId } = render( + + + + ); + + expect(getByTestId('LandingImageCard-image')).toHaveAttribute('src', image); + }); +}); diff --git a/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.tsx b/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.tsx index 9a6787083f848..5f54d4c53693f 100644 --- a/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.tsx +++ b/x-pack/plugins/security_solution/public/landing_pages/components/landing_links_images.tsx @@ -4,13 +4,21 @@ * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ -import { EuiFlexGroup, EuiFlexItem, EuiImage, EuiPanel, EuiText, EuiTitle } from '@elastic/eui'; +import { + EuiCard, + EuiFlexGroup, + EuiFlexItem, + EuiImage, + EuiPanel, + EuiText, + EuiTitle, +} from '@elastic/eui'; import React from 'react'; import styled from 'styled-components'; import { withSecuritySolutionLink } from '../../common/components/links'; import type { NavLinkItem } from '../../common/components/navigation/types'; -interface LandingLinksImagesProps { +interface LandingImagesProps { items: NavLinkItem[]; } @@ -31,13 +39,13 @@ const StyledFlexItem = styled(EuiFlexItem)` align-items: center; `; -const SecuritySolutionLink = withSecuritySolutionLink(Link); - const Content = styled(EuiFlexItem)` padding-left: ${({ theme }) => theme.eui.euiSizeS}; `; -export const LandingLinksImages: React.FC = ({ items }) => ( +const SecuritySolutionLink = withSecuritySolutionLink(Link); + +export const LandingLinksImages: React.FC = ({ items }) => ( {items.map(({ title, description, image, id }) => ( @@ -71,3 +79,58 @@ export const LandingLinksImages: React.FC = ({ items }) ))} ); + +const LandingImageCardItem = styled(EuiFlexItem)` + max-width: 364px; +`; + +const LandingCardDescripton = styled(EuiText)` + padding-top: ${({ theme }) => theme.eui.euiSizeXS}; +`; + +// Needed to use the primary color in the title underlining on hover +const PrimaryTitleCard = styled(EuiCard)` + .euiCard__title { + color: ${(props) => props.theme.eui.euiColorPrimary}; + } +`; + +const SecuritySolutionCard = withSecuritySolutionLink(PrimaryTitleCard); + +export const LandingImageCards: React.FC = React.memo(({ items }) => ( + + {items.map(({ id, image, title, description }) => ( + + + ) + } + title={ + +

{title}

+
+ } + description={ + + {description} + + } + /> +
+ ))} +
+)); + +LandingImageCards.displayName = 'LandingImageCards'; diff --git a/x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.test.tsx b/x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.test.tsx new file mode 100644 index 0000000000000..81f2c59e9bd85 --- /dev/null +++ b/x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.test.tsx @@ -0,0 +1,128 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { fireEvent, render } from '@testing-library/react'; +import React from 'react'; +import { SecurityPageName } from '../../app/types'; +import { TestProviders } from '../../common/mock'; +import { DashboardsLandingPage } from './dashboards'; +import type { NavLinkItem } from '../../common/components/navigation/types'; + +jest.mock('../../common/utils/route/spy_routes', () => ({ SpyRoute: () => null })); + +const OVERVIEW_ITEM_LABEL = 'Overview'; +const DETECTION_RESPONSE_ITEM_LABEL = 'Detection & Response'; + +const defaultAppDashboardsLink: NavLinkItem = { + id: SecurityPageName.dashboardsLanding, + title: 'Dashboards', + links: [ + { + id: SecurityPageName.overview, + title: OVERVIEW_ITEM_LABEL, + description: '', + icon: 'testIcon1', + }, + { + id: SecurityPageName.detectionAndResponse, + title: DETECTION_RESPONSE_ITEM_LABEL, + description: '', + icon: 'testIcon2', + }, + ], +}; + +const mockAppManageLink = jest.fn(() => defaultAppDashboardsLink); +jest.mock('../../common/components/navigation/nav_links', () => ({ + useAppRootNavLink: () => mockAppManageLink(), +})); + +const dashboardTableItems = [ + { + id: 'id 1', + title: 'dashboard title 1', + description: 'dashboard desc 1', + }, + { + id: 'id 2', + title: 'dashboard title 2', + description: 'dashboard desc 2', + }, +]; +const mockUseSecurityDashboardsTableItems = jest.fn(() => dashboardTableItems); +jest.mock('../../common/containers/dashboards/use_security_dashboards', () => { + const actual = jest.requireActual('../../common/containers/dashboards/use_security_dashboards'); + return { + ...actual, + useSecurityDashboardsTableItems: () => mockUseSecurityDashboardsTableItems(), + }; +}); + +const renderDashboardLanding = () => render(, { wrapper: TestProviders }); + +describe('Dashboards landing', () => { + it('should render items', () => { + const { queryByText } = renderDashboardLanding(); + + expect(queryByText(OVERVIEW_ITEM_LABEL)).toBeInTheDocument(); + expect(queryByText(DETECTION_RESPONSE_ITEM_LABEL)).toBeInTheDocument(); + }); + + it('should render items in the same order as defined', () => { + mockAppManageLink.mockReturnValueOnce({ + ...defaultAppDashboardsLink, + }); + const { queryAllByTestId } = renderDashboardLanding(); + + const renderedItems = queryAllByTestId('LandingImageCard-item'); + + expect(renderedItems[0]).toHaveTextContent(OVERVIEW_ITEM_LABEL); + expect(renderedItems[1]).toHaveTextContent(DETECTION_RESPONSE_ITEM_LABEL); + }); + + it('should not render items if all items filtered', () => { + mockAppManageLink.mockReturnValueOnce({ + ...defaultAppDashboardsLink, + links: [], + }); + const { queryByText } = renderDashboardLanding(); + + expect(queryByText(OVERVIEW_ITEM_LABEL)).not.toBeInTheDocument(); + expect(queryByText(DETECTION_RESPONSE_ITEM_LABEL)).not.toBeInTheDocument(); + }); + + it('should render dashboards table', () => { + const result = renderDashboardLanding(); + + expect(result.getByTestId('dashboards-table')).toBeInTheDocument(); + }); + + it('should render dashboards table rows', () => { + const result = renderDashboardLanding(); + + expect(mockUseSecurityDashboardsTableItems).toHaveBeenCalled(); + + expect(result.queryAllByText(dashboardTableItems[0].title).length).toBeGreaterThan(0); + expect(result.queryAllByText(dashboardTableItems[0].description).length).toBeGreaterThan(0); + + expect(result.queryAllByText(dashboardTableItems[1].title).length).toBeGreaterThan(0); + expect(result.queryAllByText(dashboardTableItems[1].description).length).toBeGreaterThan(0); + }); + + it('should render dashboards table rows filtered by search term', () => { + const result = renderDashboardLanding(); + + const input = result.getByRole('searchbox'); + fireEvent.change(input, { target: { value: dashboardTableItems[0].title } }); + + expect(result.queryAllByText(dashboardTableItems[0].title).length).toBeGreaterThan(0); + expect(result.queryAllByText(dashboardTableItems[0].description).length).toBeGreaterThan(0); + + expect(result.queryByText(dashboardTableItems[1].title)).not.toBeInTheDocument(); + expect(result.queryByText(dashboardTableItems[1].description)).not.toBeInTheDocument(); + }); +}); diff --git a/x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.tsx b/x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.tsx index 1d46aa6706a26..15afdedb4dd93 100644 --- a/x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.tsx +++ b/x-pack/plugins/security_solution/public/landing_pages/pages/dashboards.tsx @@ -4,22 +4,39 @@ * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ +import { EuiHorizontalRule, EuiSpacer, EuiTitle } from '@elastic/eui'; import React from 'react'; import { SecurityPageName } from '../../app/types'; +import { DashboardsTable } from '../../common/components/dashboards/dashboards_table'; import { HeaderPage } from '../../common/components/header_page'; import { useAppRootNavLink } from '../../common/components/navigation/nav_links'; import { SecuritySolutionPageWrapper } from '../../common/components/page_wrapper'; import { SpyRoute } from '../../common/utils/route/spy_routes'; -import { LandingLinksImages } from '../components/landing_links_images'; -import { DASHBOARDS_PAGE_TITLE } from './translations'; +import { LandingImageCards } from '../components/landing_links_images'; +import * as i18n from './translations'; export const DashboardsLandingPage = () => { const dashboardLinks = useAppRootNavLink(SecurityPageName.dashboardsLanding)?.links ?? []; return ( - - + + + + +

{i18n.DASHBOARDS_PAGE_SECTION_DEFAULT}

+
+ + + + + +

{i18n.DASHBOARDS_PAGE_SECTION_CUSTOM}

+
+ + + +
); diff --git a/x-pack/plugins/security_solution/public/landing_pages/pages/translations.ts b/x-pack/plugins/security_solution/public/landing_pages/pages/translations.ts index 4986c6b5f31ec..9b8b8f71ce509 100644 --- a/x-pack/plugins/security_solution/public/landing_pages/pages/translations.ts +++ b/x-pack/plugins/security_solution/public/landing_pages/pages/translations.ts @@ -21,6 +21,20 @@ export const DASHBOARDS_PAGE_TITLE = i18n.translate( } ); +export const DASHBOARDS_PAGE_SECTION_DEFAULT = i18n.translate( + 'xpack.securitySolution.landing.dashboards.section.default', + { + defaultMessage: 'DEFAULT', + } +); + +export const DASHBOARDS_PAGE_SECTION_CUSTOM = i18n.translate( + 'xpack.securitySolution.landing.dashboards.section.custom', + { + defaultMessage: 'CUSTOM', + } +); + export const MANAGE_PAGE_TITLE = i18n.translate('xpack.securitySolution.landing.manage.pageTitle', { defaultMessage: 'Manage', }); diff --git a/x-pack/plugins/security_solution/public/plugin.tsx b/x-pack/plugins/security_solution/public/plugin.tsx index 986667363f7b6..39892dcd9b3ea 100644 --- a/x-pack/plugins/security_solution/public/plugin.tsx +++ b/x-pack/plugins/security_solution/public/plugin.tsx @@ -31,6 +31,7 @@ import type { AppObservableLibs, SubPlugins, StartedSubPlugins, + StartPluginsDependencies, } from './types'; import { initTelemetry } from './common/lib/telemetry'; import { KibanaServices } from './common/lib/kibana/services'; @@ -94,7 +95,10 @@ export class Plugin implements IPlugin, plugins: SetupPlugins): PluginSetup { + public setup( + core: CoreSetup, + plugins: SetupPlugins + ): PluginSetup { initTelemetry( { usageCollection: plugins.usageCollection, @@ -122,13 +126,16 @@ export class Plugin implements IPlugin = (async () => { - const [coreStart, startPlugins] = await core.getStartServices(); + const [coreStart, startPluginsDeps] = await core.getStartServices(); const { apm } = await import('@elastic/apm-rum'); + const { savedObjectsTaggingOss, ...startPlugins } = startPluginsDeps; + const services: StartServices = { ...coreStart, ...startPlugins, apm, + savedObjectsTagging: savedObjectsTaggingOss.getTaggingApi(), storage: this.storage, security: plugins.security, }; diff --git a/x-pack/plugins/security_solution/public/types.ts b/x-pack/plugins/security_solution/public/types.ts index 1a32eefa983e9..d1b6875635372 100644 --- a/x-pack/plugins/security_solution/public/types.ts +++ b/x-pack/plugins/security_solution/public/types.ts @@ -34,6 +34,10 @@ import type { DashboardStart } from '@kbn/dashboard-plugin/public'; import type { IndexPatternFieldEditorStart } from '@kbn/data-view-field-editor-plugin/public'; import type { UnifiedSearchPublicPluginStart } from '@kbn/unified-search-plugin/public'; import type { ApmBase } from '@elastic/apm-rum'; +import type { + SavedObjectsTaggingApi, + SavedObjectTaggingOssPluginStart, +} from '@kbn/saved-objects-tagging-oss-plugin/public'; import type { ResolverPluginSetup } from './resolver/types'; import type { Inspect } from '../common/search_strategy'; import type { Detections } from './detections'; @@ -83,10 +87,15 @@ export interface StartPlugins { security: SecurityPluginSetup; } +export interface StartPluginsDependencies extends StartPlugins { + savedObjectsTaggingOss: SavedObjectTaggingOssPluginStart; +} + export type StartServices = CoreStart & StartPlugins & { storage: Storage; apm: ApmBase; + savedObjectsTagging?: SavedObjectsTaggingApi; }; export interface PluginSetup { From ac434b3433c82d2e267746c8598972d2f1fdcbca Mon Sep 17 00:00:00 2001 From: Pete Harverson Date: Thu, 14 Jul 2022 11:33:58 +0100 Subject: [PATCH 017/111] [ML] Add action to view datafeed counts chart to jobs list rows (#136274) * [ML] Add action to view datafeed counts chart to jobs list rows * [ML] Update functional tests for permissions and job actions * [ML] Edit to test in job_table service message * [ML] Update translations * [ML] type change in datafeed_chart_flyout --- .../annotations_table/annotations_table.js | 30 ++++++- .../datafeed_chart_flyout.tsx | 86 +++++++++++++++++++ .../components/datafeed_chart_flyout/index.ts | 2 +- .../components/job_actions/management.js | 21 +++++ .../components/job_details/job_details.js | 33 +++---- .../job_details/job_details_pane.js | 2 +- .../components/jobs_list/jobs_list.js | 2 + .../jobs_list_view/jobs_list_view.js | 16 +++- .../translations/translations/fr-FR.json | 2 - .../translations/translations/ja-JP.json | 2 - .../translations/translations/zh-CN.json | 2 - .../apps/ml/permissions/full_ml_access.ts | 2 + .../apps/ml/permissions/read_ml_access.ts | 16 +++- .../test/functional/services/ml/job_table.ts | 25 ++++++ 14 files changed, 209 insertions(+), 32 deletions(-) diff --git a/x-pack/plugins/ml/public/application/components/annotations/annotations_table/annotations_table.js b/x-pack/plugins/ml/public/application/components/annotations/annotations_table/annotations_table.js index bbf5dc81768a1..a0a364e3af0f8 100644 --- a/x-pack/plugins/ml/public/application/components/annotations/annotations_table/annotations_table.js +++ b/x-pack/plugins/ml/public/application/components/annotations/annotations_table/annotations_table.js @@ -51,6 +51,7 @@ import { ML_APP_LOCATOR, ML_PAGES } from '../../../../../common/constants/locato import { timeFormatter } from '../../../../../common/util/date_utils'; import { MlAnnotationUpdatesContext } from '../../../contexts/ml/ml_annotation_updates_context'; import { DatafeedChartFlyout } from '../../../jobs/jobs_list/components/datafeed_chart_flyout'; +import { RevertModelSnapshotFlyout } from '../../model_snapshots/revert_model_snapshot_flyout'; const editAnnotationsText = ( ); @@ -72,9 +73,14 @@ const CURRENT_SERIES = 'current_series'; class AnnotationsTableUI extends Component { static propTypes = { annotations: PropTypes.array, + annotationUpdatesService: PropTypes.object.isRequired, jobs: PropTypes.array, + detectors: PropTypes.array, isSingleMetricViewerLinkVisible: PropTypes.bool, isNumberBadgeVisible: PropTypes.bool, + refreshJobList: PropTypes.func, + chartDetails: PropTypes.object, + kibana: PropTypes.object, }; constructor(props) { @@ -91,6 +97,8 @@ class AnnotationsTableUI extends Component { ? this.props.jobs[0].job_id : undefined, datafeedFlyoutVisible: false, + modelSnapshot: null, + revertSnapshotFlyoutVisible: false, datafeedEnd: null, }; this.sorting = { @@ -727,10 +735,30 @@ class AnnotationsTableUI extends Component { datafeedFlyoutVisible: false, }); }} + onModelSnapshotAnnotationClick={(modelSnapshot) => { + this.setState({ + modelSnapshot, + revertSnapshotFlyoutVisible: true, + datafeedFlyoutVisible: false, + }); + }} end={this.state.datafeedEnd} jobId={this.state.jobId} /> ) : null} + {this.state.revertSnapshotFlyoutVisible === true && this.state.modelSnapshot !== null ? ( + { + this.setState({ + revertSnapshotFlyoutVisible: false, + }); + }} + refresh={this.props.refreshJobList ?? (() => {})} + /> + ) : null} ); } diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/datafeed_chart_flyout.tsx b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/datafeed_chart_flyout.tsx index cce322156af3a..8c4b96207b3a5 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/datafeed_chart_flyout.tsx +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/datafeed_chart_flyout.tsx @@ -50,12 +50,14 @@ import { DATAFEED_STATE } from '../../../../../../common/constants/states'; import { CombinedJobWithStats, ModelSnapshot, + MlSummaryJob, } from '../../../../../../common/types/anomaly_detection_jobs'; import { JobMessage } from '../../../../../../common/types/audit_message'; import { LineAnnotationDatumWithModelSnapshot } from '../../../../../../common/types/results'; import { useToastNotificationService } from '../../../../services/toast_notification_service'; import { useMlApiContext } from '../../../../contexts/kibana'; import { useCurrentEuiTheme } from '../../../../components/color_range_legend'; +import { RevertModelSnapshotFlyout } from '../../../../components/model_snapshots/revert_model_snapshot_flyout'; import { JobMessagesPane } from '../job_details/job_messages_pane'; import { EditQueryDelay } from './edit_query_delay'; import { CHART_DIRECTION, ChartDirectionType, CHART_SIZE } from './constants'; @@ -595,3 +597,87 @@ export const DatafeedChartFlyout: FC = ({ ); }; + +type ShowFunc = (jobUpdate: MlSummaryJob) => void; + +interface JobListDatafeedChartFlyoutProps { + setShowFunction: (showFunc: ShowFunc) => void; + unsetShowFunction: () => void; + refreshJobs(): void; +} + +/** + * Component to wire the datafeed chart flyout with the Job list view. + * @param setShowFunction function to show the flyout + * @param unsetShowFunction function called when flyout is closed + * @param refreshJobs function to refresh the jobs list + * @constructor + */ +export const JobListDatafeedChartFlyout: FC = ({ + setShowFunction, + unsetShowFunction, + refreshJobs, +}) => { + const [isVisible, setIsVisible] = useState(false); + const [job, setJob] = useState(); + const [jobWithStats, setJobWithStats] = useState(); + + const [isRevertModelSnapshotFlyoutVisible, setIsRevertModelSnapshotFlyoutVisible] = + useState(false); + const [snapshot, setSnapshot] = useState(null); + + const showFlyoutCallback = useCallback((jobUpdate: MlSummaryJob) => { + setJob(jobUpdate); + setIsVisible(true); + }, []); + + const showRevertModelSnapshot = useCallback(async () => { + // Need to load the full job with stats, as the model snapshot + // flyout needs the timestamp of the last result. + const fullJob: CombinedJobWithStats = await loadFullJob(job!.id); + setJobWithStats(fullJob); + setIsRevertModelSnapshotFlyoutVisible(true); + }, [job]); + + useEffect(() => { + setShowFunction(showFlyoutCallback); + return () => { + unsetShowFunction(); + }; + }, []); + + if (isVisible === true && job !== undefined) { + return ( + setIsVisible(false)} + onModelSnapshotAnnotationClick={(modelSnapshot) => { + setIsVisible(false); + setSnapshot(modelSnapshot); + showRevertModelSnapshot(); + }} + end={job.latestResultsTimestampMs || Date.now()} + jobId={job.id} + /> + ); + } + + if ( + isRevertModelSnapshotFlyoutVisible === true && + jobWithStats !== undefined && + snapshot !== null + ) { + return ( + { + setIsRevertModelSnapshotFlyoutVisible(false); + }} + refresh={refreshJobs} + /> + ); + } + + return null; +}; diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/index.ts b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/index.ts index ba1b6ae0b9707..1606c9491dee9 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/index.ts +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/datafeed_chart_flyout/index.ts @@ -5,4 +5,4 @@ * 2.0. */ -export { DatafeedChartFlyout } from './datafeed_chart_flyout'; +export { DatafeedChartFlyout, JobListDatafeedChartFlyout } from './datafeed_chart_flyout'; diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_actions/management.js b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_actions/management.js index 5b8b4b386213d..29045ad826bdf 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_actions/management.js +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_actions/management.js @@ -23,6 +23,7 @@ import { isManagedJob } from '../../../jobs_utils'; export function actionsMenuContent( showEditJobFlyout, + showDatafeedChartFlyout, showDeleteJobModal, showResetJobModal, showStartDatafeedModal, @@ -34,6 +35,7 @@ export function actionsMenuContent( const canCreateJob = checkPermission('canCreateJob') && mlNodesAvailable(); const canUpdateJob = checkPermission('canUpdateJob'); const canDeleteJob = checkPermission('canDeleteJob'); + const canGetDatafeeds = checkPermission('canGetDatafeeds'); const canUpdateDatafeed = checkPermission('canUpdateDatafeed'); const canStartStopDatafeed = checkPermission('canStartStopDatafeed') && mlNodesAvailable(); const canCloseJob = checkPermission('canCloseJob') && mlNodesAvailable(); @@ -152,6 +154,25 @@ export function actionsMenuContent( }, 'data-test-subj': 'mlActionButtonCloneJob', }, + { + name: i18n.translate('xpack.ml.jobsList.managementActions.viewDatafeedCountsLabel', { + defaultMessage: 'View datafeed counts', + }), + description: i18n.translate( + 'xpack.ml.jobsList.managementActions.viewDatafeedCountsDescription', + { + defaultMessage: 'View datafeed counts', + } + ), + icon: 'visAreaStacked', + enabled: () => canGetDatafeeds, + available: () => canGetDatafeeds, + onClick: (item) => { + showDatafeedChartFlyout(item); + closeMenu(); + }, + 'data-test-subj': 'mlActionButtonViewDatafeedChart', + }, { name: i18n.translate('xpack.ml.jobsList.managementActions.editJobLabel', { defaultMessage: 'Edit job', diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details.js b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details.js index 5a62800a6ce39..8d98052eab26c 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details.js +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details.js @@ -9,7 +9,7 @@ import PropTypes from 'prop-types'; import React, { Component, Fragment } from 'react'; import { FormattedMessage } from '@kbn/i18n-react'; import { i18n } from '@kbn/i18n'; -import { EuiButtonIcon, EuiTabbedContent, EuiLoadingSpinner, EuiToolTip } from '@elastic/eui'; +import { EuiButtonEmpty, EuiTabbedContent, EuiLoadingSpinner } from '@elastic/eui'; import { extractJobDetails } from './extract_job_details'; import { JsonPane } from './json_tab'; @@ -84,27 +84,20 @@ export class JobDetailsUI extends Component { } = extractJobDetails(job, basePath, refreshJobList); datafeed.titleAction = ( - + + this.setState({ + datafeedChartFlyoutVisible: true, + }) } + iconType="visAreaStacked" + size="s" > - - this.setState({ - datafeedChartFlyoutVisible: true, - }) - } + - + ); const tabs = [ @@ -248,7 +241,7 @@ export class JobDetailsUI extends Component { }), content: ( - + ), diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details_pane.js b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details_pane.js index 4046f4d5d8071..c70c049dd7489 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details_pane.js +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/job_details/job_details_pane.js @@ -44,7 +44,7 @@ function Section({ section }) { return ( - +

{section.title}

diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list/jobs_list.js b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list/jobs_list.js index a475f39a8c10b..09a783dd5ad7f 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list/jobs_list.js +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list/jobs_list.js @@ -330,6 +330,7 @@ export class JobsList extends Component { ), actions: actionsMenuContent( this.props.showEditJobFlyout, + this.props.showDatafeedChartFlyout, this.props.showDeleteJobModal, this.props.showResetJobModal, this.props.showStartDatafeedModal, @@ -406,6 +407,7 @@ JobsList.propTypes = { toggleRow: PropTypes.func.isRequired, selectJobChange: PropTypes.func.isRequired, showEditJobFlyout: PropTypes.func, + showDatafeedChartFlyout: PropTypes.func, showDeleteJobModal: PropTypes.func, showStartDatafeedModal: PropTypes.func, showCloseJobsConfirmModal: PropTypes.func, diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list_view/jobs_list_view.js b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list_view/jobs_list_view.js index 5e65a9bec23d6..0eb7f810932fb 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list_view/jobs_list_view.js +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/jobs_list_view/jobs_list_view.js @@ -14,6 +14,7 @@ import { JobsList } from '../jobs_list'; import { JobDetails } from '../job_details'; import { JobFilterBar } from '../job_filter_bar'; import { EditJobFlyout } from '../edit_job_flyout'; +import { JobListDatafeedChartFlyout } from '../datafeed_chart_flyout'; import { DeleteJobModal } from '../delete_job_modal'; import { ResetJobModal } from '../reset_job_modal'; import { StartDatafeedModal } from '../start_datafeed_modal'; @@ -53,6 +54,7 @@ export class JobsListView extends Component { this.updateFunctions = {}; this.showEditJobFlyout = () => {}; + this.showDatafeedChartFlyout = () => {}; this.showStopDatafeedsConfirmModal = () => {}; this.showCloseJobsConfirmModal = () => {}; this.showDeleteJobModal = () => {}; @@ -178,6 +180,13 @@ export class JobsListView extends Component { this.showEditJobFlyout = () => {}; }; + setShowDatafeedChartFlyoutFunction = (func) => { + this.showDatafeedChartFlyout = func; + }; + unsetShowDatafeedChartFlyoutFunction = () => { + this.showDatafeedChartFlyout = () => {}; + }; + setShowStopDatafeedsConfirmModalFunction = (func) => { this.showStopDatafeedsConfirmModal = func; }; @@ -437,6 +446,7 @@ export class JobsListView extends Component { toggleRow={this.toggleRow} selectJobChange={this.selectJobChange} showEditJobFlyout={this.showEditJobFlyout} + showDatafeedChartFlyout={this.showDatafeedChartFlyout} showDeleteJobModal={this.showDeleteJobModal} showResetJobModal={this.showResetJobModal} showCloseJobsConfirmModal={this.showCloseJobsConfirmModal} @@ -459,13 +469,17 @@ export class JobsListView extends Component { refreshJobs={() => this.refreshJobSummaryList(true)} allJobIds={jobIds} /> + this.refreshJobSummaryList(true)} + /> this.refreshJobSummaryList(true)} allJobIds={jobIds} /> - Date: Thu, 14 Jul 2022 13:35:35 +0300 Subject: [PATCH 018/111] [Cloud Posture] Refactor status and query logic out of CspPageTemplate (#136104) --- .../components/cloud_posture_page.test.tsx | 276 ++++++++++++++++++ .../public/components/cloud_posture_page.tsx | 193 ++++++++++++ .../public/components/csp_loading_state.tsx | 1 + .../components/csp_page_template.test.tsx | 250 +--------------- .../public/components/csp_page_template.tsx | 178 +---------- .../public/components/translations.ts | 36 --- .../compliance_dashboard.test.tsx | 19 +- .../compliance_dashboard.tsx | 88 +++--- .../compliance_dashboard/test_subjects.ts | 2 +- .../public/pages/findings/findings.tsx | 79 ++--- .../public/pages/rules/index.tsx | 39 +-- .../public/pages/rules/rules.test.tsx | 28 -- .../translations/translations/fr-FR.json | 10 - .../translations/translations/ja-JP.json | 10 - .../translations/translations/zh-CN.json | 10 - 15 files changed, 590 insertions(+), 629 deletions(-) create mode 100644 x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.test.tsx create mode 100644 x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.tsx delete mode 100644 x-pack/plugins/cloud_security_posture/public/components/translations.ts diff --git a/x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.test.tsx b/x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.test.tsx new file mode 100644 index 0000000000000..3ca9e9cf2d02c --- /dev/null +++ b/x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.test.tsx @@ -0,0 +1,276 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import Chance from 'chance'; +import { useCisKubernetesIntegration } from '../common/api/use_cis_kubernetes_integration'; +import { + DEFAULT_NO_DATA_TEST_SUBJECT, + ERROR_STATE_TEST_SUBJECT, + isCommonError, + LOADING_STATE_TEST_SUBJECT, + PACKAGE_NOT_INSTALLED_TEST_SUBJECT, +} from './cloud_posture_page'; +import { createReactQueryResponse } from '../test/fixtures/react_query'; +import { TestProvider } from '../test/test_provider'; +import { coreMock } from '@kbn/core/public/mocks'; +import { render, screen } from '@testing-library/react'; +import React, { ComponentProps } from 'react'; +import { UseQueryResult } from 'react-query'; +import { CloudPosturePage } from './cloud_posture_page'; +import { NoDataPage } from '@kbn/kibana-react-plugin/public'; + +const chance = new Chance(); +jest.mock('../common/api/use_cis_kubernetes_integration'); + +describe('', () => { + beforeEach(() => { + jest.resetAllMocks(); + // if package installation status is 'not_installed', CloudPosturePage will render a noDataConfig prompt + (useCisKubernetesIntegration as jest.Mock).mockImplementation(() => ({ + isSuccess: true, + isLoading: false, + data: { item: { status: 'installed' } }, + })); + }); + + const renderCloudPosturePage = ( + props: ComponentProps = { children: null } + ) => { + const mockCore = coreMock.createStart(); + + render( + + + + ); + }; + + it('renders children if integration is installed', () => { + const children = chance.sentence(); + renderCloudPosturePage({ children }); + + expect(screen.getByText(children)).toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('renders integrations installation prompt if integration is not installed', () => { + (useCisKubernetesIntegration as jest.Mock).mockImplementation(() => ({ + isSuccess: true, + isLoading: false, + data: { item: { status: 'not_installed' } }, + })); + + const children = chance.sentence(); + renderCloudPosturePage({ children }); + + expect(screen.getByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('renders default loading state when the integration query is loading', () => { + (useCisKubernetesIntegration as jest.Mock).mockImplementation( + () => + createReactQueryResponse({ + status: 'loading', + }) as unknown as UseQueryResult + ); + + const children = chance.sentence(); + renderCloudPosturePage({ children }); + + expect(screen.getByTestId(LOADING_STATE_TEST_SUBJECT)).toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('renders default error state when the integration query has an error', () => { + (useCisKubernetesIntegration as jest.Mock).mockImplementation( + () => + createReactQueryResponse({ + status: 'error', + error: new Error('error'), + }) as unknown as UseQueryResult + ); + + const children = chance.sentence(); + renderCloudPosturePage({ children }); + + expect(screen.getByTestId(ERROR_STATE_TEST_SUBJECT)).toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('renders default loading text when query isLoading', () => { + const query = createReactQueryResponse({ + status: 'loading', + }) as unknown as UseQueryResult; + + const children = chance.sentence(); + renderCloudPosturePage({ children, query }); + + expect(screen.getByTestId(LOADING_STATE_TEST_SUBJECT)).toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('renders default loading text when query is idle', () => { + const query = createReactQueryResponse({ + status: 'idle', + }) as unknown as UseQueryResult; + + const children = chance.sentence(); + renderCloudPosturePage({ children, query }); + + expect(screen.getByTestId(LOADING_STATE_TEST_SUBJECT)).toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('renders default error texts when query isError', () => { + const error = chance.sentence(); + const message = chance.sentence(); + const statusCode = chance.integer(); + + const query = createReactQueryResponse({ + status: 'error', + error: { + body: { + error, + message, + statusCode, + }, + }, + }) as unknown as UseQueryResult; + + const children = chance.sentence(); + renderCloudPosturePage({ children, query }); + + [error, message, statusCode].forEach((text) => + expect(screen.getByText(text, { exact: false })).toBeInTheDocument() + ); + expect(screen.getByTestId(ERROR_STATE_TEST_SUBJECT)).toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('prefers custom error render', () => { + const error = chance.sentence(); + const message = chance.sentence(); + const statusCode = chance.integer(); + + const query = createReactQueryResponse({ + status: 'error', + error: { + body: { + error, + message, + statusCode, + }, + }, + }) as unknown as UseQueryResult; + + const children = chance.sentence(); + renderCloudPosturePage({ + children, + query, + errorRender: (err) =>
{isCommonError(err) && err.body.message}
, + }); + + expect(screen.getByText(message)).toBeInTheDocument(); + [error, statusCode].forEach((text) => expect(screen.queryByText(text)).not.toBeInTheDocument()); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('prefers custom loading render', () => { + const loading = chance.sentence(); + + const query = createReactQueryResponse({ + status: 'loading', + }) as unknown as UseQueryResult; + + const children = chance.sentence(); + renderCloudPosturePage({ + children, + query, + loadingRender: () =>
{loading}
, + }); + + expect(screen.getByText(loading)).toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('renders no data prompt when query data is undefined', () => { + const query = createReactQueryResponse({ + status: 'success', + data: undefined, + }) as unknown as UseQueryResult; + + const children = chance.sentence(); + renderCloudPosturePage({ children, query }); + + expect(screen.getByTestId(DEFAULT_NO_DATA_TEST_SUBJECT)).toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); + + it('prefers custom no data prompt', () => { + const pageTitle = chance.sentence(); + const solution = chance.sentence(); + const docsLink = chance.sentence(); + const noDataRenderer = () => ( + + ); + + const query = createReactQueryResponse({ + status: 'success', + data: undefined, + }) as unknown as UseQueryResult; + + const children = chance.sentence(); + renderCloudPosturePage({ + children, + query, + noDataRenderer, + }); + + expect(screen.getByText(pageTitle)).toBeInTheDocument(); + expect(screen.getAllByText(solution, { exact: false })[0]).toBeInTheDocument(); + expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByText(children)).not.toBeInTheDocument(); + expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); + expect(screen.queryByTestId(PACKAGE_NOT_INSTALLED_TEST_SUBJECT)).not.toBeInTheDocument(); + }); +}); diff --git a/x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.tsx b/x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.tsx new file mode 100644 index 0000000000000..e56795d3b1380 --- /dev/null +++ b/x-pack/plugins/cloud_security_posture/public/components/cloud_posture_page.tsx @@ -0,0 +1,193 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import React from 'react'; +import { i18n } from '@kbn/i18n'; +import type { UseQueryResult } from 'react-query'; +import { EuiEmptyPrompt } from '@elastic/eui'; +import { FormattedMessage } from '@kbn/i18n-react'; +import { NoDataPage } from '@kbn/kibana-react-plugin/public'; +import { css } from '@emotion/react'; +import { CspLoadingState } from './csp_loading_state'; +import { useCisKubernetesIntegration } from '../common/api/use_cis_kubernetes_integration'; +import { useCISIntegrationLink } from '../common/navigation/use_navigate_to_cis_integration'; + +export const LOADING_STATE_TEST_SUBJECT = 'cloud_posture_page_loading'; +export const ERROR_STATE_TEST_SUBJECT = 'cloud_posture_page_error'; +export const PACKAGE_NOT_INSTALLED_TEST_SUBJECT = 'cloud_posture_page_package_not_installed'; +export const DEFAULT_NO_DATA_TEST_SUBJECT = 'cloud_posture_page_no_data'; + +interface CommonError { + body: { + error: string; + message: string; + statusCode: number; + }; +} + +export const isCommonError = (error: unknown): error is CommonError => { + if ( + !(error as any)?.body || + !(error as any)?.body?.error || + !(error as any)?.body?.message || + !(error as any)?.body?.statusCode + ) { + return false; + } + + return true; +}; + +const packageNotInstalledRenderer = (cisIntegrationLink?: string) => ( + +); + +const defaultLoadingRenderer = () => ( + + + +); + +const defaultErrorRenderer = (error: unknown) => ( + + + + } + body={ + isCommonError(error) ? ( +

+ +

+ ) : undefined + } + /> +); + +const defaultNoDataRenderer = () => { + return ( + + ); +}; + +interface CloudPosturePageProps { + children: React.ReactNode; + query?: UseQueryResult; + loadingRender?: () => React.ReactNode; + errorRender?: (error: TError) => React.ReactNode; + noDataRenderer?: () => React.ReactNode; +} + +export const CloudPosturePage = ({ + children, + query, + loadingRender = defaultLoadingRenderer, + errorRender = defaultErrorRenderer, + noDataRenderer = defaultNoDataRenderer, +}: CloudPosturePageProps) => { + const cisKubernetesPackageInfo = useCisKubernetesIntegration(); + const cisIntegrationLink = useCISIntegrationLink(); + + const render = () => { + if (cisKubernetesPackageInfo.isError) { + return defaultErrorRenderer(cisKubernetesPackageInfo.error); + } + + if (cisKubernetesPackageInfo.isLoading || cisKubernetesPackageInfo.isIdle) { + return defaultLoadingRenderer(); + } + + if (cisKubernetesPackageInfo.data.item.status !== 'installed') { + return packageNotInstalledRenderer(cisIntegrationLink); + } + + if (!query) { + return children; + } + + if (query.isError) { + return errorRender(query.error); + } + + if (query.isLoading || query.isIdle) { + return loadingRender(); + } + + if (!query.data) { + return noDataRenderer(); + } + + return children; + }; + + return <>{render()}; +}; diff --git a/x-pack/plugins/cloud_security_posture/public/components/csp_loading_state.tsx b/x-pack/plugins/cloud_security_posture/public/components/csp_loading_state.tsx index 21a01c9f52ace..7b2e9f0f03ae7 100644 --- a/x-pack/plugins/cloud_security_posture/public/components/csp_loading_state.tsx +++ b/x-pack/plugins/cloud_security_posture/public/components/csp_loading_state.tsx @@ -18,6 +18,7 @@ export const CspLoadingState: React.FunctionComponent<{ ['data-test-subj']?: str { it('maps navigation items to side navigation items', () => { const navigationItem = createNavigationItemFixture(); @@ -52,230 +31,3 @@ describe('getSideNavItems', () => { expect(sideNavItems).toHaveLength(0); }); }); - -describe('', () => { - beforeEach(() => { - jest.resetAllMocks(); - // if package installation status is 'not_installed', CspPageTemplate will render a noDataConfig prompt - (useCisKubernetesIntegration as jest.Mock).mockImplementation(() => ({ - isSuccess: true, - isLoading: false, - data: { item: { status: 'installed' } }, - })); - }); - - const renderCspPageTemplate = (props: ComponentProps = {}) => { - const mockCore = coreMock.createStart(); - - render( - - - - ); - }; - - it('renders children if integration is installed', () => { - const children = chance.sentence(); - renderCspPageTemplate({ children }); - - expect(screen.getByText(children)).toBeInTheDocument(); - expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); - - it('renders integrations installation prompt if integration is not installed', () => { - (useCisKubernetesIntegration as jest.Mock).mockImplementation(() => ({ - isSuccess: true, - isLoading: false, - data: { item: { status: 'not_installed' } }, - })); - - const children = chance.sentence(); - renderCspPageTemplate({ children }); - - Object.values(PACKAGE_NOT_INSTALLED_TEXT).forEach((text) => - expect(screen.getAllByText(text)[0]).toBeInTheDocument() - ); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - }); - - it('renders default loading text when query isLoading', () => { - const query = createReactQueryResponse({ - status: 'loading', - }) as unknown as UseQueryResult; - - const children = chance.sentence(); - renderCspPageTemplate({ children, query }); - - expect(screen.getByTestId(LOADING_STATE_TEST_SUBJECT)).toBeInTheDocument(); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); - - it('renders default loading text when query is idle', () => { - const query = createReactQueryResponse({ - status: 'idle', - }) as unknown as UseQueryResult; - - const children = chance.sentence(); - renderCspPageTemplate({ children, query }); - - expect(screen.getByTestId(LOADING_STATE_TEST_SUBJECT)).toBeInTheDocument(); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); - - it('renders default error texts when query isError', () => { - const error = chance.sentence(); - const message = chance.sentence(); - const statusCode = chance.integer(); - - const query = createReactQueryResponse({ - status: 'error', - error: { - body: { - error, - message, - statusCode, - }, - }, - }) as unknown as UseQueryResult; - - const children = chance.sentence(); - renderCspPageTemplate({ children, query }); - - [error, message, statusCode].forEach((text) => - expect(screen.getByText(text, { exact: false })).toBeInTheDocument() - ); - expect(screen.getByTestId(ERROR_STATE_TEST_SUBJECT)).toBeInTheDocument(); - expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); - - it('prefers custom error render', () => { - const error = chance.sentence(); - const message = chance.sentence(); - const statusCode = chance.integer(); - - const query = createReactQueryResponse({ - status: 'error', - error: { - body: { - error, - message, - statusCode, - }, - }, - }) as unknown as UseQueryResult; - - const children = chance.sentence(); - renderCspPageTemplate({ - children, - query, - errorRender: (err) =>
{isCommonError(err) && err.body.message}
, - }); - - expect(screen.getByText(message)).toBeInTheDocument(); - [error, statusCode].forEach((text) => expect(screen.queryByText(text)).not.toBeInTheDocument()); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); - - it('prefers custom loading render', () => { - const loading = chance.sentence(); - - const query = createReactQueryResponse({ - status: 'loading', - }) as unknown as UseQueryResult; - - const children = chance.sentence(); - renderCspPageTemplate({ - children, - query, - loadingRender: () =>
{loading}
, - }); - - expect(screen.getByText(loading)).toBeInTheDocument(); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); - - it('renders noDataConfig prompt when query data is undefined', () => { - const query = createReactQueryResponse({ - status: 'success', - data: undefined, - }) as unknown as UseQueryResult; - - const children = chance.sentence(); - renderCspPageTemplate({ children, query }); - - expect(screen.getByText(DEFAULT_NO_DATA_TEXT.PAGE_TITLE)).toBeInTheDocument(); - expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); - - it('prefers custom noDataConfig prompt', () => { - const pageTitle = chance.sentence(); - const solution = chance.sentence(); - const docsLink = chance.sentence(); - - const query = createReactQueryResponse({ - status: 'success', - data: undefined, - }) as unknown as UseQueryResult; - - const children = chance.sentence(); - renderCspPageTemplate({ - children, - query, - noDataConfig: { pageTitle, solution, docsLink, actions: {} }, - }); - - expect(screen.getByText(pageTitle)).toBeInTheDocument(); - expect(screen.getAllByText(solution, { exact: false })[0]).toBeInTheDocument(); - expect(screen.queryByTestId(LOADING_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - expect(screen.queryByText(children)).not.toBeInTheDocument(); - expect(screen.queryByTestId(ERROR_STATE_TEST_SUBJECT)).not.toBeInTheDocument(); - packageNotInstalledUniqueTexts.forEach((text) => - expect(screen.queryByText(text)).not.toBeInTheDocument() - ); - }); -}); diff --git a/x-pack/plugins/cloud_security_posture/public/components/csp_page_template.tsx b/x-pack/plugins/cloud_security_posture/public/components/csp_page_template.tsx index 24ac368b0ec01..7a6d4272edbc3 100644 --- a/x-pack/plugins/cloud_security_posture/public/components/csp_page_template.tsx +++ b/x-pack/plugins/cloud_security_posture/public/components/csp_page_template.tsx @@ -5,45 +5,18 @@ * 2.0. */ import React from 'react'; -import type { UseQueryResult } from 'react-query'; import { NavLink } from 'react-router-dom'; -import { EuiEmptyPrompt, EuiErrorBoundary, EuiTitle } from '@elastic/eui'; -import { FormattedMessage } from '@kbn/i18n-react'; -import { KibanaPageTemplate, type KibanaPageTemplateProps } from '@kbn/kibana-react-plugin/public'; +import { i18n } from '@kbn/i18n'; +import { EuiErrorBoundary } from '@elastic/eui'; +import { KibanaPageTemplate, type KibanaPageTemplateProps } from '@kbn/shared-ux-components'; import { allNavigationItems } from '../common/navigation/constants'; import type { CspNavigationItem } from '../common/navigation/types'; -import { CspLoadingState } from './csp_loading_state'; -import { - CLOUD_SECURITY_POSTURE, - DEFAULT_NO_DATA_TEXT, - PACKAGE_NOT_INSTALLED_TEXT, -} from './translations'; -import { useCisKubernetesIntegration } from '../common/api/use_cis_kubernetes_integration'; -import { useCISIntegrationLink } from '../common/navigation/use_navigate_to_cis_integration'; - -export interface CommonError { - body: { - error: string; - message: string; - statusCode: number; - }; -} - -export const isCommonError = (x: any): x is CommonError => { - if (!('body' in x)) return false; - - const { - body: { error, message, statusCode }, - } = x; - - return !!(error && message && statusCode); -}; const activeItemStyle = { fontWeight: 700 }; export const getSideNavItems = ( navigationItems: Record -): NonNullable['items'] => +): NonNullable['items']> => Object.entries(navigationItems) .filter(([_, navigationItem]) => !navigationItem.disabled) .map(([id, navigationItem]) => ({ @@ -58,7 +31,9 @@ export const getSideNavItems = ( const DEFAULT_PAGE_PROPS: KibanaPageTemplateProps = { solutionNav: { - name: CLOUD_SECURITY_POSTURE, + name: i18n.translate('xpack.csp.cspPageTemplate.navigationTitle', { + defaultMessage: 'Cloud Security Posture', + }), items: getSideNavItems({ dashboard: allNavigationItems.dashboard, findings: allNavigationItems.findings, @@ -68,146 +43,13 @@ const DEFAULT_PAGE_PROPS: KibanaPageTemplateProps = { restrictWidth: false, }; -export const DEFAULT_NO_DATA_CONFIG: KibanaPageTemplateProps['noDataConfig'] = { - pageTitle: DEFAULT_NO_DATA_TEXT.PAGE_TITLE, - solution: DEFAULT_NO_DATA_TEXT.SOLUTION, - // TODO: Add real docs link once we have it - docsLink: 'https://www.elastic.co/guide/index.html', - logo: 'logoSecurity', - actions: {}, -}; - -export const LOADING_STATE_TEST_SUBJECT = 'csp_page_template_loading'; -export const ERROR_STATE_TEST_SUBJECT = 'csp_page_template_error'; - -const getPackageNotInstalledNoDataConfig = ( - cisIntegrationLink?: string -): KibanaPageTemplateProps['noDataConfig'] => ({ - pageTitle: PACKAGE_NOT_INSTALLED_TEXT.PAGE_TITLE, - solution: PACKAGE_NOT_INSTALLED_TEXT.SOLUTION, - // TODO: Add real docs link once we have it - docsLink: 'https://www.elastic.co/guide/index.html', - logo: 'logoSecurity', - actions: { - elasticAgent: { - href: cisIntegrationLink, - isDisabled: !cisIntegrationLink, - title: PACKAGE_NOT_INSTALLED_TEXT.BUTTON_TITLE, - description: PACKAGE_NOT_INSTALLED_TEXT.DESCRIPTION, - }, - }, -}); - -const DefaultLoading = () => ( - - - -); - -const DefaultError = (error: unknown) => ( - - -

- -

-
- {isCommonError(error) && ( - <> - -
- -
-
- -
- -
-
- - )} - - } - /> -); - export const CspPageTemplate = ({ - query, children, - loadingRender = DefaultLoading, - errorRender = DefaultError, ...kibanaPageTemplateProps -}: KibanaPageTemplateProps & { - loadingRender?: () => React.ReactNode; - errorRender?: (error: TError) => React.ReactNode; - query?: UseQueryResult; -}) => { - const cisKubernetesPackageInfo = useCisKubernetesIntegration(); - const cisIntegrationLink = useCISIntegrationLink(); - - const getNoDataConfig = (): KibanaPageTemplateProps['noDataConfig'] => { - if (cisKubernetesPackageInfo.data?.item.status !== 'installed') { - return getPackageNotInstalledNoDataConfig(cisIntegrationLink); - } - - // when query was successful, but data is undefined - if (query?.isSuccess && !query?.data) { - return kibanaPageTemplateProps.noDataConfig || DEFAULT_NO_DATA_CONFIG; - } - - return kibanaPageTemplateProps.noDataConfig; - }; - - const getTemplate = (): KibanaPageTemplateProps['template'] => { - if (query?.isLoading || query?.isError || cisKubernetesPackageInfo.isLoading) - return 'centeredContent'; - - return kibanaPageTemplateProps.template || 'default'; - }; - - const render = () => { - if (query?.isLoading || query?.isIdle || cisKubernetesPackageInfo.isLoading) { - return loadingRender(); - } - if (query?.isError) return errorRender(query.error); - if (query?.isSuccess) return children; - - return children; - }; - +}: KibanaPageTemplateProps) => { return ( - - - <>{render()} - + + {children} ); }; diff --git a/x-pack/plugins/cloud_security_posture/public/components/translations.ts b/x-pack/plugins/cloud_security_posture/public/components/translations.ts deleted file mode 100644 index 84d1ae489f8ea..0000000000000 --- a/x-pack/plugins/cloud_security_posture/public/components/translations.ts +++ /dev/null @@ -1,36 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ -import { i18n } from '@kbn/i18n'; - -export const PACKAGE_NOT_INSTALLED_TEXT = { - PAGE_TITLE: i18n.translate('xpack.csp.cspPageTemplate.packageNotInstalled.pageTitle', { - defaultMessage: 'Install Integration to get started', - }), - SOLUTION: i18n.translate('xpack.csp.cspPageTemplate.packageNotInstalled.solutionNameLabel', { - defaultMessage: 'Cloud Security Posture', - }), - BUTTON_TITLE: i18n.translate('xpack.csp.cspPageTemplate.packageNotInstalled.buttonLabel', { - defaultMessage: 'Add a CIS integration', - }), - DESCRIPTION: i18n.translate('xpack.csp.cspPageTemplate.packageNotInstalled.description', { - defaultMessage: - 'Use our CIS Kubernetes Benchmark integration to measure your Kubernetes cluster setup against the CIS recommendations.', - }), -}; - -export const DEFAULT_NO_DATA_TEXT = { - PAGE_TITLE: i18n.translate('xpack.csp.cspPageTemplate.defaultNoDataConfig.pageTitle', { - defaultMessage: 'No data found', - }), - SOLUTION: i18n.translate('xpack.csp.cspPageTemplate.defaultNoDataConfig.solutionNameLabel', { - defaultMessage: 'Cloud Security Posture', - }), -}; - -export const CLOUD_SECURITY_POSTURE = i18n.translate('xpack.csp.cspPageTemplate.navigationTitle', { - defaultMessage: 'Cloud Security Posture', -}); diff --git a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx index 4b25fe3c8b175..71362c2c92525 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx +++ b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx @@ -5,6 +5,7 @@ * 2.0. */ +import { createReactQueryResponse } from '../../test/fixtures/react_query'; import React from 'react'; import { coreMock } from '@kbn/core/public/mocks'; import { render, screen } from '@testing-library/react'; @@ -13,7 +14,7 @@ import { ComplianceDashboard } from '..'; import { useCspSetupStatusApi } from '../../common/api/use_setup_status_api'; import { useCisKubernetesIntegration } from '../../common/api/use_cis_kubernetes_integration'; import { useComplianceDashboardDataApi } from '../../common/api/use_compliance_dashboard_data_api'; -import { DASHBOARD_PAGE_HEADER, MISSING_FINDINGS_NO_DATA_CONFIG } from './test_subjects'; +import { DASHBOARD_CONTAINER, MISSING_FINDINGS_NO_DATA_CONFIG } from './test_subjects'; jest.mock('../../common/api/use_setup_status_api'); jest.mock('../../common/api/use_cis_kubernetes_integration'); @@ -196,17 +197,17 @@ describe('', () => { }; it('shows noDataConfig when latestFindingsIndexStatus is inapplicable', () => { - (useCspSetupStatusApi as jest.Mock).mockImplementation(() => ({ - data: { latestFindingsIndexStatus: 'inapplicable' }, - })); - (useComplianceDashboardDataApi as jest.Mock).mockImplementation(() => ({ - data: undefined, - })); + (useCspSetupStatusApi as jest.Mock).mockImplementation(() => + createReactQueryResponse({ status: 'success', data: 'inapplicable' }) + ); + (useComplianceDashboardDataApi as jest.Mock).mockImplementation(() => + createReactQueryResponse({ status: 'success', data: undefined }) + ); renderComplianceDashboardPage(); expect(screen.queryByTestId(MISSING_FINDINGS_NO_DATA_CONFIG)).toBeInTheDocument(); - expect(screen.queryByTestId(DASHBOARD_PAGE_HEADER)).not.toBeInTheDocument(); + expect(screen.queryByTestId(DASHBOARD_CONTAINER)).not.toBeInTheDocument(); }); it('shows dashboard when latestFindingsIndexStatus is applicable', () => { @@ -225,6 +226,6 @@ describe('', () => { renderComplianceDashboardPage(); expect(screen.queryByTestId(MISSING_FINDINGS_NO_DATA_CONFIG)).not.toBeInTheDocument(); - expect(screen.getByTestId(DASHBOARD_PAGE_HEADER)).toBeInTheDocument(); + expect(screen.getByTestId(DASHBOARD_CONTAINER)).toBeInTheDocument(); }); }); diff --git a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx index e0ba90441ea74..606d7671125da 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx +++ b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx @@ -7,10 +7,12 @@ import React from 'react'; import { EuiSpacer, EuiIcon } from '@elastic/eui'; -import { type KibanaPageTemplateProps } from '@kbn/kibana-react-plugin/public'; +import { NoDataPage } from '@kbn/kibana-react-plugin/public'; import { UseQueryResult } from 'react-query'; import { i18n } from '@kbn/i18n'; -import { DASHBOARD_PAGE_HEADER, MISSING_FINDINGS_NO_DATA_CONFIG } from './test_subjects'; +import { css } from '@emotion/react'; +import { CloudPosturePage } from '../../components/cloud_posture_page'; +import { DASHBOARD_CONTAINER, MISSING_FINDINGS_NO_DATA_CONFIG } from './test_subjects'; import { allNavigationItems } from '../../common/navigation/constants'; import { useCspBreadcrumbs } from '../../common/navigation/use_csp_breadcrumbs'; import { SummarySection } from './dashboard_sections/summary_section'; @@ -19,31 +21,39 @@ import { useComplianceDashboardDataApi } from '../../common/api'; import { CspPageTemplate } from '../../components/csp_page_template'; import { useCspSetupStatusApi } from '../../common/api/use_setup_status_api'; -const getNoDataConfig = (onClick: () => void): KibanaPageTemplateProps['noDataConfig'] => ({ - 'data-test-subj': MISSING_FINDINGS_NO_DATA_CONFIG, - pageTitle: i18n.translate('xpack.csp.dashboard.noDataConfig.pageTitle', { - defaultMessage: 'Cloud Posture Dashboard', - }), - solution: i18n.translate('xpack.csp.dashboard.noDataConfig.solutionNameTitle', { - defaultMessage: 'Cloud Security Posture', - }), - // TODO: Add real docs link once we have it - docsLink: 'https://www.elastic.co/guide/index.html', - logo: 'logoSecurity', - actions: { - dashboardNoDataCard: { - icon: , - onClick, - title: i18n.translate('xpack.csp.dashboard.noDataConfig.actionTitle', { - defaultMessage: 'Try Again', - }), - description: i18n.translate('xpack.csp.dashboard.noDataConfig.actionDescription', { - defaultMessage: - "The cloud posture dashboard can't be presented since there are no findings. This can happen due to the agent not being installed yet, or since data is still being processed.", - }), - }, - }, -}); +const NoData = ({ onClick }: { onClick: () => void }) => ( + , + onClick, + title: i18n.translate('xpack.csp.dashboard.noDataConfig.actionTitle', { + defaultMessage: 'Try Again', + }), + description: i18n.translate('xpack.csp.dashboard.noDataConfig.actionDescription', { + defaultMessage: + "The cloud posture dashboard can't be presented since there are no findings. This can happen due to the agent not being installed yet, or since data is still being processed.", + }), + }, + }} + /> +); export const ComplianceDashboard = () => { const getInfo = useCspSetupStatusApi(); @@ -51,6 +61,7 @@ export const ComplianceDashboard = () => { const getDashboardData = useComplianceDashboardDataApi({ enabled: isFindingsIndexApplicable, }); + useCspBreadcrumbs([allNavigationItems.dashboard]); const pageQuery: UseQueryResult = isFindingsIndexApplicable ? getDashboardData : getInfo; @@ -58,23 +69,24 @@ export const ComplianceDashboard = () => { return ( - {getDashboardData.data && ( - <> - - - - - - )} + + {isFindingsIndexApplicable ? ( +
+ + + + +
+ ) : ( + + )} +
); }; diff --git a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/test_subjects.ts b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/test_subjects.ts index 04cf7a1398114..6e0ca5773b7fc 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/test_subjects.ts +++ b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/test_subjects.ts @@ -6,4 +6,4 @@ */ export const MISSING_FINDINGS_NO_DATA_CONFIG = 'missing-findings-no-data-config'; -export const DASHBOARD_PAGE_HEADER = 'dashboard-page-header'; +export const DASHBOARD_CONTAINER = 'dashboard-container'; diff --git a/x-pack/plugins/cloud_security_posture/public/pages/findings/findings.tsx b/x-pack/plugins/cloud_security_posture/public/pages/findings/findings.tsx index 599ab03545a2c..a8220c752b27f 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/findings/findings.tsx +++ b/x-pack/plugins/cloud_security_posture/public/pages/findings/findings.tsx @@ -7,6 +7,7 @@ import React from 'react'; import type { UseQueryResult } from 'react-query'; import { Redirect, Switch, Route, useLocation } from 'react-router-dom'; +import { CloudPosturePage } from '../../components/cloud_posture_page'; import { useFindingsEsPit } from './es_pit/use_findings_es_pit'; import { FindingsEsPitContext } from './es_pit/findings_es_pit_context'; import { useLatestFindingsDataView } from '../../common/api/use_latest_findings_data_view'; @@ -21,48 +22,50 @@ export const Findings = () => { // TODO: Consider splitting the PIT window so that each "group by" view has its own PIT const { pitQuery, pitIdRef, setPitId } = useFindingsEsPit('findings'); - let queryForPageTemplate: UseQueryResult = dataViewQuery; + let queryForSetupStatus: UseQueryResult = dataViewQuery; if (pitQuery.isError || pitQuery.isLoading || pitQuery.isIdle) { - queryForPageTemplate = pitQuery; + queryForSetupStatus = pitQuery; } return ( - - , - setPitId, - }} - > - - ( - - )} - /> - } - /> - } - /> - } - /> - - + + + , + setPitId, + }} + > + + ( + + )} + /> + } + /> + } + /> + } + /> + + + ); }; diff --git a/x-pack/plugins/cloud_security_posture/public/pages/rules/index.tsx b/x-pack/plugins/cloud_security_posture/public/pages/rules/index.tsx index 6b9953e429d9f..65de13726ced3 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/rules/index.tsx +++ b/x-pack/plugins/cloud_security_posture/public/pages/rules/index.tsx @@ -7,19 +7,18 @@ import React, { useMemo } from 'react'; import { generatePath, Link, RouteComponentProps } from 'react-router-dom'; -import { EuiTextColor, EuiEmptyPrompt, EuiButtonEmpty, EuiFlexGroup } from '@elastic/eui'; -import * as t from 'io-ts'; -import type { KibanaPageTemplateProps } from '@kbn/kibana-react-plugin/public'; +import { EuiTextColor, EuiButtonEmpty, EuiFlexGroup } from '@elastic/eui'; +import type { KibanaPageTemplateProps } from '@kbn/shared-ux-components'; import { FormattedMessage } from '@kbn/i18n-react'; import { pagePathGetters } from '@kbn/fleet-plugin/public'; import { RulesContainer, type PageUrlParams } from './rules_container'; import { allNavigationItems } from '../../common/navigation/constants'; import { useCspBreadcrumbs } from '../../common/navigation/use_csp_breadcrumbs'; import { CspNavigationItem } from '../../common/navigation/types'; -import { extractErrorMessage } from '../../../common/utils/helpers'; import { useCspIntegrationInfo } from './use_csp_integration'; import { CspPageTemplate } from '../../components/csp_page_template'; import { useKibana } from '../../common/hooks/use_kibana'; +import { CloudPosturePage } from '../../components/cloud_posture_page'; const getRulesBreadcrumbs = (name?: string): CspNavigationItem[] => [allNavigationItems.benchmarks, { ...allNavigationItems.rules, name }].filter( @@ -93,34 +92,10 @@ export const Rules = ({ match: { params } }: RouteComponentProps) ); return ( - } - > - + + + + ); }; - -// react-query puts the response data on the 'error' object -const bodyError = t.type({ - body: t.type({ - message: t.string, - }), -}); - -const extractErrorBodyMessage = (err: unknown) => { - if (bodyError.is(err)) return err.body.message; - return extractErrorMessage(err); -}; - -const RulesErrorPrompt = ({ error }: { error: string }) => ( - {error}, - }} - /> -); diff --git a/x-pack/plugins/cloud_security_posture/public/pages/rules/rules.test.tsx b/x-pack/plugins/cloud_security_posture/public/pages/rules/rules.test.tsx index 0acf17dc8005f..2056173d99f88 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/rules/rules.test.tsx +++ b/x-pack/plugins/cloud_security_posture/public/pages/rules/rules.test.tsx @@ -6,7 +6,6 @@ */ import React from 'react'; -import { LOADING_STATE_TEST_SUBJECT } from '../../components/csp_page_template'; import { Rules } from '.'; import { render, screen } from '@testing-library/react'; import { QueryClient } from 'react-query'; @@ -79,33 +78,6 @@ describe('', () => { expect(useCspIntegrationInfo).toHaveBeenCalledWith(params); }); - it('displays error state when request had an error', async () => { - const Component = getTestComponent({ packagePolicyId: '1', policyId: '2' }); - const request = createReactQueryResponse({ - status: 'error', - error: new Error('some error message'), - }); - - (useCspIntegrationInfo as jest.Mock).mockReturnValue(request); - - render(); - - expect(await screen.findByText(request.error?.message!)).toBeInTheDocument(); - }); - - it('displays loading state when request is pending', () => { - const Component = getTestComponent({ packagePolicyId: '21', policyId: '22' }); - const request = createReactQueryResponse({ - status: 'loading', - }); - - (useCspIntegrationInfo as jest.Mock).mockReturnValue(request); - - render(); - - expect(screen.getByTestId(LOADING_STATE_TEST_SUBJECT)).toBeInTheDocument(); - }); - it('displays success state when result request is resolved', async () => { const Component = getTestComponent({ packagePolicyId: '21', policyId: '22' }); const request = createReactQueryResponse({ diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index 5f685e8958e29..e36d4abb75a1c 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -10439,14 +10439,7 @@ "xpack.csp.cspHealthBadge.criticalLabel": "Critique", "xpack.csp.cspHealthBadge.healthyLabel": "Intègre", "xpack.csp.cspHealthBadge.warningLabel": "Avertissement", - "xpack.csp.cspPageTemplate.defaultNoDataConfig.pageTitle": "Aucune donnée trouvée", - "xpack.csp.cspPageTemplate.defaultNoDataConfig.solutionNameLabel": "Niveau de sécurité du cloud", - "xpack.csp.cspPageTemplate.loadingDescription": "Chargement...", "xpack.csp.cspPageTemplate.navigationTitle": "Niveau de sécurité du cloud", - "xpack.csp.cspPageTemplate.packageNotInstalled.buttonLabel": "Ajouter une intégration CIS", - "xpack.csp.cspPageTemplate.packageNotInstalled.description": "Utilisez notre intégration CIS Kubernetes Benchmark pour mesurer votre configuration de cluster Kubernetes par rapport aux recommandations du CIS.", - "xpack.csp.cspPageTemplate.packageNotInstalled.pageTitle": "Installer l'intégration pour commencer", - "xpack.csp.cspPageTemplate.packageNotInstalled.solutionNameLabel": "Niveau de sécurité du cloud", "xpack.csp.cspSettings.rules": "Règles de sécurité du CSP - ", "xpack.csp.dashboard.risksTable.cisSectionColumnLabel": "Section CIS", "xpack.csp.expandColumnDescriptionLabel": "Développer", @@ -10466,9 +10459,6 @@ "xpack.csp.findings.resourceFindings.backToResourcesPageButtonLabel": "Retour à la vue de regroupement par ressource", "xpack.csp.findings.searchBar.searchPlaceholder": "Rechercher dans les résultats (par ex. rule.section.keyword : \"serveur d'API\")", "xpack.csp.navigation.cloudPostureBreadcrumbLabel": "Niveau du cloud", - "xpack.csp.pageTemplate.errorDetails.errorBodyTitle": "{body}", - "xpack.csp.pageTemplate.errorDetails.errorCodeTitle": "{error} {statusCode}", - "xpack.csp.pageTemplate.loadErrorMessage": "Nous n'avons pas pu récupérer vos données sur le niveau de sécurité du cloud.", "xpack.csp.rules.activateAllButtonLabel": "Activer {count, plural, one {# règle} other {# règles}}", "xpack.csp.rules.clearSelectionButtonLabel": "Effacer la sélection", "xpack.csp.rules.deactivateAllButtonLabel": "Désactiver {count, plural, one {# règle} other {# règles}}", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index ccc7ddeff55c2..cc42d39638c58 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -10431,14 +10431,7 @@ "xpack.csp.cspHealthBadge.criticalLabel": "重大", "xpack.csp.cspHealthBadge.healthyLabel": "正常", "xpack.csp.cspHealthBadge.warningLabel": "警告", - "xpack.csp.cspPageTemplate.defaultNoDataConfig.pageTitle": "データが見つかりません", - "xpack.csp.cspPageTemplate.defaultNoDataConfig.solutionNameLabel": "クラウドセキュリティ態勢", - "xpack.csp.cspPageTemplate.loadingDescription": "読み込み中...", "xpack.csp.cspPageTemplate.navigationTitle": "クラウドセキュリティ態勢", - "xpack.csp.cspPageTemplate.packageNotInstalled.buttonLabel": "CIS統合を追加", - "xpack.csp.cspPageTemplate.packageNotInstalled.description": "CIS Kubernetes Benchmark統合は、CISの推奨事項に照らしてKubernetesクラスター設定を測定します。", - "xpack.csp.cspPageTemplate.packageNotInstalled.pageTitle": "開始するには統合をインストールしてください", - "xpack.csp.cspPageTemplate.packageNotInstalled.solutionNameLabel": "クラウドセキュリティ態勢", "xpack.csp.cspSettings.rules": "CSPセキュリティルール - ", "xpack.csp.dashboard.risksTable.cisSectionColumnLabel": "CISセクション", "xpack.csp.expandColumnDescriptionLabel": "拡張", @@ -10458,9 +10451,6 @@ "xpack.csp.findings.resourceFindings.backToResourcesPageButtonLabel": "リソース別グループビューに戻る", "xpack.csp.findings.searchBar.searchPlaceholder": "検索結果(例:rule.section.keyword:\"API Server\")", "xpack.csp.navigation.cloudPostureBreadcrumbLabel": "クラウド態勢", - "xpack.csp.pageTemplate.errorDetails.errorBodyTitle": "{body}", - "xpack.csp.pageTemplate.errorDetails.errorCodeTitle": "{error} {statusCode}", - "xpack.csp.pageTemplate.loadErrorMessage": "クラウドセキュリティ態勢データを取得できませんでした", "xpack.csp.rules.activateAllButtonLabel": "{count, plural, other {#個のルール}}をアクティブ化", "xpack.csp.rules.clearSelectionButtonLabel": "選択した項目をクリア", "xpack.csp.rules.deactivateAllButtonLabel": "{count, plural, other {#個のルール}}を非アクティブ化", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index 0dc9363d378b1..a0848f0acf9ad 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -10446,14 +10446,7 @@ "xpack.csp.cspHealthBadge.criticalLabel": "紧急", "xpack.csp.cspHealthBadge.healthyLabel": "运行正常", "xpack.csp.cspHealthBadge.warningLabel": "警告", - "xpack.csp.cspPageTemplate.defaultNoDataConfig.pageTitle": "未找到任何数据", - "xpack.csp.cspPageTemplate.defaultNoDataConfig.solutionNameLabel": "云安全态势", - "xpack.csp.cspPageTemplate.loadingDescription": "正在加载……", "xpack.csp.cspPageTemplate.navigationTitle": "云安全态势", - "xpack.csp.cspPageTemplate.packageNotInstalled.buttonLabel": "添加 CIS 集成", - "xpack.csp.cspPageTemplate.packageNotInstalled.description": "使用我们的 CIS Kubernetes 基准集成根据 CIS 建议衡量 Kubernetes 集群设置。", - "xpack.csp.cspPageTemplate.packageNotInstalled.pageTitle": "安装集成以开始", - "xpack.csp.cspPageTemplate.packageNotInstalled.solutionNameLabel": "云安全态势", "xpack.csp.cspSettings.rules": "CSP 安全规则 - ", "xpack.csp.dashboard.risksTable.cisSectionColumnLabel": "CIS 部分", "xpack.csp.expandColumnDescriptionLabel": "展开", @@ -10473,9 +10466,6 @@ "xpack.csp.findings.resourceFindings.backToResourcesPageButtonLabel": "返回到按资源视图分组", "xpack.csp.findings.searchBar.searchPlaceholder": "搜索结果(例如,rule.section.keyword:“APM 服务器”)", "xpack.csp.navigation.cloudPostureBreadcrumbLabel": "云态势", - "xpack.csp.pageTemplate.errorDetails.errorBodyTitle": "{body}", - "xpack.csp.pageTemplate.errorDetails.errorCodeTitle": "{error} {statusCode}", - "xpack.csp.pageTemplate.loadErrorMessage": "我们无法提取您的云安全态势数据", "xpack.csp.rules.activateAllButtonLabel": "激活 {count, plural, other {# 个规则}}", "xpack.csp.rules.clearSelectionButtonLabel": "清除所选内容", "xpack.csp.rules.deactivateAllButtonLabel": "停用 {count, plural, other {# 个规则}}", From b58d07e05be3c759c4a7c9e3c29f1a8de027f5ff Mon Sep 17 00:00:00 2001 From: Carlos Crespo Date: Thu, 14 Jul 2022 13:29:09 +0200 Subject: [PATCH 019/111] [Stack Monitoring] Add OpenTelemetry metrics to Monitoring Collection plugin (#135999) * Add otel metrics to alerting plugin * clean up otel poc * Bump @opentelemetry/api-metrics and @opentelemetry/exporter-metrics-otlp-grpc versions to 0.30.0 * Add integration test for prometheus endpoint; improve reademe.md * Fix tsconfig.base.json missing entries * Bump @opentelemetry/sdk-metrics-base; clean up * Rename PrometheusExporter properties * Readme formatting tweaks * Fix incorrect path * Remove grpc dependency * Add grpc back for handling auth headers * Fix comment positioning * Include authenticated OTLP in readme * Extract dynamic route into a new file * Enable otlp logging and compatibility with env vars * Enable OTEL_EXPORTER_OTLP_ENDPOINT env var Co-authored-by: Mat Schaffer Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .github/CODEOWNERS | 1 + package.json | 8 + test/common/config.js | 2 + .../fixtures/plugins/otel_metrics/kibana.json | 15 ++ .../plugins/otel_metrics/server/index.ts | 11 ++ .../otel_metrics/server/monitoring/metrics.ts | 19 +++ .../plugins/otel_metrics/server/plugin.ts | 28 ++++ .../server/routes/generate_otel_metrics.ts | 23 +++ .../otel_metrics/server/routes/index.ts | 9 + tsconfig.base.json | 2 + .../plugins/monitoring_collection/README.md | 137 ++++++++++++++- .../monitoring_collection/server/config.ts | 13 ++ .../monitoring_collection/server/constants.ts | 2 + .../monitoring_collection/server/lib/index.ts | 1 + .../server/lib/prometheus_exporter.ts | 73 ++++++++ .../monitoring_collection/server/plugin.ts | 102 ++++++++++- .../get_metrics_by_type.test.ts} | 4 +- .../v1/dynamic_route/get_metrics_by_type.ts} | 7 +- .../routes/api/v1/dynamic_route/index.ts | 7 + .../server/routes/api/v1/index.ts | 8 + .../api/v1/prometheus/get_metrics.test.ts | 32 ++++ .../routes/api/v1/prometheus/get_metrics.ts | 33 ++++ .../server/routes/api/v1/prometheus/index.ts | 7 + .../server/routes/index.ts | 2 +- x-pack/test/api_integration/apis/index.ts | 1 + .../apis/monitoring_collection/index.ts | 14 ++ .../apis/monitoring_collection/prometheus.ts | 24 +++ x-pack/test/api_integration/config.ts | 1 + yarn.lock | 158 +++++++++++++++++- 29 files changed, 727 insertions(+), 17 deletions(-) create mode 100644 test/common/fixtures/plugins/otel_metrics/kibana.json create mode 100644 test/common/fixtures/plugins/otel_metrics/server/index.ts create mode 100644 test/common/fixtures/plugins/otel_metrics/server/monitoring/metrics.ts create mode 100644 test/common/fixtures/plugins/otel_metrics/server/plugin.ts create mode 100644 test/common/fixtures/plugins/otel_metrics/server/routes/generate_otel_metrics.ts create mode 100644 test/common/fixtures/plugins/otel_metrics/server/routes/index.ts create mode 100644 x-pack/plugins/monitoring_collection/server/lib/prometheus_exporter.ts rename x-pack/plugins/monitoring_collection/server/routes/{dynamic_route.test.ts => api/v1/dynamic_route/get_metrics_by_type.test.ts} (97%) rename x-pack/plugins/monitoring_collection/server/routes/{dynamic_route.ts => api/v1/dynamic_route/get_metrics_by_type.ts} (86%) create mode 100644 x-pack/plugins/monitoring_collection/server/routes/api/v1/dynamic_route/index.ts create mode 100644 x-pack/plugins/monitoring_collection/server/routes/api/v1/index.ts create mode 100644 x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.test.ts create mode 100644 x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.ts create mode 100644 x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/index.ts create mode 100644 x-pack/test/api_integration/apis/monitoring_collection/index.ts create mode 100644 x-pack/test/api_integration/apis/monitoring_collection/prometheus.ts diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 793805005de8b..421a239e3b0df 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -116,6 +116,7 @@ /x-pack/plugins/monitoring/ @elastic/infra-monitoring-ui /x-pack/test/functional/apps/monitoring @elastic/infra-monitoring-ui /x-pack/test/api_integration/apis/monitoring @elastic/infra-monitoring-ui +/x-pack/test/api_integration/apis/monitoring_collection @elastic/infra-monitoring-ui # Fleet /fleet_packages.json @elastic/fleet diff --git a/package.json b/package.json index b56a4d1e803aa..a0cab1288d620 100644 --- a/package.json +++ b/package.json @@ -120,6 +120,7 @@ "@emotion/css": "^11.9.0", "@emotion/react": "^11.9.0", "@emotion/serialize": "^1.0.3", + "@grpc/grpc-js": "^1.6.7", "@hapi/accept": "^5.0.2", "@hapi/boom": "^9.1.4", "@hapi/cookie": "^11.0.2", @@ -284,6 +285,13 @@ "@mapbox/mapbox-gl-draw": "1.3.0", "@mapbox/mapbox-gl-rtl-text": "0.2.3", "@mapbox/vector-tile": "1.3.1", + "@opentelemetry/api": "^1.1.0", + "@opentelemetry/api-metrics": "^0.30.0", + "@opentelemetry/exporter-metrics-otlp-grpc": "^0.30.0", + "@opentelemetry/exporter-prometheus": "^0.30.0", + "@opentelemetry/resources": "^1.4.0", + "@opentelemetry/sdk-metrics-base": "^0.30.0", + "@opentelemetry/semantic-conventions": "^1.4.0", "@reduxjs/toolkit": "^1.6.1", "@slack/webhook": "^5.0.4", "@turf/along": "6.0.1", diff --git a/test/common/config.js b/test/common/config.js index 5079d32909ff5..f69afd4e789b5 100644 --- a/test/common/config.js +++ b/test/common/config.js @@ -51,6 +51,8 @@ export default function () { `--server.maxPayload=1679958`, // newsfeed mock service `--plugin-path=${path.join(__dirname, 'fixtures', 'plugins', 'newsfeed')}`, + // otel mock service + `--plugin-path=${path.join(__dirname, 'fixtures', 'plugins', 'otel_metrics')}`, `--newsfeed.service.urlRoot=${servers.kibana.protocol}://${servers.kibana.hostname}:${servers.kibana.port}`, `--newsfeed.service.pathTemplate=/api/_newsfeed-FTS-external-service-simulators/kibana/v{VERSION}.json`, // code coverage reporting plugin diff --git a/test/common/fixtures/plugins/otel_metrics/kibana.json b/test/common/fixtures/plugins/otel_metrics/kibana.json new file mode 100644 index 0000000000000..f9cc773c1fe0a --- /dev/null +++ b/test/common/fixtures/plugins/otel_metrics/kibana.json @@ -0,0 +1,15 @@ +{ + "id": "openTelemetryInstrumentedPlugin", + "owner": { + "name": "Stack Monitoring", + "githubTeam": "stack-monitoring-ui" + }, + "version": "1.0.0", + "kibanaVersion": "kibana", + "requiredPlugins": [ + "monitoringCollection" + ], + "optionalPlugins": [], + "server": true, + "ui": false +} \ No newline at end of file diff --git a/test/common/fixtures/plugins/otel_metrics/server/index.ts b/test/common/fixtures/plugins/otel_metrics/server/index.ts new file mode 100644 index 0000000000000..eb5f587592cae --- /dev/null +++ b/test/common/fixtures/plugins/otel_metrics/server/index.ts @@ -0,0 +1,11 @@ +/* + * 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 { OpenTelemetryUsageTest } from './plugin'; + +export const plugin = () => new OpenTelemetryUsageTest(); diff --git a/test/common/fixtures/plugins/otel_metrics/server/monitoring/metrics.ts b/test/common/fixtures/plugins/otel_metrics/server/monitoring/metrics.ts new file mode 100644 index 0000000000000..044cd7bee5441 --- /dev/null +++ b/test/common/fixtures/plugins/otel_metrics/server/monitoring/metrics.ts @@ -0,0 +1,19 @@ +/* + * 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 { Counter, Meter } from '@opentelemetry/api-metrics'; + +export class Metrics { + requestCounter: Counter; + + constructor(meter: Meter) { + this.requestCounter = meter.createCounter('request_count', { + description: 'Counts total number of requests', + }); + } +} diff --git a/test/common/fixtures/plugins/otel_metrics/server/plugin.ts b/test/common/fixtures/plugins/otel_metrics/server/plugin.ts new file mode 100644 index 0000000000000..65dec472b94f9 --- /dev/null +++ b/test/common/fixtures/plugins/otel_metrics/server/plugin.ts @@ -0,0 +1,28 @@ +/* + * 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 { CoreSetup, Plugin } from '@kbn/core/server'; +import { metrics } from '@opentelemetry/api-metrics'; +import { generateOtelMetrics } from './routes'; +import { Metrics } from './monitoring/metrics'; + +export class OpenTelemetryUsageTest implements Plugin { + private metrics: Metrics; + + constructor() { + this.metrics = new Metrics(metrics.getMeter('dummyMetric')); + } + + public setup(core: CoreSetup) { + const router = core.http.createRouter(); + generateOtelMetrics(router, this.metrics); + } + + public start() {} + public stop() {} +} diff --git a/test/common/fixtures/plugins/otel_metrics/server/routes/generate_otel_metrics.ts b/test/common/fixtures/plugins/otel_metrics/server/routes/generate_otel_metrics.ts new file mode 100644 index 0000000000000..6809059ca1472 --- /dev/null +++ b/test/common/fixtures/plugins/otel_metrics/server/routes/generate_otel_metrics.ts @@ -0,0 +1,23 @@ +/* + * 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 { IKibanaResponse, IRouter } from '@kbn/core/server'; +import { Metrics } from '../monitoring/metrics'; + +export const generateOtelMetrics = (router: IRouter, metrics: Metrics) => { + router.post( + { + path: '/api/generate_otel_metrics', + validate: {}, + }, + async function (_context, _req, res): Promise> { + metrics.requestCounter.add(1); + return res.ok({}); + } + ); +}; diff --git a/test/common/fixtures/plugins/otel_metrics/server/routes/index.ts b/test/common/fixtures/plugins/otel_metrics/server/routes/index.ts new file mode 100644 index 0000000000000..49ac53bcf5412 --- /dev/null +++ b/test/common/fixtures/plugins/otel_metrics/server/routes/index.ts @@ -0,0 +1,9 @@ +/* + * 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. + */ + +export * from './generate_otel_metrics'; diff --git a/tsconfig.base.json b/tsconfig.base.json index 9946503830c70..c4a2d579dee9a 100644 --- a/tsconfig.base.json +++ b/tsconfig.base.json @@ -201,6 +201,8 @@ "@kbn/coverage-fixtures-plugin/*": ["test/common/fixtures/plugins/coverage/*"], "@kbn/newsfeed-fixtures-plugin": ["test/common/fixtures/plugins/newsfeed"], "@kbn/newsfeed-fixtures-plugin/*": ["test/common/fixtures/plugins/newsfeed/*"], + "@kbn/open-telemetry-instrumented-plugin": ["test/common/fixtures/plugins/otel_metrics"], + "@kbn/open-telemetry-instrumented-plugin/*": ["test/common/fixtures/plugins/otel_metrics/*"], "@kbn/kbn-tp-run-pipeline-plugin": ["test/interpreter_functional/plugins/kbn_tp_run_pipeline"], "@kbn/kbn-tp-run-pipeline-plugin/*": ["test/interpreter_functional/plugins/kbn_tp_run_pipeline/*"], "@kbn/app-link-test-plugin": ["test/plugin_functional/plugins/app_link_test"], diff --git a/x-pack/plugins/monitoring_collection/README.md b/x-pack/plugins/monitoring_collection/README.md index 1f2d2984af886..1f9cadf40ee7b 100644 --- a/x-pack/plugins/monitoring_collection/README.md +++ b/x-pack/plugins/monitoring_collection/README.md @@ -2,4 +2,139 @@ ## Plugin -This plugin allows for other plugins to add data to Kibana stack monitoring documents. \ No newline at end of file +This plugin allows for other plugins to add data to Kibana stack monitoring documents. + +## OpenTelemetry Metrics + +### Enable Prometheus endpoint with Elastic Agent Prometheus input + +1. Start [local setup with fleet](../fleet/README.md#running-fleet-server-locally-in-a-container) or a cloud cluster +2. Start Kibana +3. Set up a new agent policy and enroll a new agent in your local machine +4. Install the Prometheus Metrics package + 1. Set **Hosts** with `localhost:5601` + 2. Set **Metrics Path** with `/(BASEPATH)/api/monitoring_collection/v1/prometheus` + 3. Remove the values from **Bearer Token File** and **SSL Certificate Authorities** + 4. Set **Username** and **Password** with `elastic` and `changeme` +5. Add the following configuration to `kibana.dev.yml` + + ```yml + # Enable the prometheus exporter + monitoring_collection.opentelemetry.metrics: + prometheus.enabled: true + ``` + +### Enable OpenTelemetry Metrics API exported as OpenTelemetry Protocol over GRPC + +1. Start [local setup with fleet](../fleet/README.md#running-fleet-server-locally-in-a-container) or a cloud cluster +2. Start Kibana +3. Set up a new agent policy and enroll a new agent in your local machine +4. Install Elastic APM package listening on `localhost:8200` without authentication +5. Add the following configuration to `kibana.dev.yml` + + ```yml + # Enable the OTLP exporter + monitoring_collection.opentelemetry.metrics: + otlp.url: "http://127.0.0.1:8200" + ``` + +You can also provide headers for OTLP endpoints that require authentication: + +```yml +# Enable the OTLP exporter to an authenticated APM endpoint +monitoring_collection.opentelemetry.metrics: + otlp: + url: "https://DEPLOYMENT.apm.REGION.PROVIDER.elastic-cloud.com" + headers: + Authorization: "Bearer SECRET_TOKEN" +``` + +Alternatively, OTLP Exporter can be configured using environment variables `OTEL_EXPORTER_OTLP_ENDPOINT`, `OTEL_EXPORTER_OTLP_METRICS_ENDPOINT` and `OTEL_EXPORTER_OTLP_METRICS_HEADERS`. [See OTLP Exporter docs](https://opentelemetry.io/docs/reference/specification/protocol/exporter/) for details. + +It's possible to configure logging for the OTLP integration. If not informed, the default will be `info` + +```yml +monitoring_collection.opentelemetry.metrics: + logLevel: warn | info | debug | warn | none | verbose | all +``` + +For connection-level debug information you can set these variables: + +```bash +export GRPC_NODE_TRACE="xds_client,xds_resolver,cds_balancer,eds_balancer,priority,weighted_target,round_robin,resolving_load_balancer,subchannel,keepalive,dns_resolver,fault_injection,http_filter,csds" +export GRPC_NODE_VERBOSITY=DEBUG +``` + +See the [grpc-node docs](https://github.com/grpc/grpc-node/blob/master/doc/environment_variables.md) for details and other settings. + +### Example of how to instrument the code + +* First, we need to define what metrics we want to instrument with OpenTelemetry + + ```ts + import { Counter, Meter } from '@opentelemetry/api-metrics'; + + export class FooApiMeters { + requestCount: Counter; + + constructor(meter: Meter) { + this.requestCount = meter.createCounter('request_count', { + description: 'Counts total number of requests', + }); + } + } + ``` + + In this example we're using a `Counter` metric, but [OpenTelemetry SDK](https://open-telemetry.github.io/opentelemetry-js/interfaces/_opentelemetry_api_metrics.Meter.html) provides there are other options to record metrics + +* Initialize meter in the plugin setup and pass it to the relevant components that will be instrumented. In this case, we want to instrument `FooApi` routes. + + ```ts + import { IRouter } from '@kbn/core/server'; + import { FooApiMeters } from './foo_api_meters'; + import { metrics } from '@opentelemetry/api-metrics'; + + export class FooApiPlugin implements Plugin { + private metrics: Metrics; + private libs: { router: IRouter, metrics: FooApiMeters}; + + constructor() { + this.metrics = new Metrics(metrics.getMeter('kibana.fooApi')); + } + + public setup(core: CoreSetup) { + const router = core.http.createRouter(); + + this.libs = { + router, + metrics: this.metrics + } + + initMetricsAPIRoute(this.libs); + } + } + ``` + + `monitoring_collection` plugins has to be initialized before the plugin that will be instrumented. If for some reason the instrumentation doesn't record any metrics, make sure `monitoring_collection` is included in the list of `requiredPlugins`. e.g: + + ```json + "requiredPlugins": [ + "monitoringCollection" + ], + ``` + +* Lastly we can use the `metrics` object to instrument the code + + ```ts + export const initMetricsAPIRoute = (libs: { router: IRouter, metrics: FooApiMeters}) => { + router.get( + { + path: '/api/foo', + validate: {}, + }, + async function (_context, _req, res) { + metrics.requestCount.add(1); + return res.ok({}); + } + ); + ``` \ No newline at end of file diff --git a/x-pack/plugins/monitoring_collection/server/config.ts b/x-pack/plugins/monitoring_collection/server/config.ts index 275d2f31e505d..5eda950ebe7f1 100644 --- a/x-pack/plugins/monitoring_collection/server/config.ts +++ b/x-pack/plugins/monitoring_collection/server/config.ts @@ -9,6 +9,19 @@ import { schema, TypeOf } from '@kbn/config-schema'; export const configSchema = schema.object({ enabled: schema.boolean({ defaultValue: true }), + opentelemetry: schema.object({ + metrics: schema.object({ + otlp: schema.object({ + url: schema.maybe(schema.string()), + headers: schema.maybe(schema.recordOf(schema.string(), schema.string())), + exportIntervalMillis: schema.number({ defaultValue: 10000 }), + logLevel: schema.string({ defaultValue: 'info' }), + }), + prometheus: schema.object({ + enabled: schema.boolean({ defaultValue: false }), + }), + }), + }), }); export type MonitoringCollectionConfig = ReturnType; diff --git a/x-pack/plugins/monitoring_collection/server/constants.ts b/x-pack/plugins/monitoring_collection/server/constants.ts index 86231dec6c6c2..92b43a9d80e48 100644 --- a/x-pack/plugins/monitoring_collection/server/constants.ts +++ b/x-pack/plugins/monitoring_collection/server/constants.ts @@ -5,3 +5,5 @@ * 2.0. */ export const TYPE_ALLOWLIST = ['node_rules', 'cluster_rules', 'node_actions', 'cluster_actions']; + +export const MONITORING_COLLECTION_BASE_PATH = '/api/monitoring_collection'; diff --git a/x-pack/plugins/monitoring_collection/server/lib/index.ts b/x-pack/plugins/monitoring_collection/server/lib/index.ts index 0c39a62ab359c..34c1fce763bdc 100644 --- a/x-pack/plugins/monitoring_collection/server/lib/index.ts +++ b/x-pack/plugins/monitoring_collection/server/lib/index.ts @@ -7,3 +7,4 @@ export { getKibanaStats } from './get_kibana_stats'; export { getESClusterUuid } from './get_es_cluster_uuid'; +export { PrometheusExporter } from './prometheus_exporter'; diff --git a/x-pack/plugins/monitoring_collection/server/lib/prometheus_exporter.ts b/x-pack/plugins/monitoring_collection/server/lib/prometheus_exporter.ts new file mode 100644 index 0000000000000..fc4359609bf34 --- /dev/null +++ b/x-pack/plugins/monitoring_collection/server/lib/prometheus_exporter.ts @@ -0,0 +1,73 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { AggregationTemporality, MetricReader } from '@opentelemetry/sdk-metrics-base'; +import { + PrometheusExporter as OpenTelemetryPrometheusExporter, + ExporterConfig, + PrometheusSerializer, +} from '@opentelemetry/exporter-prometheus'; +import { KibanaResponseFactory } from '@kbn/core/server'; + +export class PrometheusExporter extends MetricReader { + private readonly prefix?: string; + private readonly appendTimestamp: boolean; + private serializer: PrometheusSerializer; + + constructor(config: ExporterConfig = {}) { + super(); + this.prefix = config.prefix || OpenTelemetryPrometheusExporter.DEFAULT_OPTIONS.prefix; + this.appendTimestamp = + typeof config.appendTimestamp === 'boolean' + ? config.appendTimestamp + : OpenTelemetryPrometheusExporter.DEFAULT_OPTIONS.appendTimestamp; + + this.serializer = new PrometheusSerializer(this.prefix, this.appendTimestamp); + } + + selectAggregationTemporality(): AggregationTemporality { + return AggregationTemporality.CUMULATIVE; + } + + protected onForceFlush(): Promise { + return Promise.resolve(undefined); + } + + protected onShutdown(): Promise { + return Promise.resolve(undefined); + } + + /** + * Responds to incoming message with current state of all metrics. + */ + public async exportMetrics(res: KibanaResponseFactory) { + try { + const collectionResult = await this.collect(); + const { resourceMetrics, errors } = collectionResult; + if (errors.length) { + return res.customError({ + statusCode: 500, + body: `PrometheusExporter: Metrics collection errors ${errors}`, + }); + } + const result = this.serializer.serialize(resourceMetrics); + if (result === '') { + return res.noContent(); + } + return res.ok({ + body: result, + }); + } catch (error) { + return res.customError({ + statusCode: 500, + body: { + message: `PrometheusExporter: Failed to export metrics ${error}`, + }, + }); + } + } +} diff --git a/x-pack/plugins/monitoring_collection/server/plugin.ts b/x-pack/plugins/monitoring_collection/server/plugin.ts index e1c3a5064a579..1c30a8439cf3c 100644 --- a/x-pack/plugins/monitoring_collection/server/plugin.ts +++ b/x-pack/plugins/monitoring_collection/server/plugin.ts @@ -6,10 +6,24 @@ */ import { JsonObject } from '@kbn/utility-types'; -import { CoreSetup, Plugin, PluginInitializerContext, Logger } from '@kbn/core/server'; +import { + CoreSetup, + Plugin, + PluginInitializerContext, + Logger, + ServiceStatus, +} from '@kbn/core/server'; import { MakeSchemaFrom } from '@kbn/usage-collection-plugin/server'; -import { ServiceStatus } from '@kbn/core/server'; -import { registerDynamicRoute } from './routes'; +import { metrics } from '@opentelemetry/api-metrics'; +import { OTLPMetricExporter } from '@opentelemetry/exporter-metrics-otlp-grpc'; +import { MeterProvider, PeriodicExportingMetricReader } from '@opentelemetry/sdk-metrics-base'; +import { Resource } from '@opentelemetry/resources'; +import { diag, DiagLogger, DiagLogLevel } from '@opentelemetry/api'; +import { SemanticResourceAttributes } from '@opentelemetry/semantic-conventions'; +import * as grpc from '@grpc/grpc-js'; +import { PrometheusExporter } from './lib/prometheus_exporter'; +import { MonitoringCollectionConfig } from './config'; +import { registerDynamicRoute, registerV1PrometheusRoute, PROMETHEUS_PATH } from './routes'; import { TYPE_ALLOWLIST } from './constants'; export interface MonitoringCollectionSetup { @@ -27,12 +41,25 @@ export interface Metric { export class MonitoringCollectionPlugin implements Plugin { private readonly initializerContext: PluginInitializerContext; private readonly logger: Logger; + private readonly config: MonitoringCollectionConfig; + private readonly otlpLogger: DiagLogger; private metrics: Record> = {}; - constructor(initializerContext: PluginInitializerContext) { + private prometheusExporter?: PrometheusExporter; + + constructor(initializerContext: PluginInitializerContext) { this.initializerContext = initializerContext; this.logger = initializerContext.logger.get(); + this.config = initializerContext.config.get(); + + this.otlpLogger = { + debug: (message) => this.logger.debug(message), + error: (message) => this.logger.error(message), + info: (message) => this.logger.info(message), + warn: (message) => this.logger.warn(message), + verbose: (message) => this.logger.trace(message), + }; } async getMetric(type: string) { @@ -46,19 +73,28 @@ export class MonitoringCollectionPlugin implements Plugin; core.status.overall$.subscribe((newStatus) => { status = newStatus; }); + if (this.prometheusExporter) { + registerV1PrometheusRoute({ router, prometheusExporter: this.prometheusExporter }); + } + registerDynamicRoute({ router, config: { kibanaIndex, - kibanaVersion: this.initializerContext.env.packageInfo.version, - server: core.http.getServerInfo(), - uuid: this.initializerContext.env.instanceUuid, + kibanaVersion, + server, + uuid, }, getStatus: () => status, getMetric: async (type: string) => { @@ -85,6 +121,58 @@ export class MonitoringCollectionPlugin implements Plugin { jest.resetAllMocks(); }); -jest.mock('../lib', () => ({ +jest.mock('../../../../lib', () => ({ getESClusterUuid: () => 'clusterA', getKibanaStats: () => ({ name: 'myKibana' }), })); diff --git a/x-pack/plugins/monitoring_collection/server/routes/dynamic_route.ts b/x-pack/plugins/monitoring_collection/server/routes/api/v1/dynamic_route/get_metrics_by_type.ts similarity index 86% rename from x-pack/plugins/monitoring_collection/server/routes/dynamic_route.ts rename to x-pack/plugins/monitoring_collection/server/routes/api/v1/dynamic_route/get_metrics_by_type.ts index 944037dd17a7b..4d18eeb6ec922 100644 --- a/x-pack/plugins/monitoring_collection/server/routes/dynamic_route.ts +++ b/x-pack/plugins/monitoring_collection/server/routes/api/v1/dynamic_route/get_metrics_by_type.ts @@ -7,8 +7,9 @@ import { JsonObject } from '@kbn/utility-types'; import { schema } from '@kbn/config-schema'; import { IRouter, ServiceStatus } from '@kbn/core/server'; -import { getESClusterUuid, getKibanaStats } from '../lib'; -import { MetricResult } from '../plugin'; +import { getESClusterUuid, getKibanaStats } from '../../../../lib'; +import { MetricResult } from '../../../../plugin'; +import { MONITORING_COLLECTION_BASE_PATH } from '../../../../constants'; export function registerDynamicRoute({ router, @@ -34,7 +35,7 @@ export function registerDynamicRoute({ }) { router.get( { - path: `/api/monitoring_collection/{type}`, + path: `${MONITORING_COLLECTION_BASE_PATH}/{type}`, options: { authRequired: true, tags: ['api'], // ensures that unauthenticated calls receive a 401 rather than a 302 redirect to login page diff --git a/x-pack/plugins/monitoring_collection/server/routes/api/v1/dynamic_route/index.ts b/x-pack/plugins/monitoring_collection/server/routes/api/v1/dynamic_route/index.ts new file mode 100644 index 0000000000000..973d525b9a77b --- /dev/null +++ b/x-pack/plugins/monitoring_collection/server/routes/api/v1/dynamic_route/index.ts @@ -0,0 +1,7 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +export * from './get_metrics_by_type'; diff --git a/x-pack/plugins/monitoring_collection/server/routes/api/v1/index.ts b/x-pack/plugins/monitoring_collection/server/routes/api/v1/index.ts new file mode 100644 index 0000000000000..e5a70f3f79abc --- /dev/null +++ b/x-pack/plugins/monitoring_collection/server/routes/api/v1/index.ts @@ -0,0 +1,8 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +export { registerDynamicRoute } from './dynamic_route'; +export { registerV1PrometheusRoute, PROMETHEUS_PATH } from './prometheus'; diff --git a/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.test.ts b/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.test.ts new file mode 100644 index 0000000000000..b136d982992c4 --- /dev/null +++ b/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.test.ts @@ -0,0 +1,32 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { RequestHandlerContext } from '@kbn/core/server'; +import { httpServerMock, httpServiceMock } from '@kbn/core/server/mocks'; +import { registerV1PrometheusRoute } from '.'; +import { PrometheusExporter } from '../../../../lib'; + +describe('Prometheus route', () => { + it('forwards the request to the prometheus exporter', async () => { + const router = httpServiceMock.createRouter(); + const prometheusExporter = { + exportMetrics: jest.fn(), + } as Partial as PrometheusExporter; + + registerV1PrometheusRoute({ router, prometheusExporter }); + + const [, handler] = router.get.mock.calls[0]; + + const context = {} as jest.Mocked; + const req = httpServerMock.createKibanaRequest(); + const factory = httpServerMock.createResponseFactory(); + + await handler(context, req, factory); + + expect(prometheusExporter.exportMetrics).toHaveBeenCalledWith(factory); + }); +}); diff --git a/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.ts b/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.ts new file mode 100644 index 0000000000000..6977be155a4fb --- /dev/null +++ b/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/get_metrics.ts @@ -0,0 +1,33 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { IRouter } from '@kbn/core/server'; +import { MONITORING_COLLECTION_BASE_PATH } from '../../../../constants'; +import { PrometheusExporter } from '../../../../lib'; + +export const PROMETHEUS_PATH = `${MONITORING_COLLECTION_BASE_PATH}/v1/prometheus`; +export function registerV1PrometheusRoute({ + router, + prometheusExporter, +}: { + router: IRouter; + prometheusExporter: PrometheusExporter; +}) { + router.get( + { + path: PROMETHEUS_PATH, + options: { + authRequired: true, + tags: ['api'], // ensures that unauthenticated calls receive a 401 rather than a 302 redirect to login page + }, + validate: {}, + }, + async (_context, _req, res) => { + return prometheusExporter.exportMetrics(res); + } + ); +} diff --git a/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/index.ts b/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/index.ts new file mode 100644 index 0000000000000..5b99f51c94511 --- /dev/null +++ b/x-pack/plugins/monitoring_collection/server/routes/api/v1/prometheus/index.ts @@ -0,0 +1,7 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +export * from './get_metrics'; diff --git a/x-pack/plugins/monitoring_collection/server/routes/index.ts b/x-pack/plugins/monitoring_collection/server/routes/index.ts index eb96ce19f764e..29cd177990593 100644 --- a/x-pack/plugins/monitoring_collection/server/routes/index.ts +++ b/x-pack/plugins/monitoring_collection/server/routes/index.ts @@ -5,4 +5,4 @@ * 2.0. */ -export { registerDynamicRoute } from './dynamic_route'; +export { registerV1PrometheusRoute, PROMETHEUS_PATH, registerDynamicRoute } from './api/v1'; diff --git a/x-pack/test/api_integration/apis/index.ts b/x-pack/test/api_integration/apis/index.ts index 6bec2ebe80a13..46b10af2a52b3 100644 --- a/x-pack/test/api_integration/apis/index.ts +++ b/x-pack/test/api_integration/apis/index.ts @@ -36,5 +36,6 @@ export default function ({ loadTestFile }: FtrProviderContext) { loadTestFile(require.resolve('./watcher')); loadTestFile(require.resolve('./logs_ui')); loadTestFile(require.resolve('./osquery')); + loadTestFile(require.resolve('./monitoring_collection')); }); } diff --git a/x-pack/test/api_integration/apis/monitoring_collection/index.ts b/x-pack/test/api_integration/apis/monitoring_collection/index.ts new file mode 100644 index 0000000000000..e89bd44963c03 --- /dev/null +++ b/x-pack/test/api_integration/apis/monitoring_collection/index.ts @@ -0,0 +1,14 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { FtrProviderContext } from '../../ftr_provider_context'; + +export default function ({ loadTestFile }: FtrProviderContext) { + describe('Monitoring Collection', function taskManagerSuite() { + loadTestFile(require.resolve('./prometheus')); + }); +} diff --git a/x-pack/test/api_integration/apis/monitoring_collection/prometheus.ts b/x-pack/test/api_integration/apis/monitoring_collection/prometheus.ts new file mode 100644 index 0000000000000..0ac13dda92cb5 --- /dev/null +++ b/x-pack/test/api_integration/apis/monitoring_collection/prometheus.ts @@ -0,0 +1,24 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import expect from '@kbn/expect'; +import { FtrProviderContext } from '../../ftr_provider_context'; + +export default function ({ getService }: FtrProviderContext) { + const supertest = getService('supertest'); + + describe('Prometheus endpoint', () => { + it('returns prometheus scraped metrics', async () => { + await supertest.post('/api/generate_otel_metrics').set('kbn-xsrf', 'foo').expect(200); + const response = await supertest.get('/api/monitoring_collection/v1/prometheus').expect(200); + + expect(response.text.replace(/\s+/g, ' ')).to.match( + /^# HELP request_count_total Counts total number of requests # TYPE request_count_total counter request_count_total [0-9]/ + ); + }); + }); +} diff --git a/x-pack/test/api_integration/config.ts b/x-pack/test/api_integration/config.ts index 8cc5fb6f57d42..ca3795e812ee2 100644 --- a/x-pack/test/api_integration/config.ts +++ b/x-pack/test/api_integration/config.ts @@ -37,6 +37,7 @@ export async function getApiIntegrationConfig({ readConfigFile }: FtrConfigProvi '--xpack.ruleRegistry.write.cache.enabled=false', '--xpack.uptime.service.password=test', '--xpack.uptime.service.username=localKibanaIntegrationTestsUser', + '--monitoring_collection.opentelemetry.metrics.prometheus.enabled=true', ], }, esTestCluster: { diff --git a/yarn.lock b/yarn.lock index 47a0d08a5b1c7..7a09d8caa1dfb 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1997,6 +1997,25 @@ resolved "https://registry.yarnpkg.com/@gar/promisify/-/promisify-1.1.3.tgz#555193ab2e3bb3b6adc3d551c9c030d9e860daf6" integrity sha512-k2Ty1JcVojjJFwrg/ThKi2ujJ7XNLYaFGNB/bWT9wGR+oSMJHMa5w+CUq6p/pVrKeNNgA7pCqEcjSnHVoqJQFw== +"@grpc/grpc-js@^1.5.9", "@grpc/grpc-js@^1.6.7": + version "1.6.7" + resolved "https://registry.yarnpkg.com/@grpc/grpc-js/-/grpc-js-1.6.7.tgz#4c4fa998ff719fe859ac19fe977fdef097bb99aa" + integrity sha512-eBM03pu9hd3VqDQG+kHahiG1x80RGkkqqRb1Pchcwqej/KkAH95gAvKs6laqaHCycYaPK+TKuNQnOz9UXYA8qw== + dependencies: + "@grpc/proto-loader" "^0.6.4" + "@types/node" ">=12.12.47" + +"@grpc/proto-loader@^0.6.4", "@grpc/proto-loader@^0.6.9": + version "0.6.13" + resolved "https://registry.yarnpkg.com/@grpc/proto-loader/-/proto-loader-0.6.13.tgz#008f989b72a40c60c96cd4088522f09b05ac66bc" + integrity sha512-FjxPYDRTn6Ec3V0arm1FtSpmP6V50wuph2yILpyvTKzjc76oDdoihXqM1DzOW5ubvCC8GivfCnNtfaRE8myJ7g== + dependencies: + "@types/long" "^4.0.1" + lodash.camelcase "^4.3.0" + long "^4.0.0" + protobufjs "^6.11.3" + yargs "^16.2.0" + "@gulp-sourcemaps/identity-map@1.X": version "1.0.2" resolved "https://registry.yarnpkg.com/@gulp-sourcemaps/identity-map/-/identity-map-1.0.2.tgz#1e6fe5d8027b1f285dc0d31762f566bccd73d5a9" @@ -4431,11 +4450,120 @@ "@mattiasbuelens/web-streams-adapter" "~0.1.0" web-streams-polyfill "~3.0.3" -"@opentelemetry/api@^1.1.0": +"@opentelemetry/api-metrics@0.30.0", "@opentelemetry/api-metrics@^0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/api-metrics/-/api-metrics-0.30.0.tgz#b5defd10756e81d1c7ce8669ff8a8d2465ba0be8" + integrity sha512-jSb7iiYPY+DSUKIyzfGt0a5K1QGzWY5fSWtUB8Alfi27NhQGHBeuYYC5n9MaBP/HNWw5GpEIhXGEYCF9Pf8IEg== + dependencies: + "@opentelemetry/api" "^1.0.0" + +"@opentelemetry/api@^1.0.0", "@opentelemetry/api@^1.1.0": version "1.1.0" resolved "https://registry.yarnpkg.com/@opentelemetry/api/-/api-1.1.0.tgz#563539048255bbe1a5f4f586a4a10a1bb737f44a" integrity sha512-hf+3bwuBwtXsugA2ULBc95qxrOqP2pOekLz34BJhcAKawt94vfeNyUKpYc0lZQ/3sCP6LqRa7UAdHA7i5UODzQ== +"@opentelemetry/core@1.4.0": + version "1.4.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/core/-/core-1.4.0.tgz#26839ab9e36583a174273a1e1c5b33336c163725" + integrity sha512-faq50VFEdyC7ICAOlhSi+yYZ+peznnGjTJToha9R63i9fVopzpKrkZt7AIdXUmz2+L2OqXrcJs7EIdN/oDyr5w== + dependencies: + "@opentelemetry/semantic-conventions" "1.4.0" + +"@opentelemetry/exporter-metrics-otlp-grpc@^0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/exporter-metrics-otlp-grpc/-/exporter-metrics-otlp-grpc-0.30.0.tgz#4117d07b94302ef407dc7625a1b599de308c5476" + integrity sha512-02WEAA3X7A6qveCYISr6mvg8eKl9NeNdZytQiAexzAIItW/ncN3mxmbuf8VVZHNPBe6osisSzxhPpFH3G6Gh+w== + dependencies: + "@grpc/grpc-js" "^1.5.9" + "@grpc/proto-loader" "^0.6.9" + "@opentelemetry/core" "1.4.0" + "@opentelemetry/exporter-metrics-otlp-http" "0.30.0" + "@opentelemetry/otlp-grpc-exporter-base" "0.30.0" + "@opentelemetry/otlp-transformer" "0.30.0" + "@opentelemetry/resources" "1.4.0" + "@opentelemetry/sdk-metrics-base" "0.30.0" + +"@opentelemetry/exporter-metrics-otlp-http@0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/exporter-metrics-otlp-http/-/exporter-metrics-otlp-http-0.30.0.tgz#9d87e4c3e796e14109ac83e6d4ce5bad215c2a1e" + integrity sha512-2NFR/D9jih1TtEnEyD7oIMR47yb9Kuy5v2x+Fu19vv2gTf1HOhdA+LT4SpkxH+dUixEnDw8n11XBIa/uhNfq3Q== + dependencies: + "@opentelemetry/api-metrics" "0.30.0" + "@opentelemetry/core" "1.4.0" + "@opentelemetry/otlp-exporter-base" "0.30.0" + "@opentelemetry/otlp-transformer" "0.30.0" + "@opentelemetry/resources" "1.4.0" + "@opentelemetry/sdk-metrics-base" "0.30.0" + +"@opentelemetry/exporter-prometheus@^0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/exporter-prometheus/-/exporter-prometheus-0.30.0.tgz#f81322d3cb000170e716bc76820600d5649be538" + integrity sha512-y0SXvpzoKR+Tk/UL6F1f7vAcCzqpCDP/cTEa+Z7sX57aEG0HDXLQiLmAgK/BHqcEN5MFQMZ+MDVDsUrvpa6/Jw== + dependencies: + "@opentelemetry/api-metrics" "0.30.0" + "@opentelemetry/core" "1.4.0" + "@opentelemetry/sdk-metrics-base" "0.30.0" + +"@opentelemetry/otlp-exporter-base@0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/otlp-exporter-base/-/otlp-exporter-base-0.30.0.tgz#5f278b3529d38311dbdfc1ebcb764f5e5126e548" + integrity sha512-+dJnj2MSd3tsk+ooEw+0bF+dJs/NjGEVnCB3/FYxnUFaW9cCBbQQyt6X3YQYtYrEx4EEiTlwrW8pUpB1tsup7A== + dependencies: + "@opentelemetry/core" "1.4.0" + +"@opentelemetry/otlp-grpc-exporter-base@0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/otlp-grpc-exporter-base/-/otlp-grpc-exporter-base-0.30.0.tgz#3fa07667ddf604a028583a2a138b8b4ba8fa9bb0" + integrity sha512-86fuhZ7Z2un3L5Kd7jbH1oEn92v9DD92teErnYRXqYB/qyO61OLxaY6WxH9KOjmbs5CgCdLQ5bvED3wWDe3r7w== + dependencies: + "@grpc/grpc-js" "^1.5.9" + "@grpc/proto-loader" "^0.6.9" + "@opentelemetry/core" "1.4.0" + "@opentelemetry/otlp-exporter-base" "0.30.0" + +"@opentelemetry/otlp-transformer@0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/otlp-transformer/-/otlp-transformer-0.30.0.tgz#d81e1ae68dfb31d66cd4ca03ca965cdaa2e2b288" + integrity sha512-BTLXyBPBlCQCG4tXYZjlso4pT+gGpnTjzkFYTPYs52fO5DMWvYHlV8ST/raOIqX7wsamiH2zeqJ9W91017MtdA== + dependencies: + "@opentelemetry/api-metrics" "0.30.0" + "@opentelemetry/core" "1.4.0" + "@opentelemetry/resources" "1.4.0" + "@opentelemetry/sdk-metrics-base" "0.30.0" + "@opentelemetry/sdk-trace-base" "1.4.0" + +"@opentelemetry/resources@1.4.0", "@opentelemetry/resources@^1.4.0": + version "1.4.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/resources/-/resources-1.4.0.tgz#5e23b0d7976158861059dec17e0ee36a35a5ab85" + integrity sha512-Q3pI5+pCM+Ur7YwK9GbG89UBipwJbfmuzSPAXTw964ZHFzSrz+JAgrETC9rqsUOYdUlj/V7LbRMG5bo72xE0Xw== + dependencies: + "@opentelemetry/core" "1.4.0" + "@opentelemetry/semantic-conventions" "1.4.0" + +"@opentelemetry/sdk-metrics-base@0.30.0", "@opentelemetry/sdk-metrics-base@^0.30.0": + version "0.30.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-metrics-base/-/sdk-metrics-base-0.30.0.tgz#242d9260a89a1ac2bf1e167b3fda758f3883c769" + integrity sha512-3BDg1MYDInDyGvy+bSH8OuCX5nsue7omH6Y2eidCGTTDYRPxDmq9tsRJxnTUepoMAvWX+1sTwZ4JqTFmc1z8Mw== + dependencies: + "@opentelemetry/api-metrics" "0.30.0" + "@opentelemetry/core" "1.4.0" + "@opentelemetry/resources" "1.4.0" + lodash.merge "4.6.2" + +"@opentelemetry/sdk-trace-base@1.4.0": + version "1.4.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/sdk-trace-base/-/sdk-trace-base-1.4.0.tgz#e54d09c1258cd53d3fe726053ed1cbda9d74f023" + integrity sha512-l7EEjcOgYlKWK0hfxz4Jtkkk2DuGiqBDWmRZf7g2Is9RVneF1IgcrbYZTKGaVfBKA7lPuVtUiQ2qTv3R+dKJrw== + dependencies: + "@opentelemetry/core" "1.4.0" + "@opentelemetry/resources" "1.4.0" + "@opentelemetry/semantic-conventions" "1.4.0" + +"@opentelemetry/semantic-conventions@1.4.0", "@opentelemetry/semantic-conventions@^1.4.0": + version "1.4.0" + resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.4.0.tgz#facf2c67d6063b9918d5a5e3fdf25f3a30d547b6" + integrity sha512-Hzl8soGpmyzja9w3kiFFcYJ7n5HNETpplY6cb67KR4QPlxp4FTTresO06qXHgHDhyIInmbLJXuwARjjpsKYGuQ== + "@percy/agent@^0.28.6": version "0.28.6" resolved "https://registry.yarnpkg.com/@percy/agent/-/agent-0.28.6.tgz#b220fab6ddcf63ae4e6c343108ba6955a772ce1c" @@ -7363,6 +7491,11 @@ resolved "https://registry.yarnpkg.com/@types/long/-/long-4.0.1.tgz#459c65fa1867dafe6a8f322c4c51695663cc55e9" integrity sha512-5tXH6Bx/kNGd3MgffdmP4dy2Z+G4eaXw0SE81Tq3BNadtnMR5/ySMzX4SLEzHJzSmPNn4HIdpQsBvXMUykr58w== +"@types/long@^4.0.1": + version "4.0.2" + resolved "https://registry.yarnpkg.com/@types/long/-/long-4.0.2.tgz#b74129719fc8d11c01868010082d483b7545591a" + integrity sha512-MqTGEo5bj5t157U6fA/BiDynNkn0YknVdh48CMPkTSpFTVmvao5UQmm7uEF6xBEo7qIMAlY/JSleYaE6VOdpaA== + "@types/lru-cache@^5.1.0": version "5.1.0" resolved "https://registry.yarnpkg.com/@types/lru-cache/-/lru-cache-5.1.0.tgz#57f228f2b80c046b4a1bd5cac031f81f207f4f03" @@ -7530,7 +7663,7 @@ dependencies: "@types/node" "*" -"@types/node@*", "@types/node@12.20.24", "@types/node@16.11.41", "@types/node@>= 8", "@types/node@>=8.9.0", "@types/node@^10.1.0", "@types/node@^14.0.10", "@types/node@^14.14.31": +"@types/node@*", "@types/node@12.20.24", "@types/node@16.11.41", "@types/node@>= 8", "@types/node@>=12.12.47", "@types/node@>=13.7.0", "@types/node@>=8.9.0", "@types/node@^10.1.0", "@types/node@^14.0.10", "@types/node@^14.14.31": version "16.11.41" resolved "https://registry.yarnpkg.com/@types/node/-/node-16.11.41.tgz#88eb485b1bfdb4c224d878b7832239536aa2f813" integrity sha512-mqoYK2TnVjdkGk8qXAVGc/x9nSaTpSrFaGFm43BUH3IdoBV0nta6hYaGmdOvIMlbHJbUEVen3gvwpwovAZKNdQ== @@ -23953,6 +24086,25 @@ protobufjs@6.8.8: "@types/node" "^10.1.0" long "^4.0.0" +protobufjs@^6.11.3: + version "6.11.3" + resolved "https://registry.yarnpkg.com/protobufjs/-/protobufjs-6.11.3.tgz#637a527205a35caa4f3e2a9a4a13ddffe0e7af74" + integrity sha512-xL96WDdCZYdU7Slin569tFX712BxsxslWwAfAhCYjQKGTq7dAU91Lomy6nLLhh/dyGhk/YH4TwTSRxTzhuHyZg== + dependencies: + "@protobufjs/aspromise" "^1.1.2" + "@protobufjs/base64" "^1.1.2" + "@protobufjs/codegen" "^2.0.4" + "@protobufjs/eventemitter" "^1.1.0" + "@protobufjs/fetch" "^1.1.0" + "@protobufjs/float" "^1.0.2" + "@protobufjs/inquire" "^1.1.0" + "@protobufjs/path" "^1.1.2" + "@protobufjs/pool" "^1.1.0" + "@protobufjs/utf8" "^1.1.0" + "@types/long" "^4.0.1" + "@types/node" ">=13.7.0" + long "^4.0.0" + protocol-buffers-schema@^3.3.1: version "3.3.2" resolved "https://registry.yarnpkg.com/protocol-buffers-schema/-/protocol-buffers-schema-3.3.2.tgz#00434f608b4e8df54c59e070efeefc37fb4bb859" @@ -30903,7 +31055,7 @@ yargs-unparser@2.0.0: flat "^5.0.2" is-plain-obj "^2.1.0" -yargs@16.2.0: +yargs@16.2.0, yargs@^16.2.0: version "16.2.0" resolved "https://registry.yarnpkg.com/yargs/-/yargs-16.2.0.tgz#1c82bf0f6b6a66eafce7ef30e376f49a12477f66" integrity sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw== From e3722862ba485a99158e4ca098ce499918cc59a9 Mon Sep 17 00:00:00 2001 From: James Gowdy Date: Thu, 14 Jul 2022 13:56:18 +0100 Subject: [PATCH 020/111] [ML] Fixing start datafeed modal overflow (#136292) --- .../start_datafeed_modal.js | 2 +- .../_time_range_selector.scss | 4 -- .../time_range_selector.js | 54 ++++++++++--------- 3 files changed, 30 insertions(+), 30 deletions(-) diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/start_datafeed_modal.js b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/start_datafeed_modal.js index c5bb63b96fdd2..c4c53b00591f4 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/start_datafeed_modal.js +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/start_datafeed_modal.js @@ -143,7 +143,7 @@ export class StartDatafeedModal extends Component { modal = ( diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/_time_range_selector.scss b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/_time_range_selector.scss index 65a72a1d4a48d..faa69e90ecab5 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/_time_range_selector.scss +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/_time_range_selector.scss @@ -1,9 +1,6 @@ // stylelint-disable selector-no-qualifying-type // SASSTODO: Looks like this could use a rewrite. Needs selectors .time-range-selector { - .time-range-section-container { - display: flex; - } .time-range-section-title { font-weight: bold; margin-bottom: $euiSizeS; @@ -46,7 +43,6 @@ } .body { display: block; - height: 315px; } } & > li.has-body.active { diff --git a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/time_range_selector.js b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/time_range_selector.js index 4300a918b948f..05e8e60abc4fb 100644 --- a/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/time_range_selector.js +++ b/x-pack/plugins/ml/public/application/jobs/jobs_list/components/start_datafeed_modal/time_range_selector/time_range_selector.js @@ -9,7 +9,7 @@ import './_time_range_selector.scss'; import PropTypes from 'prop-types'; import React, { Component, useState, useEffect } from 'react'; -import { EuiDatePicker, EuiFieldText, EuiSpacer } from '@elastic/eui'; +import { EuiDatePicker, EuiFieldText, EuiSpacer, EuiFlexGroup, EuiFlexItem } from '@elastic/eui'; import moment from 'moment'; import { i18n } from '@kbn/i18n'; @@ -181,30 +181,34 @@ export class TimeRangeSelector extends Component { ) : null} -
- - } - items={startItems} - switchState={this.state.startTab} - switchFunc={this.setStartTab} - /> - - } - items={endItems} - switchState={this.state.endTab} - switchFunc={this.setEndTab} - /> -
+ + + + } + items={startItems} + switchState={this.state.startTab} + switchFunc={this.setStartTab} + /> + + + + } + items={endItems} + switchState={this.state.endTab} + switchFunc={this.setEndTab} + /> + + ); } From 9a4eca0a148ddbddadb8d585b06472a46065a583 Mon Sep 17 00:00:00 2001 From: Matthew Kime Date: Thu, 14 Jul 2022 08:01:33 -0500 Subject: [PATCH 021/111] [data views] Enforce uniqueness by name instead of index pattern (#136071) * data view uniqueness by name --- .github/CODEOWNERS | 1 + .../data_view_editor_flyout_content.tsx | 14 ++--- .../components/form_fields/name_field.tsx | 55 +++++++++++++++++-- .../form_fields/timestamp_field.tsx | 8 +-- .../components/form_fields/title_field.tsx | 28 +--------- .../public/components/form_schema.ts | 1 + .../common/data_views/data_views.ts | 14 +++-- src/plugins/data_views/common/utils.ts | 18 +++--- .../rest_api_routes/create_data_view.ts | 2 +- .../server/saved_objects/data_views.ts | 5 +- .../create_index_pattern/main.ts | 2 +- .../map_object_to_result.test.ts | 4 +- .../saved_objects/map_object_to_result.ts | 4 +- .../kbn_archiver/global_search/basic.json | 3 +- .../global_search/global_search_providers.ts | 2 +- 15 files changed, 92 insertions(+), 69 deletions(-) diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 421a239e3b0df..481415fc584b0 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -273,6 +273,7 @@ /src/plugins/saved_objects_tagging_oss @elastic/kibana-core /config/kibana.yml @elastic/kibana-core /typings/ @elastic/kibana-core +/x-pack/plugins/global_search_providers @elastic/kibana-core /x-pack/plugins/banners/ @elastic/kibana-core /x-pack/plugins/features/ @elastic/kibana-core /x-pack/plugins/licensing/ @elastic/kibana-core diff --git a/src/plugins/data_view_editor/public/components/data_view_editor_flyout_content.tsx b/src/plugins/data_view_editor/public/components/data_view_editor_flyout_content.tsx index 744e3824e3c68..3c1305d8e7860 100644 --- a/src/plugins/data_view_editor/public/components/data_view_editor_flyout_content.tsx +++ b/src/plugins/data_view_editor/public/components/data_view_editor_flyout_content.tsx @@ -193,10 +193,11 @@ const IndexPatternEditorFlyoutContentComponent = ({ useEffect(() => { loadSources(); const getTitles = async () => { - const indexPatternTitles = await dataViews.getTitles(editData ? true : false); + const dataViewListItems = await dataViews.getIdsWithTitle(editData ? true : false); + const indexPatternNames = dataViewListItems.map((item) => item.name || item.title); setExistingIndexPatterns( - editData ? indexPatternTitles.filter((v) => v !== editData.title) : indexPatternTitles + editData ? indexPatternNames.filter((v) => v !== editData.name) : indexPatternNames ); setIsLoadingIndexPatterns(false); }; @@ -226,9 +227,7 @@ const IndexPatternEditorFlyoutContentComponent = ({ const currentLoadingTimestampFieldsIdx = ++currentLoadingTimestampFieldsRef.current; let timestampOptions: TimestampOption[] = []; const isValidResult = - !existingIndexPatterns.includes(query) && - matchedIndices.exactMatchedIndices.length > 0 && - !isLoadingMatchedIndices; + matchedIndices.exactMatchedIndices.length > 0 && !isLoadingMatchedIndices; if (isValidResult) { setIsLoadingTimestampFields(true); const getFieldsOptions: GetFieldsOptions = { @@ -249,7 +248,6 @@ const IndexPatternEditorFlyoutContentComponent = ({ return timestampOptions; }, [ - existingIndexPatterns, dataViews, requireTimestampField, rollupIndex, @@ -380,7 +378,7 @@ const IndexPatternEditorFlyoutContentComponent = ({ - + @@ -388,7 +386,6 @@ const IndexPatternEditorFlyoutContentComponent = ({ diff --git a/src/plugins/data_view_editor/public/components/form_fields/name_field.tsx b/src/plugins/data_view_editor/public/components/form_fields/name_field.tsx index 8b6a0cfb74b70..f2236abad5ec7 100644 --- a/src/plugins/data_view_editor/public/components/form_fields/name_field.tsx +++ b/src/plugins/data_view_editor/public/components/form_fields/name_field.tsx @@ -6,20 +6,66 @@ * Side Public License, v 1. */ -import React, { ChangeEvent } from 'react'; +import React, { ChangeEvent, useMemo } from 'react'; import { i18n } from '@kbn/i18n'; import { EuiFormRow, EuiFieldText } from '@elastic/eui'; -import { DataView, UseField } from '../../shared_imports'; +import { + DataView, + UseField, + ValidationConfig, + FieldConfig, + getFieldValidityAndErrorMessage, +} from '../../shared_imports'; import { IndexPatternConfig } from '../../types'; +import { schema } from '../form_schema'; interface NameFieldProps { editData?: DataView; + existingDataViewNames: string[]; } -export const NameField = ({ editData }: NameFieldProps) => { +interface GetNameConfigArgs { + namesNotAllowed: string[]; +} + +const createNameNoDupesValidator = ( + namesNotAllowed: string[] +): ValidationConfig<{}, string, string> => ({ + validator: ({ value }) => { + if (namesNotAllowed.includes(value)) { + return { + message: i18n.translate('indexPatternEditor.dataViewExists.ValidationErrorMessage', { + defaultMessage: 'A data view with this name already exists.', + }), + }; + } + }, +}); + +const getNameConfig = ({ namesNotAllowed }: GetNameConfigArgs): FieldConfig => { + const nameFieldConfig = schema.name; + + const validations = [...nameFieldConfig.validations, createNameNoDupesValidator(namesNotAllowed)]; + + return { + ...nameFieldConfig!, + validations, + }; +}; + +export const NameField = ({ editData, existingDataViewNames }: NameFieldProps) => { + const config = useMemo( + () => + getNameConfig({ + namesNotAllowed: existingDataViewNames, + }), + [existingDataViewNames] + ); + return ( path="name" + config={config} componentProps={{ euiFieldProps: { 'aria-label': i18n.translate('indexPatternEditor.form.nameAriaLabel', { @@ -29,8 +75,9 @@ export const NameField = ({ editData }: NameFieldProps) => { }} > {(field) => { + const { isInvalid, errorMessage } = getFieldValidityAndErrorMessage(field); return ( - + ) => { diff --git a/src/plugins/data_view_editor/public/components/form_fields/timestamp_field.tsx b/src/plugins/data_view_editor/public/components/form_fields/timestamp_field.tsx index dd9d4f7117453..ce36d1e1fdc99 100644 --- a/src/plugins/data_view_editor/public/components/form_fields/timestamp_field.tsx +++ b/src/plugins/data_view_editor/public/components/form_fields/timestamp_field.tsx @@ -24,7 +24,6 @@ import { schema } from '../form_schema'; interface Props { options: TimestampOption[]; isLoadingOptions: boolean; - isExistingIndexPattern: boolean; isLoadingMatchedIndices: boolean; hasMatchedIndices: boolean; } @@ -73,7 +72,6 @@ const timestampFieldHelp = i18n.translate('indexPatternEditor.editor.form.timeFi export const TimestampField = ({ options = [], isLoadingOptions = false, - isExistingIndexPattern, isLoadingMatchedIndices, hasMatchedIndices, }: Props) => { @@ -85,11 +83,7 @@ export const TimestampField = ({ const selectTimestampHelp = options.length ? timestampFieldHelp : ''; const timestampNoFieldsHelp = - options.length === 0 && - !isExistingIndexPattern && - !isLoadingMatchedIndices && - !isLoadingOptions && - hasMatchedIndices + options.length === 0 && !isLoadingMatchedIndices && !isLoadingOptions && hasMatchedIndices ? noTimestampOptionText : ''; diff --git a/src/plugins/data_view_editor/public/components/form_fields/title_field.tsx b/src/plugins/data_view_editor/public/components/form_fields/title_field.tsx index 29bb64bb53997..6c41700ead531 100644 --- a/src/plugins/data_view_editor/public/components/form_fields/title_field.tsx +++ b/src/plugins/data_view_editor/public/components/form_fields/title_field.tsx @@ -30,7 +30,6 @@ interface RefreshMatchedIndicesResult { } interface TitleFieldProps { - existingIndexPatterns: string[]; isRollup: boolean; matchedIndices: MatchedItem[]; rollupIndicesCapabilities: RollupIndicesCapsResponse; @@ -55,20 +54,6 @@ const mustMatchError = { }), }; -const createTitlesNoDupesValidator = ( - namesNotAllowed: string[] -): ValidationConfig<{}, string, string> => ({ - validator: ({ value }) => { - if (namesNotAllowed.includes(value)) { - return { - message: i18n.translate('indexPatternEditor.dataViewExists.ValidationErrorMessage', { - defaultMessage: 'An index pattern with this name already exists.', - }), - }; - } - }, -}); - interface MatchesValidatorArgs { rollupIndicesCapabilities: Record; refreshMatchedIndices: (title: string) => Promise; @@ -122,7 +107,6 @@ const createMatchesIndicesValidator = ({ }); interface GetTitleConfigArgs { - namesNotAllowed: string[]; isRollup: boolean; matchedIndices: MatchedItem[]; rollupIndicesCapabilities: RollupIndicesCapsResponse; @@ -130,7 +114,6 @@ interface GetTitleConfigArgs { } const getTitleConfig = ({ - namesNotAllowed, isRollup, rollupIndicesCapabilities, refreshMatchedIndices, @@ -145,7 +128,6 @@ const getTitleConfig = ({ refreshMatchedIndices, isRollup, }), - createTitlesNoDupesValidator(namesNotAllowed), ]; return { @@ -155,7 +137,6 @@ const getTitleConfig = ({ }; export const TitleField = ({ - existingIndexPatterns, isRollup, matchedIndices, rollupIndicesCapabilities, @@ -166,19 +147,12 @@ export const TitleField = ({ const fieldConfig = useMemo( () => getTitleConfig({ - namesNotAllowed: existingIndexPatterns, isRollup, matchedIndices, rollupIndicesCapabilities, refreshMatchedIndices, }), - [ - existingIndexPatterns, - isRollup, - matchedIndices, - rollupIndicesCapabilities, - refreshMatchedIndices, - ] + [isRollup, matchedIndices, rollupIndicesCapabilities, refreshMatchedIndices] ); return ( diff --git a/src/plugins/data_view_editor/public/components/form_schema.ts b/src/plugins/data_view_editor/public/components/form_schema.ts index 9af41592dcbfe..98c3a3b5322eb 100644 --- a/src/plugins/data_view_editor/public/components/form_schema.ts +++ b/src/plugins/data_view_editor/public/components/form_schema.ts @@ -50,6 +50,7 @@ export const schema = { defaultMessage: 'Name', }), defaultValue: '', + validations: [], }, timestampField: { label: i18n.translate('indexPatternEditor.editor.form.timeFieldLabel', { diff --git a/src/plugins/data_views/common/data_views/data_views.ts b/src/plugins/data_views/common/data_views/data_views.ts index a92f18029bd4a..12a06b9a98fa7 100644 --- a/src/plugins/data_views/common/data_views/data_views.ts +++ b/src/plugins/data_views/common/data_views/data_views.ts @@ -33,7 +33,7 @@ import { } from '../types'; import { META_FIELDS, SavedObject } from '..'; import { DataViewMissingIndices } from '../lib'; -import { findByTitle } from '../utils'; +import { findByName } from '../utils'; import { DuplicateDataViewError, DataViewInsufficientAccessError } from '../errors'; const MAX_ATTEMPTS_TO_RESOLVE_CONFLICTS = 3; @@ -772,12 +772,17 @@ export class DataViewsService { * @param skipFetchFields if true, will not fetch fields * @returns DataView */ - async create({ id, ...restOfSpec }: DataViewSpec, skipFetchFields = false): Promise { + async create( + { id, name, title, ...restOfSpec }: DataViewSpec, + skipFetchFields = false + ): Promise { const shortDotsEnable = await this.config.get(FORMATS_UI_SETTINGS.SHORT_DOTS_ENABLE); const metaFields = await this.config.get(META_FIELDS); const spec = { id: id ?? uuid.v4(), + title, + name: name || title, ...restOfSpec, }; @@ -821,12 +826,13 @@ export class DataViewsService { if (!(await this.getCanSave())) { throw new DataViewInsufficientAccessError(); } - const dupe = await findByTitle(this.savedObjectsClient, dataView.title); + const dupe = await findByName(this.savedObjectsClient, dataView.getName()); + if (dupe) { if (override) { await this.delete(dupe.id); } else { - throw new DuplicateDataViewError(`Duplicate data view: ${dataView.title}`); + throw new DuplicateDataViewError(`Duplicate data view: ${dataView.getName()}`); } } diff --git a/src/plugins/data_views/common/utils.ts b/src/plugins/data_views/common/utils.ts index 98f55d6265d27..c12e6c71c92ba 100644 --- a/src/plugins/data_views/common/utils.ts +++ b/src/plugins/data_views/common/utils.ts @@ -12,22 +12,22 @@ import type { SavedObjectsClientCommon } from './types'; import { DATA_VIEW_SAVED_OBJECT_TYPE } from './constants'; /** - * Returns an object matching a given title + * Returns an object matching a given name * * @param client {SavedObjectsClientCommon} - * @param title {string} - * @returns {Promise} + * @param name {string} + * @returns {SavedObject|undefined} */ -export async function findByTitle(client: SavedObjectsClientCommon, title: string) { - if (title) { +export async function findByName(client: SavedObjectsClientCommon, name: string) { + if (name) { const savedObjects = await client.find({ type: DATA_VIEW_SAVED_OBJECT_TYPE, perPage: 10, - search: `"${title}"`, - searchFields: ['title'], - fields: ['title'], + search: `"${name}"`, + searchFields: ['name'], + fields: ['name'], }); - return savedObjects.find((obj) => obj.attributes.title.toLowerCase() === title.toLowerCase()); + return savedObjects ? savedObjects[0] : undefined; } } diff --git a/src/plugins/data_views/server/rest_api_routes/create_data_view.ts b/src/plugins/data_views/server/rest_api_routes/create_data_view.ts index c0b01329f5866..00897c364e085 100644 --- a/src/plugins/data_views/server/rest_api_routes/create_data_view.ts +++ b/src/plugins/data_views/server/rest_api_routes/create_data_view.ts @@ -113,7 +113,7 @@ const registerCreateDataViewRouteFactory = const dataView = await createDataView({ dataViewsService, usageCollection, - spec: spec as DataViewSpec, + spec: { ...spec, name: spec.name || spec.title } as DataViewSpec, override: body.override, refreshFields: body.refresh_fields, counterName: `${req.route.method} ${path}`, diff --git a/src/plugins/data_views/server/saved_objects/data_views.ts b/src/plugins/data_views/server/saved_objects/data_views.ts index 6319911f3bfd5..064302e2b6fe6 100644 --- a/src/plugins/data_views/server/saved_objects/data_views.ts +++ b/src/plugins/data_views/server/saved_objects/data_views.ts @@ -18,10 +18,10 @@ export const dataViewSavedObjectType: SavedObjectsType = { management: { displayName: 'data view', icon: 'indexPatternApp', - defaultSearchField: 'title', + defaultSearchField: 'name', importableAndExportable: true, getTitle(obj) { - return obj.attributes.title; + return obj.attributes.name || obj.attributes.title; }, getEditUrl(obj) { return `/management/kibana/dataViews/dataView/${encodeURIComponent(obj.id)}`; @@ -38,6 +38,7 @@ export const dataViewSavedObjectType: SavedObjectsType = { properties: { title: { type: 'text' }, type: { type: 'keyword' }, + name: { type: 'text' }, }, }, migrations: indexPatternSavedObjectTypeMigrations as any, diff --git a/test/api_integration/apis/index_patterns/index_pattern_crud/create_index_pattern/main.ts b/test/api_integration/apis/index_patterns/index_pattern_crud/create_index_pattern/main.ts index 43c9696fd11f8..6b6a84e539da3 100644 --- a/test/api_integration/apis/index_patterns/index_pattern_crud/create_index_pattern/main.ts +++ b/test/api_integration/apis/index_patterns/index_pattern_crud/create_index_pattern/main.ts @@ -243,7 +243,7 @@ export default function ({ getService }: FtrProviderContext) { expect(response.body[config.serviceKey].fieldAttrs.foo.customLabel).to.be('test'); }); - describe('when creating index pattern with existing title', () => { + describe('when creating index pattern with existing name', () => { it('returns error, by default', async () => { const title = `foo-${Date.now()}-${Math.random()}*`; const response1 = await supertest.post(config.path).send({ diff --git a/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.test.ts b/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.test.ts index 7f5a894a32e53..13d6803f1ccdf 100644 --- a/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.test.ts +++ b/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.test.ts @@ -153,6 +153,7 @@ describe('mapToResults', () => { management: { defaultSearchField: 'excerpt', getInAppUrl: (obj) => ({ path: `/type-c/${obj.id}`, uiCapabilitiesPath: 'test.typeC' }), + getTitle: (obj) => `${obj.attributes.title} ${obj.attributes.name}`, }, }) ); @@ -204,6 +205,7 @@ describe('mapToResults', () => { { excerpt: 'titleC', title: 'foo', + name: 'name', }, [ { name: 'tag A', type: 'tag', id: '1' }, @@ -235,7 +237,7 @@ describe('mapToResults', () => { }, { id: 'resultC', - title: 'titleC', + title: 'foo name', type: 'typeC', url: '/type-c/resultC', score: 42, diff --git a/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.ts b/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.ts index 676c92fba0b4c..bc993129435cb 100644 --- a/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.ts +++ b/x-pack/plugins/global_search_providers/server/providers/saved_objects/map_object_to_result.ts @@ -41,7 +41,7 @@ export const mapToResult = ( object: SavedObjectsFindResult, type: SavedObjectsType ): GlobalSearchProviderResult => { - const { defaultSearchField, getInAppUrl } = type.management ?? {}; + const { defaultSearchField, getInAppUrl, getTitle } = type.management ?? {}; if (defaultSearchField === undefined || getInAppUrl === undefined) { throw new Error('Trying to map an object from a type without management metadata'); } @@ -49,7 +49,7 @@ export const mapToResult = ( id: object.id, // defaultSearchField is dynamic and not 'directly' bound to the generic type of the SavedObject // so we are forced to cast the attributes to any to access the properties associated with it. - title: (object.attributes as any)[defaultSearchField], + title: getTitle ? getTitle(object) : (object.attributes as any)[defaultSearchField], type: object.type, icon: type.management?.icon ?? undefined, url: getInAppUrl(object).path, diff --git a/x-pack/test/functional/fixtures/kbn_archiver/global_search/basic.json b/x-pack/test/functional/fixtures/kbn_archiver/global_search/basic.json index 49f26e7429870..081589750929a 100644 --- a/x-pack/test/functional/fixtures/kbn_archiver/global_search/basic.json +++ b/x-pack/test/functional/fixtures/kbn_archiver/global_search/basic.json @@ -66,7 +66,8 @@ "attributes": { "fields": "[{\"name\":\"@message\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@message.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"@tags\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"@tags.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"@timestamp\",\"type\":\"date\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"_id\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_index\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_score\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_source\",\"type\":\"_source\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_type\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"agent\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"agent.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"bytes\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"clientip\",\"type\":\"ip\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"extension\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"extension.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.coordinates\",\"type\":\"geo_point\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.dest\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.src\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"geo.srcdest\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"headings\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"headings.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"host\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"host.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"id\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"index\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"index.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"ip\",\"type\":\"ip\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"links\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"links.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"machine.os\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"machine.os.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"machine.ram\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"memory\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.char\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"meta.related\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.firstname\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"meta.user.lastname\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"phpmemory\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"referer\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:modified_time\",\"type\":\"date\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:published_time\",\"type\":\"date\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:section\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:section.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.article:tag\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.article:tag.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:description\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:description.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:image\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:image:height\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:height.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:image:width\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:image:width.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:site_name\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:site_name.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:title\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:title.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:type\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:type.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.og:url\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.og:url.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.twitter:card\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:card.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.twitter:description\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:description.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.twitter:image\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:image.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.twitter:site\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:site.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.twitter:title\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.twitter:title.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"relatedContent.url\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"relatedContent.url.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"request\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"request.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"response\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"response.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"spaces\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"spaces.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"type\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"url\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"url.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"utc_time\",\"type\":\"date\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true},{\"name\":\"xss\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"xss.raw\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true}]", "timeFieldName": "@timestamp", - "title": "logstash-*" + "title": "logstash-*", + "name": "logstash-*" }, "coreMigrationVersion": "8.4.0", "id": "logstash-*", diff --git a/x-pack/test/plugin_functional/test_suites/global_search/global_search_providers.ts b/x-pack/test/plugin_functional/test_suites/global_search/global_search_providers.ts index 047b852612ecf..daf1821ef5c05 100644 --- a/x-pack/test/plugin_functional/test_suites/global_search/global_search_providers.ts +++ b/x-pack/test/plugin_functional/test_suites/global_search/global_search_providers.ts @@ -40,7 +40,7 @@ export default function ({ getPageObjects, getService }: FtrProviderContext) { await kibanaServer.savedObjects.cleanStandardList(); }); - it('can search for index patterns', async () => { + it('can search for data views', async () => { const results = await findResultsWithApi('type:index-pattern logstash'); expect(results.length).to.be(1); expect(results[0].type).to.be('index-pattern'); From 274c2c7478292c6b0368024b47a02b93db8c99e0 Mon Sep 17 00:00:00 2001 From: Paul Tavares <56442535+paul-tavares@users.noreply.github.com> Date: Thu, 14 Jul 2022 09:13:03 -0400 Subject: [PATCH 022/111] Comment out code around triggering the command input history (#136320) - Comments out Responder's command input history and defers this functionality to a future release. --- .../components/command_input/command_input.test.tsx | 12 ++++++++---- .../components/command_input/command_input.tsx | 13 +++++++------ 2 files changed, 15 insertions(+), 10 deletions(-) diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx index 42990db6e48ce..a06d6ae7c38b7 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx @@ -92,14 +92,16 @@ describe('When entering data into the Console input', () => { expect(getFooterText()).toEqual('Unknown command abc'); }); - it('should display the input history popover when UP key is pressed', async () => { + // FIXME:PT uncomment once task OLM task #4384 is implemented + it.skip('should display the input history popover when UP key is pressed', async () => { render(); await showInputHistoryPopover(); expect(renderResult.getByTestId('test-inputHistorySelector')).not.toBeNull(); }); - describe('and when the command input history popover is opened', () => { + // FIXME:PT uncomment once task OLM task #4384 is implemented + describe.skip('and when the command input history popover is opened', () => { const renderWithInputHistory = async (inputText: string = '') => { render(); enterCommand('help'); @@ -237,7 +239,8 @@ describe('When entering data into the Console input', () => { expect(getFooterText()).toEqual('cmd1 '); }); - it('should return original cursor position if input history is closed with no selection', async () => { + // FIXME:PT uncomment once task OLM task #4384 is implemented + it.skip('should return original cursor position if input history is closed with no selection', async () => { typeKeyboardKey('{Enter}'); // add `isolate` to the input history typeKeyboardKey('release'); @@ -262,7 +265,8 @@ describe('When entering data into the Console input', () => { expect(getRightOfCursorText()).toEqual('elease'); }); - it('should reset cursor position to default (at end) if a selection is done from input history', async () => { + // FIXME:PT uncomment once task OLM task #4384 is implemented + it.skip('should reset cursor position to default (at end) if a selection is done from input history', async () => { typeKeyboardKey('{Enter}'); // add `isolate` to the input history typeKeyboardKey('release'); diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx index 9c5d528c46659..89ba5f6561435 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx @@ -131,12 +131,13 @@ export const CommandInput = memo(({ prompt = '', focusRef, .. const keyCode = eventDetails.keyCode; // UP arrow key - if (keyCode === 38) { - dispatch({ type: 'removeFocusFromKeyCapture' }); - dispatch({ type: 'updateInputPopoverState', payload: { show: 'input-history' } }); - - return; - } + // FIXME:PT to be addressed via OLM task #4384 + // if (keyCode === 38) { + // dispatch({ type: 'removeFocusFromKeyCapture' }); + // dispatch({ type: 'updateInputPopoverState', payload: { show: 'input-history' } }); + // + // return; + // } // Update the store with the updated text that was entered dispatch({ From 21a9b24fed46c7a21a0abe4a825363424c84650b Mon Sep 17 00:00:00 2001 From: Davis McPhee Date: Thu, 14 Jul 2022 10:48:47 -0300 Subject: [PATCH 023/111] [Discover] Improve support for pinned filters in surrounding documents (#135722) * [Discover] Update surrounding documents to support global filters * [Discover] Finish adding support for global filters in surrounding documents * [Discover] Fix broken jest tests * [Discover] Fixed null initial global state in surrounding documents * [Discover] Fix issue with null filters when query param gets cleared, and add functional tests for changes * [Discover] Remove filterManager from useEffect dependencies * [Discover] Fix 'cannot read properties of undefined' toast when navigating between surrounding documents while filters are present * [Discover] Fix typo in createInitialGlobalState, and clear current app filters when leaving surrounding documents so they don't appear on other screens * [Discover] Fix issue where Discover breadcrumb link breaks in surrounding documents after filters have been added or modified * [Discover] Add support for syncing the current pinned filters in surrounding documents to the Discover breadcrumb link * Revert "[Discover] Add support for syncing the current pinned filters in surrounding documents to the Discover breadcrumb link" This reverts commit 651a0fcb4b68a766e27bbd4077b77e4377fe4556. * [Discover] Undo change to clear local filters when leaving Surrounding documents --- .../application/context/context_app.test.tsx | 2 + .../application/context/context_app.tsx | 12 ++- .../context/hooks/use_context_app_fetch.tsx | 24 +++--- .../context/hooks/use_context_app_state.ts | 43 +++++------ .../context/services/context_state.test.ts | 10 ++- .../context/services/context_state.ts | 73 ++++++++++++++++--- .../public/hooks/use_navigation_props.tsx | 9 ++- test/functional/apps/context/_filters.ts | 63 ++++++++++++++++ 8 files changed, 184 insertions(+), 52 deletions(-) diff --git a/src/plugins/discover/public/application/context/context_app.test.tsx b/src/plugins/discover/public/application/context/context_app.test.tsx index 828ec0d0eeb1a..032e815690d70 100644 --- a/src/plugins/discover/public/application/context/context_app.test.tsx +++ b/src/plugins/discover/public/application/context/context_app.test.tsx @@ -21,6 +21,7 @@ import { uiSettingsMock } from '../../__mocks__/ui_settings'; import { themeServiceMock } from '@kbn/core/public/mocks'; import { LocalStorageMock } from '../../__mocks__/local_storage_mock'; import { KibanaContextProvider } from '@kbn/kibana-react-plugin/public'; +import { dataPluginMock } from '@kbn/data-plugin/public/mocks'; const mockFilterManager = createFilterManagerMock(); const mockNavigationPlugin = { ui: { TopNavMenu: mockTopNavMenu } }; @@ -28,6 +29,7 @@ const mockNavigationPlugin = { ui: { TopNavMenu: mockTopNavMenu } }; describe('ContextApp test', () => { const services = { data: { + ...dataPluginMock.createStartContract(), search: { searchSource: { createEmpty: jest.fn(), diff --git a/src/plugins/discover/public/application/context/context_app.tsx b/src/plugins/discover/public/application/context/context_app.tsx index ee7203e3c780c..74f5910a4dec3 100644 --- a/src/plugins/discover/public/application/context/context_app.tsx +++ b/src/plugins/discover/public/application/context/context_app.tsx @@ -19,7 +19,7 @@ import { i18n } from '@kbn/i18n'; import { DOC_TABLE_LEGACY, SEARCH_FIELDS_FROM_SOURCE } from '../../../common'; import { ContextErrorMessage } from './components/context_error_message'; import { LoadingStatus } from './services/context_query_state'; -import { AppState, isEqualFilters } from './services/context_state'; +import { AppState, GlobalState, isEqualFilters } from './services/context_state'; import { useColumns } from '../../hooks/use_data_grid_columns'; import { useContextAppState } from './hooks/use_context_app_state'; import { useContextAppFetch } from './hooks/use_context_app_fetch'; @@ -52,8 +52,9 @@ export const ContextApp = ({ indexPattern, anchorId }: ContextAppProps) => { /** * Context app state */ - const { appState, setAppState } = useContextAppState({ services }); + const { appState, globalState, setAppState } = useContextAppState({ services }); const prevAppState = useRef(); + const prevGlobalState = useRef({ filters: [] }); /** * Context fetched state @@ -85,13 +86,18 @@ export const ContextApp = ({ indexPattern, anchorId }: ContextAppProps) => { fetchSurroundingRows(SurrDocType.PREDECESSORS); } else if (prevAppState.current.successorCount !== appState.successorCount) { fetchSurroundingRows(SurrDocType.SUCCESSORS); - } else if (!isEqualFilters(prevAppState.current.filters, appState.filters)) { + } else if ( + !isEqualFilters(prevAppState.current.filters, appState.filters) || + !isEqualFilters(prevGlobalState.current.filters, globalState.filters) + ) { fetchContextRows(); } prevAppState.current = cloneDeep(appState); + prevGlobalState.current = cloneDeep(globalState); }, [ appState, + globalState, anchorId, fetchContextRows, fetchAllRows, diff --git a/src/plugins/discover/public/application/context/hooks/use_context_app_fetch.tsx b/src/plugins/discover/public/application/context/hooks/use_context_app_fetch.tsx index 1201526da0821..ee6773507b932 100644 --- a/src/plugins/discover/public/application/context/hooks/use_context_app_fetch.tsx +++ b/src/plugins/discover/public/application/context/hooks/use_context_app_fetch.tsx @@ -130,17 +130,19 @@ export function useContextAppFetch({ try { setState({ [statusKey]: { value: LoadingStatus.LOADING } }); - const rows = await fetchSurroundingDocs( - type, - indexPattern, - anchor, - tieBreakerField, - SortDirection.desc, - count, - filters, - data, - useNewFieldsApi - ); + const rows = anchor.id + ? await fetchSurroundingDocs( + type, + indexPattern, + anchor, + tieBreakerField, + SortDirection.desc, + count, + filters, + data, + useNewFieldsApi + ) + : []; setState({ [type]: rows, [statusKey]: { value: LoadingStatus.LOADED } }); } catch (error) { setState(createError(statusKey, FailureReason.UNKNOWN, error)); diff --git a/src/plugins/discover/public/application/context/hooks/use_context_app_state.ts b/src/plugins/discover/public/application/context/hooks/use_context_app_state.ts index 9accdb363af92..594ef3d3ffd4c 100644 --- a/src/plugins/discover/public/application/context/hooks/use_context_app_state.ts +++ b/src/plugins/discover/public/application/context/hooks/use_context_app_state.ts @@ -7,13 +7,12 @@ */ import { useEffect, useMemo, useState } from 'react'; -import { cloneDeep } from 'lodash'; import { CONTEXT_DEFAULT_SIZE_SETTING } from '../../../../common'; import { DiscoverServices } from '../../../build_services'; -import { AppState, getState } from '../services/context_state'; +import { AppState, getState, GlobalState } from '../services/context_state'; export function useContextAppState({ services }: { services: DiscoverServices }) { - const { uiSettings: config, history, core, filterManager } = services; + const { uiSettings: config, history, core } = services; const stateContainer = useMemo(() => { return getState({ @@ -22,10 +21,14 @@ export function useContextAppState({ services }: { services: DiscoverServices }) history: history(), toasts: core.notifications.toasts, uiSettings: config, + data: services.data, }); - }, [config, history, core.notifications.toasts]); + }, [config, history, core.notifications.toasts, services.data]); - const [appState, setState] = useState(stateContainer.appState.getState()); + const [appState, setAppState] = useState(stateContainer.appState.getState()); + const [globalState, setGlobalState] = useState( + stateContainer.globalState.getState() + ); /** * Sync with app state container @@ -38,32 +41,24 @@ export function useContextAppState({ services }: { services: DiscoverServices }) useEffect(() => { const unsubscribeAppState = stateContainer.appState.subscribe((newState) => { - setState((prevState) => ({ ...prevState, ...newState })); + const newStateEnsureFilter = { ...newState, filters: newState.filters ?? [] }; + setAppState((prevState) => ({ ...prevState, ...newStateEnsureFilter })); }); - return () => unsubscribeAppState(); - }, [stateContainer, setState]); - - /** - * Take care of filters - */ - useEffect(() => { - const filters = stateContainer.appState.getState().filters; - if (filters) { - filterManager.setAppFilters(cloneDeep(filters)); - } - - const { setFilters } = stateContainer; - const filterObservable = filterManager.getUpdates$().subscribe(() => { - setFilters(filterManager); + const unsubscribeGlobalState = stateContainer.globalState.subscribe((newState) => { + const newStateEnsureFilter = { ...newState, filters: newState.filters ?? [] }; + setGlobalState((prevState) => ({ ...prevState, ...newStateEnsureFilter })); }); - return () => filterObservable.unsubscribe(); - }, [filterManager, stateContainer]); + return () => { + unsubscribeAppState(); + unsubscribeGlobalState(); + }; + }, [stateContainer, setAppState]); return { appState, - stateContainer, + globalState, setAppState: stateContainer.setAppState, }; } diff --git a/src/plugins/discover/public/application/context/services/context_state.test.ts b/src/plugins/discover/public/application/context/services/context_state.test.ts index 4e64ff206647e..a420b8d08e0b6 100644 --- a/src/plugins/discover/public/application/context/services/context_state.test.ts +++ b/src/plugins/discover/public/application/context/services/context_state.test.ts @@ -13,7 +13,10 @@ import { createBrowserHistory, History } from 'history'; import { FilterManager } from '@kbn/data-plugin/public'; import { coreMock } from '@kbn/core/public/mocks'; import { SEARCH_FIELDS_FROM_SOURCE } from '../../../../common'; +import { discoverServiceMock } from '../../../__mocks__/services'; +discoverServiceMock.data.query.filterManager.getAppFilters = jest.fn(() => []); +discoverServiceMock.data.query.filterManager.getGlobalFilters = jest.fn(() => []); const setupMock = coreMock.createSetup(); describe('Test Discover Context State', () => { @@ -30,6 +33,7 @@ describe('Test Discover Context State', () => { get: (key: string) => (key === SEARCH_FIELDS_FROM_SOURCE ? true : ['_source']) as unknown as T, } as IUiSettingsClient, + data: discoverServiceMock.data, }); state.startSync(); }); @@ -47,7 +51,11 @@ describe('Test Discover Context State', () => { "successorCount": 4, } `); - expect(state.globalState.getState()).toMatchInlineSnapshot(`null`); + expect(state.globalState.getState()).toMatchInlineSnapshot(` + Object { + "filters": Array [], + } + `); expect(state.startSync).toBeDefined(); expect(state.stopSync).toBeDefined(); expect(state.getFilters()).toStrictEqual([]); diff --git a/src/plugins/discover/public/application/context/services/context_state.ts b/src/plugins/discover/public/application/context/services/context_state.ts index 77fa33faa14c8..9739b5bc0fde4 100644 --- a/src/plugins/discover/public/application/context/services/context_state.ts +++ b/src/plugins/discover/public/application/context/services/context_state.ts @@ -6,10 +6,10 @@ * Side Public License, v 1. */ -import { isEqual } from 'lodash'; +import { cloneDeep, isEqual } from 'lodash'; import { History } from 'history'; import { NotificationsStart, IUiSettingsClient } from '@kbn/core/public'; -import { Filter, compareFilters, COMPARE_ALL_OPTIONS } from '@kbn/es-query'; +import { Filter, compareFilters, COMPARE_ALL_OPTIONS, FilterStateStore } from '@kbn/es-query'; import { createStateContainer, createKbnUrlStateStorage, @@ -18,7 +18,7 @@ import { ReduxLikeStateContainer, } from '@kbn/kibana-utils-plugin/public'; -import { FilterManager } from '@kbn/data-plugin/public'; +import { connectToQueryState, DataPublicPluginStart, FilterManager } from '@kbn/data-plugin/public'; import { handleSourceColumnState } from '../../../utils/state_helpers'; export interface AppState { @@ -46,7 +46,7 @@ export interface AppState { sort?: string[][]; } -interface GlobalState { +export interface GlobalState { /** * Array of filters */ @@ -78,6 +78,11 @@ export interface GetStateParams { * core ui settings service */ uiSettings: IUiSettingsClient; + + /** + * data service + */ + data: DataPublicPluginStart; } export interface GetStateReturn { @@ -128,6 +133,7 @@ export function getState({ history, toasts, uiSettings, + data, }: GetStateParams): GetStateReturn { const stateStorage = createKbnUrlStateStorage({ useHash: storeInSessionStorage, @@ -135,14 +141,20 @@ export function getState({ ...(toasts && withNotifyOnErrors(toasts)), }); - const globalStateInitial = stateStorage.get(GLOBAL_STATE_URL_KEY) as GlobalState; + const globalStateFromUrl = stateStorage.get(GLOBAL_STATE_URL_KEY) as GlobalState; + const globalStateInitial = createInitialGlobalState(globalStateFromUrl); const globalStateContainer = createStateContainer(globalStateInitial); const appStateFromUrl = stateStorage.get(APP_STATE_URL_KEY) as AppState; const appStateInitial = createInitialAppState(defaultSize, appStateFromUrl, uiSettings); const appStateContainer = createStateContainer(appStateInitial); - const { start, stop } = syncStates([ + const getAllFilters = () => [ + ...getFilters(globalStateContainer.getState()), + ...getFilters(appStateContainer.getState()), + ]; + + const { start: startSyncingStates, stop: stopSyncingStates } = syncStates([ { storageKey: GLOBAL_STATE_URL_KEY, stateContainer: { @@ -173,11 +185,33 @@ export function getState({ }, ]); + let stopSyncingFilters = () => {}; + return { globalState: globalStateContainer, appState: appStateContainer, - startSync: start, - stopSync: stop, + startSync: () => { + data.query.filterManager.setFilters(cloneDeep(getAllFilters())); + + const stopSyncingAppFilters = connectToQueryState(data.query, appStateContainer, { + filters: FilterStateStore.APP_STATE, + }); + const stopSyncingGlobalFilters = connectToQueryState(data.query, globalStateContainer, { + filters: FilterStateStore.GLOBAL_STATE, + }); + + stopSyncingFilters = () => { + stopSyncingAppFilters(); + stopSyncingGlobalFilters(); + }; + + startSyncingStates(); + }, + stopSync: () => { + stopSyncingFilters(); + stopSyncingFilters = () => {}; + stopSyncingStates(); + }, setAppState: (newState: Partial) => { const oldState = appStateContainer.getState(); const mergedState = { ...oldState, ...newState }; @@ -186,10 +220,7 @@ export function getState({ stateStorage.set(APP_STATE_URL_KEY, mergedState, { replace: true }); } }, - getFilters: () => [ - ...getFilters(globalStateContainer.getState()), - ...getFilters(appStateContainer.getState()), - ], + getFilters: getAllFilters, setFilters: (filterManager: FilterManager) => { // global state filters const globalFilters = filterManager.getGlobalFilters(); @@ -282,3 +313,21 @@ function createInitialAppState( uiSettings ); } + +/** + * Helper function to return the initial global state, which is a merged object of url state and + * default state + */ +function createInitialGlobalState(urlState: GlobalState): GlobalState { + const defaultState: GlobalState = { + filters: [], + }; + if (typeof urlState !== 'object') { + return defaultState; + } + + return { + ...defaultState, + ...urlState, + }; +} diff --git a/src/plugins/discover/public/hooks/use_navigation_props.tsx b/src/plugins/discover/public/hooks/use_navigation_props.tsx index 56720776b1553..a62df3f09e2fe 100644 --- a/src/plugins/discover/public/hooks/use_navigation_props.tsx +++ b/src/plugins/discover/public/hooks/use_navigation_props.tsx @@ -66,7 +66,14 @@ const getCurrentBreadcrumbs = ( export const useMainRouteBreadcrumb = () => { // useRef needed to retrieve initial breadcrumb link from the push state without updates - return useRef(useHistory().location.state?.breadcrumb).current; + const breadcrumb = useRef(); + const history = useHistory(); + + if (history.location.state?.breadcrumb) { + breadcrumb.current = history.location.state.breadcrumb; + } + + return breadcrumb.current; }; export const useNavigationProps = ({ diff --git a/test/functional/apps/context/_filters.ts b/test/functional/apps/context/_filters.ts index e8a8675e85f82..8c77d4fd013c1 100644 --- a/test/functional/apps/context/_filters.ts +++ b/test/functional/apps/context/_filters.ts @@ -6,6 +6,7 @@ * Side Public License, v 1. */ +import expect from '@kbn/expect'; import { FtrProviderContext } from '../../ftr_provider_context'; const TEST_INDEX_PATTERN = 'logstash-*'; @@ -19,6 +20,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { const filterBar = getService('filterBar'); const testSubjects = getService('testSubjects'); const retry = getService('retry'); + const browser = getService('browser'); const PageObjects = getPageObjects(['common', 'context']); @@ -75,5 +77,66 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { return await filterBar.hasFilter(TEST_ANCHOR_FILTER_FIELD, 'exists', true); }); }); + + const addPinnedFilter = async () => { + await filterBar.addFilter(TEST_ANCHOR_FILTER_FIELD, 'IS', TEST_ANCHOR_FILTER_VALUE); + await filterBar.toggleFilterPinned(TEST_ANCHOR_FILTER_FIELD); + }; + + const everyFieldMatches = async (matches: (field: string[]) => boolean) => { + const fields = await dataGrid.getFields(); + return fields.every(matches); + }; + + it('should update the data grid when a pinned filter is modified', async function () { + await addPinnedFilter(); + await PageObjects.context.waitUntilContextLoadingHasFinished(); + expect(await everyFieldMatches((field) => field[2] === TEST_ANCHOR_FILTER_VALUE)).to.be(true); + await filterBar.toggleFilterNegated(TEST_ANCHOR_FILTER_FIELD); + await PageObjects.context.waitUntilContextLoadingHasFinished(); + expect(await everyFieldMatches((field) => field[2] === TEST_ANCHOR_FILTER_VALUE)).to.be( + false + ); + }); + + const expectFiltersToExist = async () => { + expect(await filterBar.getFilterCount()).to.be(2); + expect( + await filterBar.hasFilter(TEST_ANCHOR_FILTER_FIELD, TEST_ANCHOR_FILTER_VALUE, true, true) + ).to.be(true); + expect(await filterBar.hasFilter('extension', 'png')).to.be(true); + expect( + await everyFieldMatches( + (field) => field[1] === 'png' && field[2] === TEST_ANCHOR_FILTER_VALUE + ) + ).to.be(true); + }; + + it('should preserve filters when the page is refreshed', async function () { + await addPinnedFilter(); + await filterBar.addFilter('extension', 'IS', 'png'); + await PageObjects.context.waitUntilContextLoadingHasFinished(); + await expectFiltersToExist(); + await browser.refresh(); + await PageObjects.context.waitUntilContextLoadingHasFinished(); + await expectFiltersToExist(); + }); + + it('should update filters when navigating forward and backward in history', async () => { + await filterBar.addFilter('extension', 'IS', 'png'); + await PageObjects.context.waitUntilContextLoadingHasFinished(); + expect(await filterBar.getFilterCount()).to.be(1); + expect(await filterBar.hasFilter('extension', 'png')).to.be(true); + expect(await everyFieldMatches((field) => field[1] === 'png')).to.be(true); + await browser.goBack(); + await PageObjects.context.waitUntilContextLoadingHasFinished(); + expect(await filterBar.getFilterCount()).to.be(0); + expect(await everyFieldMatches((field) => field[1] === 'png')).to.be(false); + await browser.goForward(); + await PageObjects.context.waitUntilContextLoadingHasFinished(); + expect(await filterBar.getFilterCount()).to.be(1); + expect(await filterBar.hasFilter('extension', 'png')).to.be(true); + expect(await everyFieldMatches((field) => field[1] === 'png')).to.be(true); + }); }); } From 9888244e2cb577d5fd318bd5980dcc221b4cb48b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alejandro=20Fern=C3=A1ndez=20Haro?= Date: Thu, 14 Jul 2022 15:58:57 +0200 Subject: [PATCH 024/111] [EBT] Add Telemetry Labels (#135682) Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .github/CODEOWNERS | 1 + src/plugins/telemetry/public/mocks.ts | 1 + src/plugins/telemetry/public/plugin.ts | 16 +++++++++ src/plugins/telemetry/server/config/config.ts | 4 +++ src/plugins/telemetry/server/config/index.ts | 1 + .../server/config/telemetry_labels.ts | 33 +++++++++++++++++++ src/plugins/telemetry/server/plugin.ts | 16 ++++++++- ...telemetry_management_section.test.tsx.snap | 1 + .../telemetry_management_section.test.tsx | 7 ++++ .../test_suites/core_plugins/rendering.ts | 11 +++++++ 10 files changed, 90 insertions(+), 1 deletion(-) create mode 100644 src/plugins/telemetry/server/config/telemetry_labels.ts diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 481415fc584b0..670fc3a7a4cac 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -332,6 +332,7 @@ /packages/kbn-handlebars/ @elastic/kibana-security /packages/core/http/core-http-server-internal/src/csp/ @elastic/kibana-security @elastic/kibana-core /src/plugins/interactive_setup/ @elastic/kibana-security +/src/plugins/telemetry/server/config/telemetry_labels.ts @elastic/kibana-security /test/interactive_setup_api_integration/ @elastic/kibana-security /test/interactive_setup_functional/ @elastic/kibana-security /test/plugin_functional/test_suites/core_plugins/rendering.ts @elastic/kibana-security diff --git a/src/plugins/telemetry/public/mocks.ts b/src/plugins/telemetry/public/mocks.ts index 7c74d8f7d8813..42225703163e6 100644 --- a/src/plugins/telemetry/public/mocks.ts +++ b/src/plugins/telemetry/public/mocks.ts @@ -40,6 +40,7 @@ export function mockTelemetryService({ allowChangingOptInStatus: true, telemetryNotifyUserAboutOptInDefault: true, userCanChangeSettings: true, + labels: {}, ...configOverride, }; diff --git a/src/plugins/telemetry/public/plugin.ts b/src/plugins/telemetry/public/plugin.ts index d6d0288cbb0bf..6bf53d59cb215 100644 --- a/src/plugins/telemetry/public/plugin.ts +++ b/src/plugins/telemetry/public/plugin.ts @@ -21,6 +21,7 @@ import type { ScreenshotModePluginSetup } from '@kbn/screenshot-mode-plugin/publ import type { HomePublicPluginSetup } from '@kbn/home-plugin/public'; import { ElasticV3BrowserShipper } from '@kbn/analytics-shippers-elastic-v3-browser'; +import { of } from 'rxjs'; import { TelemetrySender, TelemetryService, TelemetryNotifications } from './services'; import type { TelemetrySavedObjectAttributes, @@ -104,6 +105,8 @@ export interface TelemetryPluginConfig { userCanChangeSettings?: boolean; /** Should we hide the privacy statement notice? Useful on some environments, e.g. Cloud */ hidePrivacyStatement?: boolean; + /** Extra labels to add to the telemetry context */ + labels: Record; } function getTelemetryConstants(docLinks: DocLinksStart): TelemetryConstants { @@ -146,6 +149,19 @@ export class TelemetryPlugin implements Plugin, Type<'staging'>] = [ schema.literal('prod'), @@ -32,6 +33,8 @@ const configSchema = schema.object({ sendUsageFrom: schema.oneOf([schema.literal('server'), schema.literal('browser')], { defaultValue: 'server', }), + // Used for extra enrichment of telemetry + labels: labelsSchema, }); export type TelemetryConfigType = TypeOf; @@ -45,6 +48,7 @@ export const config: PluginConfigDescriptor = { sendUsageFrom: true, sendUsageTo: true, hidePrivacyStatement: true, + labels: true, }, deprecations: () => [ (cfg) => { diff --git a/src/plugins/telemetry/server/config/index.ts b/src/plugins/telemetry/server/config/index.ts index 19ccd73e17fcd..da368f2cbd1aa 100644 --- a/src/plugins/telemetry/server/config/index.ts +++ b/src/plugins/telemetry/server/config/index.ts @@ -8,3 +8,4 @@ export { config } from './config'; export type { TelemetryConfigType } from './config'; +export type { TelemetryConfigLabels } from './telemetry_labels'; diff --git a/src/plugins/telemetry/server/config/telemetry_labels.ts b/src/plugins/telemetry/server/config/telemetry_labels.ts new file mode 100644 index 0000000000000..f8cf7e6575866 --- /dev/null +++ b/src/plugins/telemetry/server/config/telemetry_labels.ts @@ -0,0 +1,33 @@ +/* + * 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 { schema, TypeOf } from '@kbn/config-schema'; + +/** + * Labels to enrich the context of the telemetry generated. + * When adding new keys, bear in mind that this info is exposed + * to the browser **even to unauthenticated pages**. + */ +export const labelsSchema = schema.object( + { + branch: schema.maybe(schema.string()), + ciBuildJobId: schema.maybe(schema.string()), + ciBuildId: schema.maybe(schema.string()), + ciBuildNumber: schema.maybe(schema.number()), + ftrConfig: schema.maybe(schema.string()), + git_rev: schema.maybe(schema.string()), + isPr: schema.maybe(schema.boolean()), + prId: schema.maybe(schema.string()), + journeyName: schema.maybe(schema.string()), + testBuildId: schema.maybe(schema.string()), + testJobId: schema.maybe(schema.string()), + }, + { defaultValue: {} } +); + +export type TelemetryConfigLabels = TypeOf; diff --git a/src/plugins/telemetry/server/plugin.ts b/src/plugins/telemetry/server/plugin.ts index cf2f7710e8729..9fe6ad52a8c3e 100644 --- a/src/plugins/telemetry/server/plugin.ts +++ b/src/plugins/telemetry/server/plugin.ts @@ -19,6 +19,7 @@ import { takeUntil, tap, shareReplay, + map, } from 'rxjs'; import { ElasticV3ServerShipper } from '@kbn/analytics-shippers-elastic-v3-server'; @@ -45,7 +46,7 @@ import { registerTelemetryUsageCollector, registerTelemetryPluginUsageCollector, } from './collectors'; -import type { TelemetryConfigType } from './config'; +import type { TelemetryConfigLabels, TelemetryConfigType } from './config'; import { FetcherTask } from './fetcher'; import { getTelemetrySavedObject, TelemetrySavedObject } from './telemetry_repository'; import { OPT_IN_POLL_INTERVAL_MS } from '../common/constants'; @@ -157,6 +158,19 @@ export class TelemetryPlugin implements Plugin({ + name: 'telemetry labels', + context$: this.config$.pipe(map(({ labels }) => ({ labels }))), + schema: { + labels: { + type: 'pass_through', + _meta: { + description: 'Custom labels added to the telemetry.labels config in the kibana.yml', + }, + }, + }, + }); + const config$ = this.config$; const isDev = this.isDev; registerCollection(telemetryCollectionManager); diff --git a/src/plugins/telemetry_management_section/public/components/__snapshots__/telemetry_management_section.test.tsx.snap b/src/plugins/telemetry_management_section/public/components/__snapshots__/telemetry_management_section.test.tsx.snap index 9cd03e02f36dc..f590a5c82a79b 100644 --- a/src/plugins/telemetry_management_section/public/components/__snapshots__/telemetry_management_section.test.tsx.snap +++ b/src/plugins/telemetry_management_section/public/components/__snapshots__/telemetry_management_section.test.tsx.snap @@ -264,6 +264,7 @@ exports[`TelemetryManagementSectionComponent renders null because allowChangingO "defaultConfig": Object { "allowChangingOptInStatus": false, "banner": true, + "labels": Object {}, "optIn": true, "sendUsageFrom": "browser", "sendUsageTo": "staging", diff --git a/src/plugins/telemetry_management_section/public/components/telemetry_management_section.test.tsx b/src/plugins/telemetry_management_section/public/components/telemetry_management_section.test.tsx index f747e9c6194db..7576c0f35b6a9 100644 --- a/src/plugins/telemetry_management_section/public/components/telemetry_management_section.test.tsx +++ b/src/plugins/telemetry_management_section/public/components/telemetry_management_section.test.tsx @@ -30,6 +30,7 @@ describe('TelemetryManagementSectionComponent', () => { allowChangingOptInStatus: true, optIn: true, sendUsageFrom: 'browser', + labels: {}, }, isScreenshotMode: false, reportOptInStatusChange: false, @@ -61,6 +62,7 @@ describe('TelemetryManagementSectionComponent', () => { optIn: false, sendUsageFrom: 'browser', sendUsageTo: 'staging', + labels: {}, }, isScreenshotMode: false, reportOptInStatusChange: false, @@ -112,6 +114,7 @@ describe('TelemetryManagementSectionComponent', () => { optIn: false, sendUsageTo: 'staging', sendUsageFrom: 'browser', + labels: {}, }, isScreenshotMode: false, reportOptInStatusChange: false, @@ -157,6 +160,7 @@ describe('TelemetryManagementSectionComponent', () => { optIn: true, sendUsageTo: 'staging', sendUsageFrom: 'browser', + labels: {}, }, isScreenshotMode: false, reportOptInStatusChange: false, @@ -193,6 +197,7 @@ describe('TelemetryManagementSectionComponent', () => { optIn: false, sendUsageTo: 'staging', sendUsageFrom: 'browser', + labels: {}, }, isScreenshotMode: false, reportOptInStatusChange: false, @@ -233,6 +238,7 @@ describe('TelemetryManagementSectionComponent', () => { optIn: false, sendUsageTo: 'staging', sendUsageFrom: 'browser', + labels: {}, }, isScreenshotMode: false, reportOptInStatusChange: false, @@ -280,6 +286,7 @@ describe('TelemetryManagementSectionComponent', () => { optIn: false, sendUsageTo: 'staging', sendUsageFrom: 'browser', + labels: {}, }, isScreenshotMode: false, reportOptInStatusChange: false, diff --git a/test/plugin_functional/test_suites/core_plugins/rendering.ts b/test/plugin_functional/test_suites/core_plugins/rendering.ts index 1e71c304165c5..5381d212598d9 100644 --- a/test/plugin_functional/test_suites/core_plugins/rendering.ts +++ b/test/plugin_functional/test_suites/core_plugins/rendering.ts @@ -143,6 +143,17 @@ export default function ({ getService }: PluginFunctionalProviderContext) { 'newsfeed.service.urlRoot (string)', 'telemetry.allowChangingOptInStatus (boolean)', 'telemetry.banner (boolean)', + 'telemetry.labels.branch (string)', + 'telemetry.labels.ciBuildId (string)', + 'telemetry.labels.ciBuildJobId (string)', + 'telemetry.labels.ciBuildNumber (number)', + 'telemetry.labels.ftrConfig (string)', + 'telemetry.labels.git_rev (string)', + 'telemetry.labels.isPr (boolean)', + 'telemetry.labels.journeyName (string)', + 'telemetry.labels.prId (string)', + 'telemetry.labels.testBuildId (string)', + 'telemetry.labels.testJobId (string)', 'telemetry.hidePrivacyStatement (boolean)', 'telemetry.optIn (boolean)', 'telemetry.sendUsageFrom (alternatives)', From fe1b7e8cf94ddc1bc3c3b1a514a5769d5832274c Mon Sep 17 00:00:00 2001 From: spalger Date: Thu, 14 Jul 2022 09:21:27 -0500 Subject: [PATCH 025/111] Revert "unskip test (#134549)" This reverts commit 8f369db749b1bbb5d8b89e01a889535b7d30cf53. --- .../synthetics/public/legacy_uptime/pages/overview.test.tsx | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/x-pack/plugins/synthetics/public/legacy_uptime/pages/overview.test.tsx b/x-pack/plugins/synthetics/public/legacy_uptime/pages/overview.test.tsx index b3aa4714fa664..30ea0e361580a 100644 --- a/x-pack/plugins/synthetics/public/legacy_uptime/pages/overview.test.tsx +++ b/x-pack/plugins/synthetics/public/legacy_uptime/pages/overview.test.tsx @@ -9,7 +9,8 @@ import React from 'react'; import { OverviewPageComponent } from './overview'; import { render } from '../lib/helper/rtl_helpers'; -describe('MonitorPage', () => { +// FLAKY: https://github.com/elastic/kibana/issues/131346 +describe.skip('MonitorPage', () => { it('renders expected elements for valid props', async () => { const { findByText, findByPlaceholderText } = render(); From 3d582f33f575b96d3434467b88f3ef5b5073054b Mon Sep 17 00:00:00 2001 From: Jonathan Budzenski Date: Thu, 14 Jul 2022 09:38:32 -0500 Subject: [PATCH 026/111] Bump html-loader to 1.3.2 (#136360) --- package.json | 2 +- yarn.lock | 144 +++++++++++++-------------------------------------- 2 files changed, 36 insertions(+), 110 deletions(-) diff --git a/package.json b/package.json index a0cab1288d620..44111b5550366 100644 --- a/package.json +++ b/package.json @@ -1066,7 +1066,7 @@ "has-ansi": "^3.0.0", "hdr-histogram-js": "^1.2.0", "html": "1.0.0", - "html-loader": "^0.5.5", + "html-loader": "^1.3.2", "http-proxy": "^1.18.1", "is-glob": "^4.0.1", "is-path-inside": "^3.0.2", diff --git a/yarn.lock b/yarn.lock index 7a09d8caa1dfb..25e8f56335861 100644 --- a/yarn.lock +++ b/yarn.lock @@ -9582,11 +9582,6 @@ ast-types-flow@^0.0.7: resolved "https://registry.yarnpkg.com/ast-types-flow/-/ast-types-flow-0.0.7.tgz#f70b735c6bca1a5c9c22d982c3e39e7feba3bdad" integrity sha1-9wtzXGvKGlycItmCw+Oef+ujva0= -ast-types@0.9.6: - version "0.9.6" - resolved "https://registry.yarnpkg.com/ast-types/-/ast-types-0.9.6.tgz#102c9e9e9005d3e7e3829bf0c4fa24ee862ee9b9" - integrity sha1-ECyenpAF0+fjgpvwxPok7oYu6bk= - ast-types@^0.13.2: version "0.13.3" resolved "https://registry.yarnpkg.com/ast-types/-/ast-types-0.13.3.tgz#50da3f28d17bdbc7969a3a2d83a0e4a72ae755a7" @@ -10868,14 +10863,6 @@ callsites@^3.1.0: resolved "https://registry.yarnpkg.com/callsites/-/callsites-3.1.0.tgz#b3630abd8943432f54b3f0519238e33cd7df2f73" integrity sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ== -camel-case@3.0.x: - version "3.0.0" - resolved "https://registry.yarnpkg.com/camel-case/-/camel-case-3.0.0.tgz#ca3c3688a4e9cf3a4cda777dc4dcbc713249cf73" - integrity sha1-yjw2iKTpzzpM2nd9xNy8cTJJz3M= - dependencies: - no-case "^2.2.0" - upper-case "^1.1.1" - camel-case@^4.1.1: version "4.1.1" resolved "https://registry.yarnpkg.com/camel-case/-/camel-case-4.1.1.tgz#1fc41c854f00e2f7d0139dfeba1542d6896fe547" @@ -11211,7 +11198,7 @@ classnames@2.2.6, classnames@2.x, classnames@^2.2.5, classnames@^2.2.6: resolved "https://registry.yarnpkg.com/classnames/-/classnames-2.2.6.tgz#43935bffdd291f326dad0a205309b38d00f650ce" integrity sha512-JR/iSQOSt+LQIWwrwEzJ9uk0xfN3mTVYMwt1Ir5mUcSN6pU+V4zQFFaJsclJbPuAUQH+yfWef6tm7l1quW3C8Q== -clean-css@4.2.x, clean-css@^4.2.3: +clean-css@^4.2.3: version "4.2.3" resolved "https://registry.yarnpkg.com/clean-css/-/clean-css-4.2.3.tgz#507b5de7d97b48ee53d84adb0160ff6216380f78" integrity sha512-VcMWDN54ZN/DS+g58HYL5/n4Zrqe8vHJpGA8KdgUXFU4fuP/aHNw8eld9SyEIyabIMJX/0RaY/fplOo5hYLSFA== @@ -11600,11 +11587,6 @@ commander@2, commander@^2.19.0, commander@^2.20.0, commander@^2.7.1: resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.3.tgz#fd485e84c03eb4881c20722ba48035e8531aeb33" integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== -commander@2.17.x: - version "2.17.1" - resolved "https://registry.yarnpkg.com/commander/-/commander-2.17.1.tgz#bd77ab7de6de94205ceacc72f1716d29f20a77bf" - integrity sha512-wPMUt6FnH2yzG95SA6mzjQOEKUU3aLaDEmzs1ti+1E9h+CsrZghRlqEM/EJ4KscsQVG8uNN4uVreUeT8+drlgg== - commander@7, commander@^7.2.0: version "7.2.0" resolved "https://registry.yarnpkg.com/commander/-/commander-7.2.0.tgz#a36cb57d0b501ce108e4d20559a150a391d97ab7" @@ -13709,20 +13691,20 @@ domhandler@^2.3.0: dependencies: domelementtype "1" -domhandler@^4.0, domhandler@^4.2.2: +domhandler@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/domhandler/-/domhandler-3.0.0.tgz#51cd13efca31da95bbb0c5bee3a48300e333b3e9" + integrity sha512-eKLdI5v9m67kbXQbJSNn1zjh0SDzvzWVWtX+qEI3eMjZw8daH9k8rlj1FZY9memPwjiskQFbe7vHVVJIAqoEhw== + dependencies: + domelementtype "^2.0.1" + +domhandler@^4.0.0, domhandler@^4.0, domhandler@^4.2.0, domhandler@^4.2.2: version "4.3.0" resolved "https://registry.yarnpkg.com/domhandler/-/domhandler-4.3.0.tgz#16c658c626cf966967e306f966b431f77d4a5626" integrity sha512-fC0aXNQXqKSFTr2wDNZDhsEYjCiYsDWl3D01kwt25hm1YIPyDGHvvi3rw+PLqHAl/m71MaiF7d5zvBr0p5UB2g== dependencies: domelementtype "^2.2.0" -domhandler@^4.0.0, domhandler@^4.2.0: - version "4.2.0" - resolved "https://registry.yarnpkg.com/domhandler/-/domhandler-4.2.0.tgz#f9768a5f034be60a89a27c2e4d0f74eba0d8b059" - integrity sha512-zk7sgt970kzPks2Bf+dwT/PLzghLnsivb9CcxkvR8Mzr66Olr0Ofd8neSbglHJHaHa2MadfoSdNlKYAaafmWfA== - dependencies: - domelementtype "^2.2.0" - domutils@1.1: version "1.1.6" resolved "https://registry.yarnpkg.com/domutils/-/domutils-1.1.6.tgz#bddc3de099b9a2efacc51c623f28f416ecc57485" @@ -13746,7 +13728,7 @@ domutils@^1.5.1, domutils@^1.7.0: dom-serializer "0" domelementtype "1" -domutils@^2.5.2, domutils@^2.6.0, domutils@^2.7.0, domutils@^2.8.0: +domutils@^2.0.0, domutils@^2.5.2, domutils@^2.6.0, domutils@^2.7.0, domutils@^2.8.0: version "2.8.0" resolved "https://registry.yarnpkg.com/domutils/-/domutils-2.8.0.tgz#4437def5db6e2d1f5d6ee859bd95ca7d02048135" integrity sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A== @@ -14374,14 +14356,6 @@ es6-symbol@3.1.1, es6-symbol@^3.1.1, es6-symbol@~3.1.1: d "1" es5-ext "~0.10.14" -es6-templates@^0.2.3: - version "0.2.3" - resolved "https://registry.yarnpkg.com/es6-templates/-/es6-templates-0.2.3.tgz#5cb9ac9fb1ded6eb1239342b81d792bbb4078ee4" - integrity sha1-XLmsn7He1usSOTQrgdeSu7QHjuQ= - dependencies: - recast "~0.11.12" - through "~2.3.6" - es6-weak-map@^2.0.1, es6-weak-map@^2.0.2: version "2.0.2" resolved "https://registry.yarnpkg.com/es6-weak-map/-/es6-weak-map-2.0.2.tgz#5e3ab32251ffd1538a1f8e5ffa1357772f92d96f" @@ -14766,11 +14740,6 @@ esprima@~1.0.4: resolved "https://registry.yarnpkg.com/esprima/-/esprima-1.0.4.tgz#9f557e08fc3b4d26ece9dd34f8fbf476b62585ad" integrity sha1-n1V+CPw7TSbs6d00+Pv0drYlha0= -esprima@~3.1.0: - version "3.1.3" - resolved "https://registry.yarnpkg.com/esprima/-/esprima-3.1.3.tgz#fdca51cee6133895e3c88d535ce49dbff62a4633" - integrity sha1-/cpRzuYTOJXjyI1TXOSdv/YqRjM= - esquery@^1.4.0: version "1.4.0" resolved "https://registry.yarnpkg.com/esquery/-/esquery-1.4.0.tgz#2148ffc38b82e8c7057dfed48425b3e61f0f24a5" @@ -15269,11 +15238,6 @@ fastest-stable-stringify@^1.0.1: resolved "https://registry.yarnpkg.com/fastest-stable-stringify/-/fastest-stable-stringify-1.0.1.tgz#9122d406d4c9d98bea644a6b6853d5874b87b028" integrity sha1-kSLUBtTJ2YvqZEpraFPVh0uHsCg= -fastparse@^1.1.1: - version "1.1.1" - resolved "https://registry.yarnpkg.com/fastparse/-/fastparse-1.1.1.tgz#d1e2643b38a94d7583b479060e6c4affc94071f8" - integrity sha1-0eJkOzipTXWDtHkGDmxK/8lAcfg= - fastq@^1.6.0: version "1.6.0" resolved "https://registry.yarnpkg.com/fastq/-/fastq-1.6.0.tgz#4ec8a38f4ac25f21492673adb7eae9cfef47d1c2" @@ -16992,7 +16956,7 @@ hdr-histogram-js@^1.2.0: base64-js "^1.2.0" pako "^1.0.3" -he@1.2.0, he@1.2.x, he@^1.2.0: +he@1.2.0, he@^1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f" integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw== @@ -17139,18 +17103,17 @@ html-escaper@^2.0.0: resolved "https://registry.yarnpkg.com/html-escaper/-/html-escaper-2.0.2.tgz#dfd60027da36a36dfcbe236262c00a5822681453" integrity sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg== -html-loader@^0.5.5: - version "0.5.5" - resolved "https://registry.yarnpkg.com/html-loader/-/html-loader-0.5.5.tgz#6356dbeb0c49756d8ebd5ca327f16ff06ab5faea" - integrity sha512-7hIW7YinOYUpo//kSYcPB6dCKoceKLmOwjEMmhIobHuWGDVl0Nwe4l68mdG/Ru0wcUxQjVMEoZpkalZ/SE7zog== +html-loader@^1.3.2: + version "1.3.2" + resolved "https://registry.yarnpkg.com/html-loader/-/html-loader-1.3.2.tgz#5a72ebba420d337083497c9aba7866c9e1aee340" + integrity sha512-DEkUwSd0sijK5PF3kRWspYi56XP7bTNkyg5YWSzBdjaSDmvCufep5c4Vpb3PBf6lUL0YPtLwBfy9fL0t5hBAGA== dependencies: - es6-templates "^0.2.3" - fastparse "^1.1.1" - html-minifier "^3.5.8" - loader-utils "^1.1.0" - object-assign "^4.1.1" + html-minifier-terser "^5.1.1" + htmlparser2 "^4.1.0" + loader-utils "^2.0.0" + schema-utils "^3.0.0" -html-minifier-terser@^5.0.1: +html-minifier-terser@^5.0.1, html-minifier-terser@^5.1.1: version "5.1.1" resolved "https://registry.yarnpkg.com/html-minifier-terser/-/html-minifier-terser-5.1.1.tgz#922e96f1f3bb60832c2634b79884096389b1f054" integrity sha512-ZPr5MNObqnV/T9akshPKbVgyOqLmy+Bxo7juKCfTfnjNniTAMdy4hz21YQqoofMBJD2kdREaqPPdThoR78Tgxg== @@ -17163,19 +17126,6 @@ html-minifier-terser@^5.0.1: relateurl "^0.2.7" terser "^4.6.3" -html-minifier@^3.5.8: - version "3.5.21" - resolved "https://registry.yarnpkg.com/html-minifier/-/html-minifier-3.5.21.tgz#d0040e054730e354db008463593194015212d20c" - integrity sha512-LKUKwuJDhxNa3uf/LPR/KVjm/l3rBqtYeCOAekvG8F1vItxMUpueGd94i/asDDr8/1u7InxzFA5EeGjhhG5mMA== - dependencies: - camel-case "3.0.x" - clean-css "4.2.x" - commander "2.17.x" - he "1.2.x" - param-case "2.1.x" - relateurl "0.2.x" - uglify-js "3.4.x" - html-tags@^3.1.0: version "3.1.0" resolved "https://registry.yarnpkg.com/html-tags/-/html-tags-3.1.0.tgz#7b5e6f7e665e9fb41f30007ed9e0d41e97fb2140" @@ -17235,6 +17185,16 @@ htmlparser2@^3.10.0: inherits "^2.0.1" readable-stream "^3.1.1" +htmlparser2@^4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/htmlparser2/-/htmlparser2-4.1.0.tgz#9a4ef161f2e4625ebf7dfbe6c0a2f52d18a59e78" + integrity sha512-4zDq1a1zhE4gQso/c5LP1OtrhYTncXNSpvJYtWJBtXAETPlMfi3IFNjGuQbYLuVY4ZR0QMqRVvo4Pdy9KLyP8Q== + dependencies: + domelementtype "^2.0.1" + domhandler "^3.0.0" + domutils "^2.0.0" + entities "^2.0.0" + htmlparser2@^6.1.0: version "6.1.0" resolved "https://registry.yarnpkg.com/htmlparser2/-/htmlparser2-6.1.0.tgz#c4d762b6c3371a05dbe65e94ae43a9f845fb8fb7" @@ -20425,11 +20385,6 @@ loose-envify@^1.0.0, loose-envify@^1.1.0, loose-envify@^1.2.0, loose-envify@^1.3 dependencies: js-tokens "^3.0.0 || ^4.0.0" -lower-case@^1.1.1: - version "1.1.4" - resolved "https://registry.yarnpkg.com/lower-case/-/lower-case-1.1.4.tgz#9a2cabd1b9e8e0ae993a4bf7d5875c39c42e8eac" - integrity sha1-miyr0bno4K6ZOkv31YdcOcQujqw= - lower-case@^2.0.1: version "2.0.1" resolved "https://registry.yarnpkg.com/lower-case/-/lower-case-2.0.1.tgz#39eeb36e396115cc05e29422eaea9e692c9408c7" @@ -21661,13 +21616,6 @@ nise@^1.5.2: lolex "^5.0.1" path-to-regexp "^1.7.0" -no-case@^2.2.0: - version "2.3.2" - resolved "https://registry.yarnpkg.com/no-case/-/no-case-2.3.2.tgz#60b813396be39b3f1288a4c1ed5d1e7d28b464ac" - integrity sha512-rmTZ9kz+f3rCvK2TD1Ue/oZlns7OGoIWP4fc3llxxRXlOkHKoWPPWJOfFYpITabSow43QJbRIoHQXtt10VldyQ== - dependencies: - lower-case "^1.1.1" - no-case@^3.0.3: version "3.0.3" resolved "https://registry.yarnpkg.com/no-case/-/no-case-3.0.3.tgz#c21b434c1ffe48b39087e86cfb4d2582e9df18f8" @@ -22681,13 +22629,6 @@ parallel-transform@^1.1.0: inherits "^2.0.3" readable-stream "^2.1.5" -param-case@2.1.x: - version "2.1.1" - resolved "https://registry.yarnpkg.com/param-case/-/param-case-2.1.1.tgz#df94fd8cf6531ecf75e6bef9a0858fbc72be2247" - integrity sha1-35T9jPZTHs915r75oIWPvHK+Ikc= - dependencies: - no-case "^2.2.0" - param-case@^3.0.3: version "3.0.3" resolved "https://registry.yarnpkg.com/param-case/-/param-case-3.0.3.tgz#4be41f8399eff621c56eebb829a5e451d9801238" @@ -23903,7 +23844,7 @@ prismjs@^1.22.0, prismjs@~1.25.0, prismjs@~1.27.0: resolved "https://registry.yarnpkg.com/prismjs/-/prismjs-1.27.0.tgz#bb6ee3138a0b438a3653dd4d6ce0cc6510a45057" integrity sha512-t13BGPUlFDR7wRB5kQDG4jjl7XeuH6jbJGt11JHPL96qwsEHNX2+68tFXqc1/k+/jALsbSWJKUOT/hcYAZ5LkA== -private@^0.1.8, private@~0.1.5: +private@^0.1.8: version "0.1.8" resolved "https://registry.yarnpkg.com/private/-/private-0.1.8.tgz#2381edb3689f7a53d653190060fcf822d2f368ff" integrity sha512-VvivMrbvd2nKkiG38qjULzlc+4Vx4wm/whI9pQD35YrARNnhxeiRktSOhSukRLFNlzg6Br/cJPet5J/u19r/mg== @@ -25314,16 +25255,6 @@ realpath-native@^1.1.0: dependencies: util.promisify "^1.0.0" -recast@~0.11.12: - version "0.11.23" - resolved "https://registry.yarnpkg.com/recast/-/recast-0.11.23.tgz#451fd3004ab1e4df9b4e4b66376b2a21912462d3" - integrity sha1-RR/TAEqx5N+bTktmN2sqIZEkYtM= - dependencies: - ast-types "0.9.6" - esprima "~3.1.0" - private "~0.1.5" - source-map "~0.5.0" - rechoir@^0.6.2: version "0.6.2" resolved "https://registry.yarnpkg.com/rechoir/-/rechoir-0.6.2.tgz#85204b54dba82d5742e28c96756ef43af50e3384" @@ -25573,7 +25504,7 @@ rehype-stringify@^8.0.0: dependencies: hast-util-to-html "^7.1.1" -relateurl@0.2.x, relateurl@^0.2.7: +relateurl@^0.2.7: version "0.2.7" resolved "https://registry.yarnpkg.com/relateurl/-/relateurl-0.2.7.tgz#54dbf377e51440aca90a4cd274600d3ff2d888a9" integrity sha1-VNvzd+UUQKypCkzSdGANP/LYiKk= @@ -27064,7 +26995,7 @@ source-map@0.5.6: resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.5.6.tgz#75ce38f52bf0733c5a7f0c118d81334a2bb5f412" integrity sha1-dc449SvwczxafwwRjYEzSiu19BI= -source-map@^0.5.0, source-map@^0.5.1, source-map@^0.5.6, source-map@^0.5.7, source-map@~0.5.0, source-map@~0.5.3: +source-map@^0.5.0, source-map@^0.5.1, source-map@^0.5.6, source-map@^0.5.7, source-map@~0.5.3: version "0.5.7" resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.5.7.tgz#8a039d2d1021d22d1ea14c80d8ea468ba2ef3fcc" integrity sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w= @@ -28354,7 +28285,7 @@ through2@^4.0.2: dependencies: readable-stream "3" -"through@>=2.2.7 <3", through@^2.3.4, through@^2.3.6, through@^2.3.8, through@~2.3.4, through@~2.3.6: +"through@>=2.2.7 <3", through@^2.3.4, through@^2.3.6, through@^2.3.8, through@~2.3.4: version "2.3.8" resolved "https://registry.yarnpkg.com/through/-/through-2.3.8.tgz#0dd4c9ffaabc357960b1b724115d7e0e86a2e1f5" integrity sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU= @@ -28936,7 +28867,7 @@ uc.micro@^1.0.1, uc.micro@^1.0.5: resolved "https://registry.yarnpkg.com/uc.micro/-/uc.micro-1.0.5.tgz#0c65f15f815aa08b560a61ce8b4db7ffc3f45376" integrity sha512-JoLI4g5zv5qNyT09f4YAvEZIIV1oOjqnewYg5D38dkQljIzpPT296dbIGvKro3digYI1bkb7W6EP1y4uDlmzLg== -uglify-js@3.4.x, uglify-js@^3.1.4, uglify-js@^3.14.3: +uglify-js@^3.1.4, uglify-js@^3.14.3: version "3.14.4" resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-3.14.4.tgz#68756f17d1b90b9d289341736cb9a567d6882f90" integrity sha512-AbiSR44J0GoCeV81+oxcy/jDOElO2Bx3d0MfQCUShq7JRXaM4KtQopZsq2vFv8bCq2yMaGrw1FgygUd03RyRDA== @@ -29382,11 +29313,6 @@ update-notifier@^5.1.0: semver-diff "^3.1.1" xdg-basedir "^4.0.0" -upper-case@^1.1.1: - version "1.1.3" - resolved "https://registry.yarnpkg.com/upper-case/-/upper-case-1.1.3.tgz#f6b4501c2ec4cdd26ba78be7222961de77621598" - integrity sha1-9rRQHC7EzdJrp4vnIilh3ndiFZg= - uri-js@^4.2.2: version "4.2.2" resolved "https://registry.yarnpkg.com/uri-js/-/uri-js-4.2.2.tgz#94c540e1ff772956e2299507c010aea6c8838eb0" From 623808cba3d029486dbd4bc3fdad91679f8bd61f Mon Sep 17 00:00:00 2001 From: Byron Hulcher Date: Thu, 14 Jul 2022 10:57:41 -0400 Subject: [PATCH 027/111] Fix path of internal endpoint for enterprise search crawler domain validation (#136400) --- .../server/routes/enterprise_search/crawler/crawler.test.ts | 2 +- .../server/routes/enterprise_search/crawler/crawler.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.test.ts b/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.test.ts index 3891f4023feb0..60be99f7a8073 100644 --- a/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.test.ts +++ b/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.test.ts @@ -430,7 +430,7 @@ describe('crawler routes', () => { it('creates a request to enterprise search', () => { expect(mockRequestHandler.createRequest).toHaveBeenCalledWith({ - path: '/api/ent/v1/internal/crawler/validate_url', + path: '/api/ent/v1/internal/crawler2/validate_url', }); }); diff --git a/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.ts b/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.ts index 652f72318074e..34138780583be 100644 --- a/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.ts +++ b/x-pack/plugins/enterprise_search/server/routes/enterprise_search/crawler/crawler.ts @@ -42,7 +42,7 @@ export function registerCrawlerRoutes(routeDependencies: RouteDependencies) { }, }, enterpriseSearchRequestHandler.createRequest({ - path: '/api/ent/v1/internal/crawler/validate_url', + path: '/api/ent/v1/internal/crawler2/validate_url', }) ); From ff2e2550ba4527540d54a07924926ec352ad42a9 Mon Sep 17 00:00:00 2001 From: Jack Date: Thu, 14 Jul 2022 11:02:25 -0400 Subject: [PATCH 028/111] [8.4] [Kubernetes Security] Rename charts toggle and fix count widgets alignment and tooltip (#136238) * Rename widgets toggle to charts toggle and update translation * Fix count widget small screen alignment and tooltip Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../common/translations.ts | 8 +- .../components/charts_toggle/index.test.tsx | 54 +++ .../public/components/charts_toggle/index.tsx | 29 ++ .../components/count_widget/index.test.tsx | 6 +- .../public/components/count_widget/index.tsx | 39 +-- .../public/components/count_widget/styles.ts | 2 - .../kubernetes_security_routes/index.tsx | 309 +++++++++--------- .../kubernetes_security_routes/styles.ts | 2 +- .../components/widgets_toggle/index.test.tsx | 57 ---- .../components/widgets_toggle/index.tsx | 29 -- .../public/utils/add_commas_to_number.test.ts | 35 ++ .../public/utils/add_commas_to_number.ts | 16 + 12 files changed, 310 insertions(+), 276 deletions(-) create mode 100644 x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.test.tsx create mode 100644 x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.tsx delete mode 100644 x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.test.tsx delete mode 100644 x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.tsx create mode 100644 x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.test.ts create mode 100644 x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.ts diff --git a/x-pack/plugins/kubernetes_security/common/translations.ts b/x-pack/plugins/kubernetes_security/common/translations.ts index d13bf8be60265..0264be3e55bd5 100644 --- a/x-pack/plugins/kubernetes_security/common/translations.ts +++ b/x-pack/plugins/kubernetes_security/common/translations.ts @@ -22,12 +22,12 @@ export const SEARCH_GROUP_SORT_BY = i18n.translate('xpack.kubernetesSecurity.sea defaultMessage: 'Sort by', }); -export const WIDGET_TOGGLE_SHOW = i18n.translate('xpack.kubernetesSecurity.widgetsToggle.show', { - defaultMessage: 'Show widgets', +export const CHART_TOGGLE_SHOW = i18n.translate('xpack.kubernetesSecurity.chartsToggle.show', { + defaultMessage: 'Show charts', }); -export const WIDGET_TOGGLE_HIDE = i18n.translate('xpack.kubernetesSecurity.widgetsToggle.hide', { - defaultMessage: 'Hide widgets', +export const CHART_TOGGLE_HIDE = i18n.translate('xpack.kubernetesSecurity.chartsToggle.hide', { + defaultMessage: 'Hide charts', }); export const COUNT_WIDGET_CLUSTERS = i18n.translate( diff --git a/x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.test.tsx b/x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.test.tsx new file mode 100644 index 0000000000000..e0d8249326d55 --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.test.tsx @@ -0,0 +1,54 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { AppContextTestRender, createAppRootMockRenderer } from '../../test'; +import { CHART_TOGGLE_SHOW, CHART_TOGGLE_HIDE } from '../../../common/translations'; +import { ChartsToggle, TOGGLE_TEST_ID } from '.'; + +describe('ChartsToggle component', () => { + let render: () => ReturnType; + let renderResult: ReturnType; + let mockedContext: AppContextTestRender; + const handleToggleHideCharts = jest.fn(); + + beforeEach(() => { + mockedContext = createAppRootMockRenderer(); + }); + + describe('When ChartsToggle is mounted', () => { + it('show "hide charts" text when shouldHideCharts is false', async () => { + renderResult = mockedContext.render( + + ); + + expect(renderResult.getByText(CHART_TOGGLE_HIDE)).toBeVisible(); + }); + it('show "show charts" text when shouldHideCharts is true', async () => { + renderResult = mockedContext.render( + + ); + + expect(renderResult.getByText(CHART_TOGGLE_SHOW)).toBeVisible(); + }); + it('shouldHideCharts defaults to false when not provided', async () => { + renderResult = mockedContext.render( + + ); + + expect(renderResult.getByText(CHART_TOGGLE_HIDE)).toBeVisible(); + }); + it('clicking the toggle fires the callback', async () => { + renderResult = mockedContext.render( + + ); + + renderResult.queryByTestId(TOGGLE_TEST_ID)?.click(); + expect(handleToggleHideCharts).toHaveBeenCalledTimes(1); + }); + }); +}); diff --git a/x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.tsx b/x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.tsx new file mode 100644 index 0000000000000..d38d1fed3c7aa --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/charts_toggle/index.tsx @@ -0,0 +1,29 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import React from 'react'; +import { EuiButtonEmpty } from '@elastic/eui'; +import { CHART_TOGGLE_SHOW, CHART_TOGGLE_HIDE } from '../../../common/translations'; + +export const TOGGLE_TEST_ID = 'kubernetesSecurity:chartToggle'; + +interface ChartsToggleDeps { + handleToggleHideCharts: () => void; + shouldHideCharts?: boolean; +} + +export const ChartsToggle = ({ + handleToggleHideCharts, + shouldHideCharts = false, +}: ChartsToggleDeps) => ( + + {shouldHideCharts ? CHART_TOGGLE_SHOW : CHART_TOGGLE_HIDE} + +); diff --git a/x-pack/plugins/kubernetes_security/public/components/count_widget/index.test.tsx b/x-pack/plugins/kubernetes_security/public/components/count_widget/index.test.tsx index 72d087f47d364..a0fbe2c90c690 100644 --- a/x-pack/plugins/kubernetes_security/public/components/count_widget/index.test.tsx +++ b/x-pack/plugins/kubernetes_security/public/components/count_widget/index.test.tsx @@ -8,7 +8,7 @@ import React from 'react'; import { AppContextTestRender, createAppRootMockRenderer } from '../../test'; import { GlobalFilter } from '../../types'; -import { CountWidget, LOADING_TEST_ID, TOOLTIP_TEST_ID } from '.'; +import { CountWidget, LOADING_TEST_ID, TOOLTIP_TEST_ID, VALUE_TEST_ID } from '.'; import { useFetchCountWidgetData } from './hooks'; import { fireEvent, waitFor } from '@testing-library/dom'; @@ -137,9 +137,9 @@ describe('CountWidget component', () => { isLoading: false, })); render(); - fireEvent.mouseOver(renderResult.getByText('Info')); + fireEvent.mouseOver(renderResult.getByTestId(VALUE_TEST_ID)); await waitFor(() => renderResult.getByTestId(TOOLTIP_TEST_ID)); - expect(renderResult.queryByText(MOCK_DATA_THOUSAND.pages[0])).toBeTruthy(); + expect(renderResult.queryByText('5,236')).toBeTruthy(); }); }); }); diff --git a/x-pack/plugins/kubernetes_security/public/components/count_widget/index.tsx b/x-pack/plugins/kubernetes_security/public/components/count_widget/index.tsx index 5e5f5eacc374f..534187057b5e9 100644 --- a/x-pack/plugins/kubernetes_security/public/components/count_widget/index.tsx +++ b/x-pack/plugins/kubernetes_security/public/components/count_widget/index.tsx @@ -6,9 +6,10 @@ */ import React, { useMemo } from 'react'; -import { EuiFlexGroup, EuiFlexItem, EuiText, EuiLoadingSpinner, EuiIconTip } from '@elastic/eui'; +import { EuiText, EuiLoadingSpinner, EuiToolTip } from '@elastic/eui'; import { useStyles } from './styles'; import type { IndexPattern, GlobalFilter } from '../../types'; +import { addCommasToNumber } from '../../utils/add_commas_to_number'; import { addTimerangeToQuery } from '../../utils/add_timerange_to_query'; import { useFetchCountWidgetData } from './hooks'; import { addResourceTypeToFilterQuery, numberFormatter } from './helpers'; @@ -16,6 +17,7 @@ import { COUNT_WIDGET_KEY_PODS } from '../../../common/constants'; export const LOADING_TEST_ID = 'kubernetesSecurity:countWidgetLoading'; export const TOOLTIP_TEST_ID = 'kubernetesSecurity:countWidgetTooltip'; +export const VALUE_TEST_ID = 'kubernetesSecurity:countWidgetValue'; export interface CountWidgetDeps { title: string; @@ -60,26 +62,21 @@ export const CountWidget = ({ return (
-
- {title} - -
- - - - {isLoading ? ( - - ) : ( - formattedNumber - )} - - - +
{title}
+ + + {isLoading ? ( + + ) : ( + formattedNumber + )} + +
); }; diff --git a/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts b/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts index abd89925b5cf3..b02f30fa952fa 100644 --- a/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts +++ b/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts @@ -31,8 +31,6 @@ export const useStyles = () => { const dataInfo: CSSObject = { marginBottom: size.xs, - display: 'flex', - alignItems: 'center', height: '18px', fontSize: size.l, fontWeight: font.weight.bold, diff --git a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx index 182873f954d8d..7be342a782d98 100644 --- a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx +++ b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx @@ -36,7 +36,7 @@ import { AggregateResult } from '../../../common/types/aggregate'; import { useLastUpdated } from '../../hooks'; import { useStyles } from './styles'; import { TreeViewContainer } from '../tree_view_container'; -import { WidgetsToggle } from '../widgets_toggle'; +import { ChartsToggle } from '../charts_toggle'; import { COUNT_WIDGET_CLUSTERS, COUNT_WIDGET_NAMESPACE, @@ -51,7 +51,7 @@ const KubernetesSecurityRoutesComponent = ({ globalFilter, renderSessionsView, }: KubernetesSecurityDeps) => { - const [shouldHideWidgets, setShouldHideWidgets] = useLocalStorage( + const [shouldHideCharts, setShouldHideCharts] = useLocalStorage( LOCAL_STORAGE_HIDE_WIDGETS_KEY, false ); @@ -82,9 +82,9 @@ const KubernetesSecurityRoutesComponent = ({ [] ); - const handleToggleHideWidgets = useCallback(() => { - setShouldHideWidgets(!shouldHideWidgets); - }, [setShouldHideWidgets, shouldHideWidgets]); + const handleToggleHideCharts = useCallback(() => { + setShouldHideCharts(!shouldHideCharts); + }, [setShouldHideCharts, shouldHideCharts]); return ( @@ -98,171 +98,162 @@ const KubernetesSecurityRoutesComponent = ({
{lastUpdated}
-
- {!shouldHideWidgets && ( + {!shouldHideCharts && ( <> - + - - - - - - - - - - - - - - - - - + - - - - - - - - } + + + + + + + + + + + + + + + + + + + - - } - widgetKey="sessionsPercentage" - indexPattern={indexPattern} - globalFilter={globalFilter} - dataValueMap={{ - true: { - name: i18n.translate( - 'xpack.kubernetesSecurity.sessionChart.interactive', - { - defaultMessage: 'Interactive', - } - ), - fieldName: ENTRY_LEADER_INTERACTIVE, - color: euiThemeVars.euiColorVis0, - }, - false: { - name: i18n.translate( - 'xpack.kubernetesSecurity.sessionChart.nonInteractive', - { - defaultMessage: 'Non-interactive', - } - ), - fieldName: ENTRY_LEADER_INTERACTIVE, - color: euiThemeVars.euiColorVis1, - shouldHideFilter: true, - }, - }} - groupedBy={ENTRY_LEADER_INTERACTIVE} - countBy={ENTRY_LEADER_ENTITY_ID} - onReduce={onReduceInteractiveAggs} - /> - - - - - - - - } + } + /> + + } + widgetKey="sessionsPercentage" + indexPattern={indexPattern} + globalFilter={globalFilter} + dataValueMap={{ + true: { + name: i18n.translate( + 'xpack.kubernetesSecurity.sessionChart.interactive', + { + defaultMessage: 'Interactive', + } + ), + fieldName: ENTRY_LEADER_INTERACTIVE, + color: euiThemeVars.euiColorVis0, + }, + false: { + name: i18n.translate( + 'xpack.kubernetesSecurity.sessionChart.nonInteractive', + { + defaultMessage: 'Non-interactive', + } + ), + fieldName: ENTRY_LEADER_INTERACTIVE, + color: euiThemeVars.euiColorVis1, + shouldHideFilter: true, + }, + }} + groupedBy={ENTRY_LEADER_INTERACTIVE} + countBy={ENTRY_LEADER_ENTITY_ID} + onReduce={onReduceInteractiveAggs} + /> + + + + + + + - - } - widgetKey="rootLoginPercentage" - indexPattern={indexPattern} - globalFilter={globalFilter} - dataValueMap={{ - '0': { - name: i18n.translate('xpack.kubernetesSecurity.entryUserChart.root', { - defaultMessage: 'Root', - }), - fieldName: ENTRY_LEADER_USER_ID, - color: euiThemeVars.euiColorVis2, - }, - nonRoot: { - name: i18n.translate( - 'xpack.kubernetesSecurity.entryUserChart.nonRoot', - { - defaultMessage: 'Non-root', - } - ), - fieldName: ENTRY_LEADER_USER_ID, - color: euiThemeVars.euiColorVis3, - shouldHideFilter: true, - }, - }} - groupedBy={ENTRY_LEADER_USER_ID} - countBy={ENTRY_LEADER_ENTITY_ID} - onReduce={onReduceRootAggs} - /> - - + } + /> + + } + widgetKey="rootLoginPercentage" + indexPattern={indexPattern} + globalFilter={globalFilter} + dataValueMap={{ + '0': { + name: i18n.translate('xpack.kubernetesSecurity.entryUserChart.root', { + defaultMessage: 'Root', + }), + fieldName: ENTRY_LEADER_USER_ID, + color: euiThemeVars.euiColorVis2, + }, + nonRoot: { + name: i18n.translate('xpack.kubernetesSecurity.entryUserChart.nonRoot', { + defaultMessage: 'Non-root', + }), + fieldName: ENTRY_LEADER_USER_ID, + color: euiThemeVars.euiColorVis3, + shouldHideFilter: true, + }, + }} + groupedBy={ENTRY_LEADER_USER_ID} + countBy={ENTRY_LEADER_ENTITY_ID} + onReduce={onReduceRootAggs} + /> diff --git a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts index 889f99715393b..49e41b4cbca38 100644 --- a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts +++ b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts @@ -59,7 +59,7 @@ export const useStyles = () => { }; const countWidgets: CSSObject = { - margin: size.l, + marginBottom: size.l, }; const widgetHolder: CSSObject = { diff --git a/x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.test.tsx b/x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.test.tsx deleted file mode 100644 index cb2db24d28faf..0000000000000 --- a/x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.test.tsx +++ /dev/null @@ -1,57 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import React from 'react'; -import { AppContextTestRender, createAppRootMockRenderer } from '../../test'; -import { WIDGET_TOGGLE_SHOW, WIDGET_TOGGLE_HIDE } from '../../../common/translations'; -import { WidgetsToggle, TOGGLE_TEST_ID } from '.'; - -describe('WidgetsToggle component', () => { - let render: () => ReturnType; - let renderResult: ReturnType; - let mockedContext: AppContextTestRender; - const handleToggleHideWidgets = jest.fn(); - - beforeEach(() => { - mockedContext = createAppRootMockRenderer(); - }); - - describe('When PercentWidget is mounted', () => { - it('show "hide widgets" text when shouldHideWidgets is false', async () => { - renderResult = mockedContext.render( - - ); - - expect(renderResult.getByText(WIDGET_TOGGLE_HIDE)).toBeVisible(); - }); - it('show "show widgets" text when shouldHideWidgets is true', async () => { - renderResult = mockedContext.render( - - ); - - expect(renderResult.getByText(WIDGET_TOGGLE_SHOW)).toBeVisible(); - }); - it('shouldHideWidgets defaults to false when not provided', async () => { - renderResult = mockedContext.render( - - ); - - expect(renderResult.getByText(WIDGET_TOGGLE_HIDE)).toBeVisible(); - }); - it('clicking the toggle fires the callback', async () => { - renderResult = mockedContext.render( - - ); - - renderResult.queryByTestId(TOGGLE_TEST_ID)?.click(); - expect(handleToggleHideWidgets).toHaveBeenCalledTimes(1); - }); - }); -}); diff --git a/x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.tsx b/x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.tsx deleted file mode 100644 index 5a31b8504f8ab..0000000000000 --- a/x-pack/plugins/kubernetes_security/public/components/widgets_toggle/index.tsx +++ /dev/null @@ -1,29 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ -import React from 'react'; -import { EuiButtonEmpty } from '@elastic/eui'; -import { WIDGET_TOGGLE_SHOW, WIDGET_TOGGLE_HIDE } from '../../../common/translations'; - -export const TOGGLE_TEST_ID = 'kubernetesSecurity:widgetToggle'; - -interface WidgetsToggleDeps { - handleToggleHideWidgets: () => void; - shouldHideWidgets?: boolean; -} - -export const WidgetsToggle = ({ - handleToggleHideWidgets, - shouldHideWidgets = false, -}: WidgetsToggleDeps) => ( - - {shouldHideWidgets ? WIDGET_TOGGLE_SHOW : WIDGET_TOGGLE_HIDE} - -); diff --git a/x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.test.ts b/x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.test.ts new file mode 100644 index 0000000000000..03faf16921c1b --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.test.ts @@ -0,0 +1,35 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { addCommasToNumber } from './add_commas_to_number'; + +describe('addCommasToNumber(num)', () => { + it('works for a number without needing a comma', () => { + expect(addCommasToNumber(123)).toEqual('123'); + }); + it('works for a number that needs a comma', () => { + expect(addCommasToNumber(1234)).toEqual('1,234'); + }); + it('works for a number that needs multiple commas', () => { + expect(addCommasToNumber(123456789)).toEqual('123,456,789'); + }); + it('works for negative number', () => { + expect(addCommasToNumber(-10)).toEqual('-10'); + }); + it('works for negative number with commas', () => { + expect(addCommasToNumber(-10000)).toEqual('-10,000'); + }); + it('works for NaN', () => { + expect(addCommasToNumber(NaN)).toEqual('NaN'); + }); + it('works for Infinity', () => { + expect(addCommasToNumber(Infinity)).toEqual('Infinity'); + }); + it('works for zero', () => { + expect(addCommasToNumber(0)).toEqual('0'); + }); +}); diff --git a/x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.ts b/x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.ts new file mode 100644 index 0000000000000..3e440ab8c9226 --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/utils/add_commas_to_number.ts @@ -0,0 +1,16 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +/** + * Add commas as thousands separators to a number. + * + * @param {Number} num + * @return {String} num in string with commas as thousands separaters + */ +export function addCommasToNumber(num: number) { + return num.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ','); +} From 495d64694b7d7ddbb97d9f1e7f1a22bd9e917030 Mon Sep 17 00:00:00 2001 From: Jonathan Budzenski Date: Thu, 14 Jul 2022 10:22:37 -0500 Subject: [PATCH 029/111] skip suite failing es promotion. #136412 --- x-pack/test/api_integration/apis/uptime/rest/index_status.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/x-pack/test/api_integration/apis/uptime/rest/index_status.ts b/x-pack/test/api_integration/apis/uptime/rest/index_status.ts index 620621274a078..6526278bb8a46 100644 --- a/x-pack/test/api_integration/apis/uptime/rest/index_status.ts +++ b/x-pack/test/api_integration/apis/uptime/rest/index_status.ts @@ -10,7 +10,8 @@ import { FtrProviderContext } from '../../../ftr_provider_context'; import { expectFixtureEql } from './helper/expect_fixture_eql'; export default function ({ getService }: FtrProviderContext) { - describe('docCount query', () => { + // Failing ES Promotion: https://github.com/elastic/kibana/issues/136412 + describe.skip('docCount query', () => { const supertest = getService('supertest'); it(`will fetch the index's count`, async () => { From 2aa000b9ea54784716bc7d5656386685b29a9c63 Mon Sep 17 00:00:00 2001 From: Tre Date: Thu, 14 Jul 2022 16:31:35 +0100 Subject: [PATCH 030/111] [Archive Migrations] x-pack..lens/reporting (#136262) --- .../apps/lens/group3/lens_reporting.ts | 8 +- .../es_archives/lens/reporting/data.json.gz | Bin 4542 -> 0 bytes .../es_archives/lens/reporting/mappings.json | 1261 ----------------- .../fixtures/kbn_archiver/lens/reporting.json | 491 +++++++ 4 files changed, 496 insertions(+), 1264 deletions(-) delete mode 100644 x-pack/test/functional/es_archives/lens/reporting/data.json.gz delete mode 100644 x-pack/test/functional/es_archives/lens/reporting/mappings.json create mode 100644 x-pack/test/functional/fixtures/kbn_archiver/lens/reporting.json diff --git a/x-pack/test/functional/apps/lens/group3/lens_reporting.ts b/x-pack/test/functional/apps/lens/group3/lens_reporting.ts index 2cbb55ae03d97..dd54475efff32 100644 --- a/x-pack/test/functional/apps/lens/group3/lens_reporting.ts +++ b/x-pack/test/functional/apps/lens/group3/lens_reporting.ts @@ -11,13 +11,15 @@ import { FtrProviderContext } from '../../../ftr_provider_context'; export default function ({ getService, getPageObjects }: FtrProviderContext) { const PageObjects = getPageObjects(['common', 'dashboard', 'reporting', 'timePicker']); const es = getService('es'); - const esArchiver = getService('esArchiver'); + const kibanaServer = getService('kibanaServer'); const listingTable = getService('listingTable'); const security = getService('security'); describe('lens reporting', () => { before(async () => { - await esArchiver.loadIfNeeded('x-pack/test/functional/es_archives/lens/reporting'); + await kibanaServer.importExport.load( + 'x-pack/test/functional/fixtures/kbn_archiver/lens/reporting' + ); await PageObjects.timePicker.setDefaultAbsoluteRangeViaUiSettings(); await security.testUser.setRoles( [ @@ -30,7 +32,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { }); after(async () => { - await esArchiver.unload('x-pack/test/functional/es_archives/lens/reporting'); + await kibanaServer.savedObjects.cleanStandardList(); await PageObjects.timePicker.resetDefaultAbsoluteRangeViaUiSettings(); await es.deleteByQuery({ index: '.reporting-*', diff --git a/x-pack/test/functional/es_archives/lens/reporting/data.json.gz b/x-pack/test/functional/es_archives/lens/reporting/data.json.gz deleted file mode 100644 index 3c06824f606462a44aabd3a24b000cc4a6975cd8..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4542 zcmd7U^&=b(z<_ZM)6+41rlz~5nQnHv9d1n5u!)J&v14jDo#%@=)7{f?a>p?}Jw4v{ z{V(3e&~>zz5V&w zVdmQDf^(q6?N)+lEbYVQgEoNQ%A(-Ss0wn^|I2m<#d$X|rC}edDzzAIF3;Ghv3-t| zcCL-yv}5`V-q`r!J2!QTTLm4ndXtAlCES`j{7t)xlB**Aztwq% z0tSvudN<{{SNd~FYJ{@(oWEr3DvUk=3b92!Z+Cbd62Rsn-ll!i8L60h(1>|0oALgD zfJu3pI@NS#^tX>&e{a7po8%$5DYc_YsLNo}7e25skmiP_w`uV#(Iyx+4XGy22o$b@ zR*}@1QYiDaX*XE~6phZngtA|$ieMY6J8{^RkOUD|N+!9?36GiEey_o|PHM9cRXDa3 zLcMDUrRXz@UDi=}64djh_^f2XvY9;zdKKRX&1i+HR8vG8Mf!IVVxR(cfXXC{b=7pQ zkM!HwV)?WkH@KXnOcIfksLfA?4@%(l*nUqDXC_pBd zXiMmcGM>>`EJ?JOpEgga3(L9-x4#2tkuJibS?`h-CWMvOH)hC^0~n!;&}r6#)53_H zOu%mu`7BQXsyW8`NL)<;riOrA;j&3EcDlBC2Hh>q7(U%;Wi))Z9Ve6^(U{#>B;$XU7O znW-kqUKw9l&uiWg71d~^cUD@*X~QP@N7Dn`RCYY2>*R7^g5%q`xOMIGxB2?@OfEj$ue)wJ$|H1@F46l%&xEK?vg6{- z#XEMgk4YJW>LK$O#LBa|=%?1-%nsDM7)1ZkR>j3RVslD7%#84h$$wLH9`-GV9^JE_ z65RZn^7d3GeJs5kR*yOmFANpEe2Vf-JXTkn>hwN!?*^8a{Hr>3D)x-8u6t zp?N@R8tZ-(motibe7Df}xNOWVRru^+&1}H7VwB4(NgX?RT&fX#R|d4N&ucV(4!)Hu zM~VMxKC>gt8uKVu<=IpFF%6Tz{awsA#wjcKsGeOYmgQ1rNH*sYb6%{oR{h?(d>NV6 zAfR>+j!8Eb^JoFb(O>$sKm}X0scr|uNX@Uyb($MX`ApYeXLuv+_$5HCwLZg*`SNBS z;TGz2HPuR$S~eD^AH3ZQ-*m?}dpx@4Qj8v(os*2&E?-ux4zbLIjao_Gh)pm?yMKS= z8R6sZpiB0h<#kLtT>1>DyILP;dDEnHU2(VOQHa2RMDTp#D@Fx)4 zyuih`#jR5?<&*osRY&LafuZeKpkP9J1aNua?DmuE-*1B*-9@X95e#0Dp7^p2Y)ZD| zST+?3r}9jImjp$ss>7wi*-W}mx_IoX3#D--l$(`vw)8~mCrehJK~(yYqqf&q_GJm- zi{m6BAq1L(`f)XXobJ;!ctwktgxVe6JHg#Y9%Col)sNm|>_@JSmi#UttG9pWZLDf& zs>JoSBeEupRBf0ObFep=Ezka;Kat~KcCk`jxDzMn^9|y)g;uqTt>(U%ocHe>ehkhQ zCoCEKnb-HKBem$&P79|Ve7=}1q2wVDR4`?x^*v*U`t<|i+@5N1d);L)G>pJz{hD;u zS77g6??RbvH?)e)_0|i}(QWq$b$5P_X&*tGPO}n2NI48!+e@f1ii>5(6Z}Cg<|e2a z)*KZPMQT{%Hf~FHdSIvyoT3ePLVB~Gl2$?@#OZ~ z(wyVa(^v0HN2t#rX=_bvatJ3i$CE*U(AjY7%?av2>nc8cwI-emL~~MD?}jY$d$Hqe zndAw%iWTk>5A@%L3u9?sd)UW70l3V>(UJQW`g``{i@#-aLAqTx+Bw3X#Nz>7eJOZ1 zKl%zB>d(!59!i8)mSU(ES1i{wHO{8?zgBZCXvNOX%%l*zKYCO7}8663mHMY{e-(ZO-fhFfiwHs&JUweMGd&#(Rs+AC+VSuqGO zbI5($S@t4;leDU43|9S&uF%4VbAl!%mU2J;zO|xf|AiNbaG3r>;v$XAhnErddx82Z z_n?O(0wJUborGsAR}635hCo|9C@(WB*76p@XbI-DBMCDY=Q|YDkLFh%gpk|LxX(KT z!H}s%8Pu;7X>9kp1pM8|*8c#}%wZ>>u)@iZ?;o5LXMf6m7bmKk{tL0mWJ5dWbDr;j z&}+?c@p85DE)!{UtFFq_*0;9i*UWo@_@oXoTEp`OyZ`E)<;h7u+Mtgz)V`Jt2<5lw zuU4|r@`a^*szE9Pj=C4^yG&HESTBIjV9(&#ICLsx@_ex++rQ{jC^?0X42c~RBAjlR`d#d? zS?_UiY0J32r$<&vQTO*zGC8pvTX zB%-;#eqQ7KB6!4Qz%8%Z5;TXjeaG{GG4G`OY*|T~Xa>za$BGGUHZ=^Y+%Ty~ZLY{m z33bs!d(7V7J*K_y=hhN~w2-B5@4Ck2B9wly4K7N2EZR4W91Af;3(G8z62_{k(y_DJ zPx(iJE$D*_R3oX#Syy0f|REzn**v9ciO?-VA{#6zhnhz zL$5Y?cJ4r}{!H;pH+5F+(x)DQs01IQsKL&$q^K%;QSNmBhM{OcMd!I6&B>SvLET=7ylAm3`+hj-Ia~y4Swi%8*k!}M= zk*|=Or#-`Xw6k3bjGr}lzIcwv;AKjYdPD1Rs+NAW@r(=DC(o|}cx$PSK!B8 zg-&yUbwaX2@Q#gRn?7WrJiqF#GNEtR3SCutxY2c!Pd` zvm8f`>ZSdDAeJ0@Are9{g~Hi;$sBO(yEHHt1UYSCUPIpJfRh7ja~*)H}X?acvT6l*eUvIxHuX7##;Rr=G0RDgRsqutSRAu3!07 zum5?NuNQfeGTUYK5VKb5z6LYE&H7;R=eY|~EC%t!;jp_&a^~1KSyspn_)!>qXrsIr zL0|4=Nxii6`>v;1o}7FguY6xM8lWjptY}4kSA%O4T<+Hk3>v7w8TRv-^NHM~^px?- z!@m(M@A1{$egTiS9+n0wtOtI-S6O)57H(eKcD8xEfa_`3LB+G7&chk*;-#(FMruCq zLGwhIKd+Oqui+Lc$^-3rx}Jm z>!?xLoe}Tvm+Osb=XYW6!(fChP_8=Illzv zM+PZfipJ2Z4ab8BzK)yPCRIm|+g}~K>hv-@0ZwkIf>nP!C=+%7@!{Oo3eYJQky|N( zc~`xB{^5bq>48yI^Me<2sd2OCxESpi1!=rnc1ryyyYL+rwm)eP#R`obkb+XX2+xy? z3l0ND94;a8n!lBhGUW%fmKQx6%AbUlen~6>9QyoJeiggG(-7SwDdOhsYY9oa+cz)H z(HounyPi`K3!Ik;&iQn!LrdWh)$lkMl3ht;PoIn2f*vto(;{CHc)MZaTeUgiW-&5s zev7YGPS^!=R_ETZ6x82Qjol0YtE$2uF7{`QWpUd~Xs8cOG=d7)j{;T5FT*8|o~0i% zD&Wm~r;V6WMKGnrO*h~~tLPRvbf^87ce2{1B}Wv-%)pMS^^?I8P_juK*R6Fzof{C4 z!w(0ktcm4;zT*ChsSLfr0TZOTc)Ma`ITK`jtG>ae ze$q`Ly|+dt6@We~X&j!M3M8w6oF44VFVs~C2ODU%KGidHWYIW&zK_ES?dueiC%8e# zTtW8smRjB$T-!o>56?^NmoSsmqG9$xG@uKN+cW#|xasx46{*}#j=_Xj|8z6|_Sx2E z0$U>If7&0(qJfG`Ay8(9JEEPOIMM!W*W)QMvOx#2DLI&pt$o3Vy~UMJ*-OQ+eB;io5T=>A#4J9Mx60DdNz`Ph%|Thk+%lW^)GWJ zpXV371wP8L`@E`6w1NOh3AH;AKdZc`z6!5Zk*#Z_=y Date: Thu, 14 Jul 2022 10:45:25 -0500 Subject: [PATCH 031/111] Remove api-{extractor,documenter} (#136357) With the merges of https://github.com/elastic/kibana/pull/134313 and https://github.com/elastic/kibana/pull/135163 we no longer use these dependencies. --- api-documenter.json | 4 - package.json | 2 - src/dev/precommit_hook/casing_check_config.js | 3 - yarn.lock | 171 ++---------------- 4 files changed, 12 insertions(+), 168 deletions(-) delete mode 100644 api-documenter.json diff --git a/api-documenter.json b/api-documenter.json deleted file mode 100644 index a2303b939c8ec..0000000000000 --- a/api-documenter.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "newlineKind": "lf", - "outputTarget": "markdown" -} diff --git a/package.json b/package.json index 44111b5550366..5f7e4a706b826 100644 --- a/package.json +++ b/package.json @@ -609,8 +609,6 @@ "@kbn/type-summarizer-core": "link:bazel-bin/packages/kbn-type-summarizer-core", "@loaders.gl/polyfills": "^2.3.5", "@mapbox/vector-tile": "1.3.1", - "@microsoft/api-documenter": "7.13.68", - "@microsoft/api-extractor": "7.18.19", "@octokit/rest": "^16.35.0", "@openpgp/web-stream-tools": "^0.0.10", "@percy/agent": "^0.28.6", diff --git a/src/dev/precommit_hook/casing_check_config.js b/src/dev/precommit_hook/casing_check_config.js index b16dc39c4f50b..0c65b924f14b1 100644 --- a/src/dev/precommit_hook/casing_check_config.js +++ b/src/dev/precommit_hook/casing_check_config.js @@ -53,9 +53,6 @@ export const IGNORE_FILE_GLOBS = [ '**/preview-body.html', '**/preview-head.html', - // filename required by api-extractor - 'api-documenter.json', - // filename must match upstream filenames from lodash 'packages/elastic-safer-lodash-set/**/*', diff --git a/yarn.lock b/yarn.lock index 25e8f56335861..20a306f722661 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4013,61 +4013,6 @@ resolved "https://registry.yarnpkg.com/@mdx-js/util/-/util-1.6.22.tgz#219dfd89ae5b97a8801f015323ffa4b62f45718b" integrity sha512-H1rQc1ZOHANWBvPcW+JpGwr+juXSxM8Q8YCkm3GhZd8REu1fHR3z99CErO1p9pkcfcxZnMdIZdIsXkOHY0NilA== -"@microsoft/api-documenter@7.13.68": - version "7.13.68" - resolved "https://registry.yarnpkg.com/@microsoft/api-documenter/-/api-documenter-7.13.68.tgz#c1e144764cac0684adefe78fd848d78c3f374681" - integrity sha512-cRjwK1TDyGxFGgCsRG8G0Yi3Z4akvfWgw1pWAxKFbm7ajlQQGZcHPnb+n4lKlSeQ5g/cxc7hcdw54Mvisne9Bg== - dependencies: - "@microsoft/api-extractor-model" "7.13.16" - "@microsoft/tsdoc" "0.13.2" - "@rushstack/node-core-library" "3.43.2" - "@rushstack/ts-command-line" "4.10.4" - colors "~1.2.1" - js-yaml "~3.13.1" - resolve "~1.17.0" - -"@microsoft/api-extractor-model@7.13.16": - version "7.13.16" - resolved "https://registry.yarnpkg.com/@microsoft/api-extractor-model/-/api-extractor-model-7.13.16.tgz#1d67541ebbcea32672c5fdd9392dc1579b2fc23a" - integrity sha512-ttdxVXsTWL5dd26W1YNLe3LgDsE0EE273aZlcLe58W0opymBybCYU1Mn+OHQM8BuErrdvdN8LdpWAAbkiOEN/Q== - dependencies: - "@microsoft/tsdoc" "0.13.2" - "@microsoft/tsdoc-config" "~0.15.2" - "@rushstack/node-core-library" "3.43.2" - -"@microsoft/api-extractor@7.18.19": - version "7.18.19" - resolved "https://registry.yarnpkg.com/@microsoft/api-extractor/-/api-extractor-7.18.19.tgz#f09afc1c210aa67e2f3f34b0a68281a12f144541" - integrity sha512-aY+/XR7PtQXtnqNPFRs3/+iVRlQJpo6uLTjO2g7PqmnMywl3GBU3bCgAlV/khZtAQbIs6Le57XxmSE6rOqbcfg== - dependencies: - "@microsoft/api-extractor-model" "7.13.16" - "@microsoft/tsdoc" "0.13.2" - "@microsoft/tsdoc-config" "~0.15.2" - "@rushstack/node-core-library" "3.43.2" - "@rushstack/rig-package" "0.3.5" - "@rushstack/ts-command-line" "4.10.4" - colors "~1.2.1" - lodash "~4.17.15" - resolve "~1.17.0" - semver "~7.3.0" - source-map "~0.6.1" - typescript "~4.4.2" - -"@microsoft/tsdoc-config@~0.15.2": - version "0.15.2" - resolved "https://registry.yarnpkg.com/@microsoft/tsdoc-config/-/tsdoc-config-0.15.2.tgz#eb353c93f3b62ab74bdc9ab6f4a82bcf80140f14" - integrity sha512-mK19b2wJHSdNf8znXSMYVShAHktVr/ib0Ck2FA3lsVBSEhSI/TfXT7DJQkAYgcztTuwazGcg58ZjYdk0hTCVrA== - dependencies: - "@microsoft/tsdoc" "0.13.2" - ajv "~6.12.6" - jju "~1.4.0" - resolve "~1.19.0" - -"@microsoft/tsdoc@0.13.2": - version "0.13.2" - resolved "https://registry.yarnpkg.com/@microsoft/tsdoc/-/tsdoc-0.13.2.tgz#3b0efb6d3903bd49edb073696f60e90df08efb26" - integrity sha512-WrHvO8PDL8wd8T2+zBGKrMwVL5IyzR3ryWUsl0PXgEV0QHup4mTLi0QcATefGI6Gx9Anu7vthPyyyLpY0EpiQg== - "@mrmlnc/readdir-enhanced@^2.2.1": version "2.2.1" resolved "https://registry.yarnpkg.com/@mrmlnc/readdir-enhanced/-/readdir-enhanced-2.2.1.tgz#524af240d1a360527b730475ecfa1344aa540dde" @@ -4731,39 +4676,6 @@ redux-thunk "^2.3.0" reselect "^4.0.0" -"@rushstack/node-core-library@3.43.2": - version "3.43.2" - resolved "https://registry.yarnpkg.com/@rushstack/node-core-library/-/node-core-library-3.43.2.tgz#f067371a94fd92ed8f9d9aa8201c5e9e17a19f0f" - integrity sha512-b7AEhSf6CvZgvuDcWMFDeKx2mQSn9AVnMQVyxNxFeHCtLz3gJicqCOlw2GOXM8HKh6PInLdil/NVCDcstwSrIw== - dependencies: - "@types/node" "12.20.24" - colors "~1.2.1" - fs-extra "~7.0.1" - import-lazy "~4.0.0" - jju "~1.4.0" - resolve "~1.17.0" - semver "~7.3.0" - timsort "~0.3.0" - z-schema "~3.18.3" - -"@rushstack/rig-package@0.3.5": - version "0.3.5" - resolved "https://registry.yarnpkg.com/@rushstack/rig-package/-/rig-package-0.3.5.tgz#7ddab0994647837bab8fdef26f990f1774d82e78" - integrity sha512-CvqWw+E81U5lRBN/lUj7Ngr/XQa/PPb2jAS5QcLP7WL+IMUl+3+Cc2qYrsDoB4zke81kz+usWGmBQpBzGMLmAA== - dependencies: - resolve "~1.17.0" - strip-json-comments "~3.1.1" - -"@rushstack/ts-command-line@4.10.4": - version "4.10.4" - resolved "https://registry.yarnpkg.com/@rushstack/ts-command-line/-/ts-command-line-4.10.4.tgz#05142b74e5cb207d3dd9b935c82f80d7fcb68042" - integrity sha512-4T5ao4UgDb6LmiRj4GumvG3VT/p6RSMgl7TN7S58ifaAGN2GeTNBajFCDdJs9QQP0d/4tA5p0SFzT7Ps5Byirg== - dependencies: - "@types/argparse" "1.0.38" - argparse "~1.0.9" - colors "~1.2.1" - string-argv "~0.3.1" - "@samverschueren/stream-to-observable@^0.3.0": version "0.3.0" resolved "https://registry.yarnpkg.com/@samverschueren/stream-to-observable/-/stream-to-observable-0.3.0.tgz#ecdf48d532c58ea477acfcab80348424f8d0662f" @@ -6039,11 +5951,6 @@ dependencies: "@types/glob" "*" -"@types/argparse@1.0.38": - version "1.0.38" - resolved "https://registry.yarnpkg.com/@types/argparse/-/argparse-1.0.38.tgz#a81fd8606d481f873a3800c6ebae4f1d768a56a9" - integrity sha512-ebDJ9b0e702Yr7pWgB0jzm+CX4Srzz8RcXtLJDJB+BSccqMa36uyH/zUsSYao5+BD1ytv3k3rPYCq4mAE1hsXA== - "@types/aria-query@^4.2.0": version "4.2.0" resolved "https://registry.yarnpkg.com/@types/aria-query/-/aria-query-4.2.0.tgz#14264692a9d6e2fa4db3df5e56e94b5e25647ac0" @@ -7663,7 +7570,7 @@ dependencies: "@types/node" "*" -"@types/node@*", "@types/node@12.20.24", "@types/node@16.11.41", "@types/node@>= 8", "@types/node@>=12.12.47", "@types/node@>=13.7.0", "@types/node@>=8.9.0", "@types/node@^10.1.0", "@types/node@^14.0.10", "@types/node@^14.14.31": +"@types/node@*", "@types/node@16.11.41", "@types/node@>= 8", "@types/node@>=12.12.47", "@types/node@>=13.7.0", "@types/node@>=8.9.0", "@types/node@^10.1.0", "@types/node@^14.0.10", "@types/node@^14.14.31": version "16.11.41" resolved "https://registry.yarnpkg.com/@types/node/-/node-16.11.41.tgz#88eb485b1bfdb4c224d878b7832239536aa2f813" integrity sha512-mqoYK2TnVjdkGk8qXAVGc/x9nSaTpSrFaGFm43BUH3IdoBV0nta6hYaGmdOvIMlbHJbUEVen3gvwpwovAZKNdQ== @@ -8959,7 +8866,7 @@ ajv@^6.1.0, ajv@^6.10.0, ajv@^6.10.2, ajv@^6.12.2, ajv@^6.12.4, ajv@^6.5.5: json-schema-traverse "^0.4.1" uri-js "^4.2.2" -ajv@^6.11.0, ajv@^6.12.5, ajv@~6.12.6: +ajv@^6.11.0, ajv@^6.12.5: version "6.12.6" resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.6.tgz#baf5a62e802b07d977034586f8c3baf5adf26df4" integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== @@ -9292,7 +9199,7 @@ arg@^4.1.0: resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089" integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA== -argparse@^1.0.7, argparse@~1.0.9: +argparse@^1.0.7: version "1.0.10" resolved "https://registry.yarnpkg.com/argparse/-/argparse-1.0.10.tgz#bcd6791ea5ae09725e17e5ad988134cd40b3d911" integrity sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg== @@ -11542,11 +11449,6 @@ colors@1.4.0, colors@^1.3.2: resolved "https://registry.yarnpkg.com/colors/-/colors-1.4.0.tgz#c50491479d4c1bdaed2c9ced32cf7c7dc2360f78" integrity sha512-a+UqTh4kgZg/SlGvfbzDHpgRu7AAQOmmqRHJnxhRZICKFUT91brVhNNt58CMWU9PsBbv3PDCZUHbVxuDiH2mtA== -colors@~1.2.1: - version "1.2.5" - resolved "https://registry.yarnpkg.com/colors/-/colors-1.2.5.tgz#89c7ad9a374bc030df8013241f68136ed8835afc" - integrity sha512-erNRLao/Y3Fv54qUa0LBB+//Uf3YwMUmdJinN20yMXm9zdKKqH9wt7R9IIVZ+K7ShzfpLV/Zg8+VyrBJYB4lpg== - colorspace@1.1.x: version "1.1.1" resolved "https://registry.yarnpkg.com/colorspace/-/colorspace-1.1.1.tgz#9ac2491e1bc6f8fb690e2176814f8d091636d972" @@ -15805,7 +15707,7 @@ fs-extra@^10.0.0: jsonfile "^6.0.1" universalify "^2.0.0" -fs-extra@^7.0.0, fs-extra@^7.0.1, fs-extra@~7.0.1: +fs-extra@^7.0.0, fs-extra@^7.0.1: version "7.0.1" resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== @@ -17493,7 +17395,7 @@ import-lazy@^2.1.0: resolved "https://registry.yarnpkg.com/import-lazy/-/import-lazy-2.1.0.tgz#05698e3d45c88e8d7e9d92cb0584e77f096f3e43" integrity sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM= -import-lazy@^4.0.0, import-lazy@~4.0.0: +import-lazy@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/import-lazy/-/import-lazy-4.0.0.tgz#e8eb627483a0a43da3c03f3e35548be5cb0cc153" integrity sha512-rKtvo6a868b5Hu3heneU+L4yEQ4jYKLtjpnPeUdK7h0yzXGmyBTypknlkCvHFBqfX9YlorEiMM6Dnq/5atfHkw== @@ -17912,7 +17814,7 @@ is-color-stop@^1.0.0: rgb-regex "^1.0.1" rgba-regex "^1.0.0" -is-core-module@^2.1.0, is-core-module@^2.2.0, is-core-module@^2.6.0, is-core-module@^2.8.1: +is-core-module@^2.2.0, is-core-module@^2.6.0, is-core-module@^2.8.1: version "2.8.1" resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.8.1.tgz#f59fdfca701d5879d0a6b100a40aa1560ce27211" integrity sha512-SdNCUs284hr40hFTFP6l0IfZ/RSrMXF3qgoRHd3/79unUTvrFO/JoXwkGm+5J/Oe3E/b5GsnG330uUNgRpu1PA== @@ -19246,11 +19148,6 @@ jimp@^0.14.0: "@jimp/types" "^0.14.0" regenerator-runtime "^0.13.3" -jju@~1.4.0: - version "1.4.0" - resolved "https://registry.yarnpkg.com/jju/-/jju-1.4.0.tgz#a3abe2718af241a2b2904f84a625970f389ae32a" - integrity sha1-o6vicYryQaKykE+EpiWXDzia4yo= - joi@*, joi@^17.3.0, joi@^17.4.0: version "17.4.0" resolved "https://registry.yarnpkg.com/joi/-/joi-17.4.0.tgz#b5c2277c8519e016316e49ababd41a1908d9ef20" @@ -19358,14 +19255,6 @@ js-yaml@4.1.0, js-yaml@^4.1.0: dependencies: argparse "^2.0.1" -js-yaml@~3.13.1: - version "3.13.1" - resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.13.1.tgz#aff151b30bfdfa8e49e05da22e7415e9dfa37847" - integrity sha512-YfbcO7jXDdyj0DGxYVSlSeQNHbD7XPWvrVWeVUujrQEoZzWJIRrCPoyk6kL6IAjAG2IolMK4T0hNUe0HOUs5Jw== - dependencies: - argparse "^1.0.7" - esprima "^4.0.0" - jsbn@~0.1.0: version "0.1.1" resolved "https://registry.yarnpkg.com/jsbn/-/jsbn-0.1.1.tgz#a5e654c2e5a2deb5f201d96cefbca80c0ef2f513" @@ -20143,7 +20032,7 @@ lodash.flattendeep@^4.4.0: resolved "https://registry.yarnpkg.com/lodash.flattendeep/-/lodash.flattendeep-4.4.0.tgz#fb030917f86a3134e5bc9bec0d69e0013ddfedb2" integrity sha1-+wMJF/hqMTTlvJvsDWngAT3f7bI= -lodash.get@^4.0.0, lodash.get@^4.4.2: +lodash.get@^4.4.2: version "4.4.2" resolved "https://registry.yarnpkg.com/lodash.get/-/lodash.get-4.4.2.tgz#2d177f652fa31e939b4438d5341499dfa3825e99" integrity sha1-LRd/ZS+jHpObRDjVNBSZ36OCXpk= @@ -20263,7 +20152,7 @@ lodash.uniq@4.5.0, lodash.uniq@^4.5.0: resolved "https://registry.yarnpkg.com/lodash.uniq/-/lodash.uniq-4.5.0.tgz#d0225373aeb652adc1bc82e4945339a842754773" integrity sha1-0CJTc662Uq3BvILklFM5qEJ1R3M= -lodash@>4.17.4, lodash@^4.0.1, lodash@^4.17.10, lodash@^4.17.11, lodash@^4.17.13, lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.19, lodash@^4.17.20, lodash@^4.17.21, lodash@^4.17.4, lodash@~4.17.10, lodash@~4.17.15: +lodash@>4.17.4, lodash@^4.0.1, lodash@^4.17.10, lodash@^4.17.11, lodash@^4.17.13, lodash@^4.17.14, lodash@^4.17.15, lodash@^4.17.19, lodash@^4.17.20, lodash@^4.17.21, lodash@^4.17.4, lodash@~4.17.10: version "4.17.21" resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== @@ -25960,21 +25849,6 @@ resolve@^2.0.0-next.3: is-core-module "^2.2.0" path-parse "^1.0.6" -resolve@~1.17.0: - version "1.17.0" - resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.17.0.tgz#b25941b54968231cc2d1bb76a79cb7f2c0bf8444" - integrity sha512-ic+7JYiV8Vi2yzQGFWOkiZD5Z9z7O2Zhm9XMaTxdJExKasieFCr+yXZ/WmXsckHiKl12ar0y6XiXDx3m4RHn1w== - dependencies: - path-parse "^1.0.6" - -resolve@~1.19.0: - version "1.19.0" - resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.19.0.tgz#1af5bf630409734a067cae29318aac7fa29a267c" - integrity sha512-rArEXAgsBG4UgRGcynxWIWKFvh/XZCcS8UJdHhwy91zwAvCZIbcs+vAbflgBnNjYMs/i/i+/Ux6IZhML1yPvxg== - dependencies: - is-core-module "^2.1.0" - path-parse "^1.0.6" - responselike@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/responselike/-/responselike-1.0.2.tgz#918720ef3b631c5642be068f15ade5a46f4ba1e7" @@ -26444,7 +26318,7 @@ semver@^6.0.0, semver@^6.1.0, semver@^6.1.1, semver@^6.1.2, semver@^6.2.0, semve resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.0.tgz#ee0a64c8af5e8ceea67687b133761e1becbd1d3d" integrity sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw== -semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5, semver@~7.3.0, semver@~7.3.2: +semver@^7.2.1, semver@^7.3.2, semver@^7.3.4, semver@^7.3.5, semver@~7.3.2: version "7.3.5" resolved "https://registry.yarnpkg.com/semver/-/semver-7.3.5.tgz#0b621c879348d8998e4b0e4be94b3f12e6018ef7" integrity sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ== @@ -27447,11 +27321,6 @@ strict-uri-encode@^2.0.0: resolved "https://registry.yarnpkg.com/strict-uri-encode/-/strict-uri-encode-2.0.0.tgz#b9c7330c7042862f6b142dc274bbcc5866ce3546" integrity sha1-ucczDHBChi9rFC3CdLvMWGbONUY= -string-argv@~0.3.1: - version "0.3.1" - resolved "https://registry.yarnpkg.com/string-argv/-/string-argv-0.3.1.tgz#95e2fbec0427ae19184935f816d74aaa4c5c19da" - integrity sha512-a1uQGz7IyVy9YwhqjZIZu1c8JO8dNIe20xBmSS6qu9kv++k3JGzCVmprbNN5Kn+BgzD5E7YYwg1CcjuJMRNsvg== - string-length@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/string-length/-/string-length-1.0.1.tgz#56970fb1c38558e9e70b728bf3de269ac45adfac" @@ -27671,7 +27540,7 @@ strip-indent@^3.0.0: dependencies: min-indent "^1.0.0" -strip-json-comments@3.1.1, strip-json-comments@^3.1.0, strip-json-comments@^3.1.1, strip-json-comments@~3.1.1: +strip-json-comments@3.1.1, strip-json-comments@^3.1.0, strip-json-comments@^3.1.1: version "3.1.1" resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== @@ -28332,7 +28201,7 @@ timm@^1.6.1: resolved "https://registry.yarnpkg.com/timm/-/timm-1.6.1.tgz#5f8aafc932248c76caf2c6af60542a32d3c30701" integrity sha512-hqDTYi/bWuDxL2i6T3v6nrvkAQ/1Bc060GSkVEQZp02zTSTB4CHSKsOkliequCftQaNRcjRqUZmpGWs5FfhrNg== -timsort@^0.3.0, timsort@~0.3.0: +timsort@^0.3.0: version "0.3.0" resolved "https://registry.yarnpkg.com/timsort/-/timsort-0.3.0.tgz#405411a8e7e6339fe64db9a234de11dc31e02bd4" integrity sha1-QFQRqOfmM5/mTbmiNN4R3DHgK9Q= @@ -28852,7 +28721,7 @@ typescript-tuple@^2.2.1: dependencies: typescript-compare "^0.0.2" -typescript@4.6.3, typescript@^3.3.3333, typescript@^3.5.3, typescript@^4.5.5, typescript@~4.4.2: +typescript@4.6.3, typescript@^3.3.3333, typescript@^3.5.3, typescript@^4.5.5: version "4.6.3" resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.6.3.tgz#eefeafa6afdd31d725584c67a0eaba80f6fc6c6c" integrity sha512-yNIatDa5iaofVozS/uQJEl3JRWLKKGJKh6Yaiv0GLGSuhpFJe7P3SbHZ8/yjAHRQwKRoA6YZqlfjXWmVzoVSMw== @@ -29595,11 +29464,6 @@ validator@^13.6.0, validator@^13.7.0: resolved "https://registry.yarnpkg.com/validator/-/validator-13.7.0.tgz#4f9658ba13ba8f3d82ee881d3516489ea85c0857" integrity sha512-nYXQLCBkpJ8X6ltALua9dRrZDHVYxjJ1wgskNt1lH9fzGjs3tgojGSCBjmEPwkWS1y29+DrizMTW19Pr9uB2nw== -validator@^8.0.0: - version "8.2.0" - resolved "https://registry.yarnpkg.com/validator/-/validator-8.2.0.tgz#3c1237290e37092355344fef78c231249dab77b9" - integrity sha512-Yw5wW34fSv5spzTXNkokD6S6/Oq92d8q/t14TqsS3fAiA1RYnxSFSIZ+CY3n6PGGRCq5HhJTSepQvFUS2QUDxA== - value-equal@^0.4.0: version "0.4.0" resolved "https://registry.yarnpkg.com/value-equal/-/value-equal-0.4.0.tgz#c5bdd2f54ee093c04839d71ce2e4758a6890abc7" @@ -31134,17 +30998,6 @@ z-schema@^5.0.1: optionalDependencies: commander "^2.7.1" -z-schema@~3.18.3: - version "3.18.4" - resolved "https://registry.yarnpkg.com/z-schema/-/z-schema-3.18.4.tgz#ea8132b279533ee60be2485a02f7e3e42541a9a2" - integrity sha512-DUOKC/IhbkdLKKiV89gw9DUauTV8U/8yJl1sjf6MtDmzevLKOF2duNJ495S3MFVjqZarr+qNGCPbkg4mu4PpLw== - dependencies: - lodash.get "^4.0.0" - lodash.isequal "^4.0.0" - validator "^8.0.0" - optionalDependencies: - commander "^2.7.1" - zip-stream@^4.1.0: version "4.1.0" resolved "https://registry.yarnpkg.com/zip-stream/-/zip-stream-4.1.0.tgz#51dd326571544e36aa3f756430b313576dc8fc79" From f7d030fa64ba4ddae103e9c99b74eda004e20b83 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20S=C3=A1nchez?= Date: Thu, 14 Jul 2022 17:50:56 +0200 Subject: [PATCH 032/111] [Security Solution] [Endpoint] Responder new help panel design (#136106) * Help panel restyling and add copy command functionality * Adds tooltip and clean code * Use theme props instead hardcoded ones and adds import type * Fix unit test increasing array length due generic common args * freeze static objects * Moves code to utils file and use
    for numbered list * Moves utils file into /service folder * UI adjustments according mocks * Removes padding. Set function in UseCallback. Removes EuiTextColor. Reduce padding-bottom size. Removes unnecessary grow prop * Fixes border radius --- .../console/components/command_list.tsx | 256 ++++++++++++++++-- .../console/components/console_header.tsx | 31 ++- .../handle_execute_command.test.tsx | 3 +- .../side_panel/side_panel_content_layout.tsx | 9 +- .../side_panel/side_panel_content_manager.tsx | 65 ++++- .../side_panel/side_panel_flex_item.tsx | 14 +- .../management/components/console/console.tsx | 65 +++-- .../console/service/builtin_commands.tsx | 25 ++ .../components/console/service/utils.ts | 30 ++ .../management/components/console/types.ts | 10 +- ...point_response_actions_console_commands.ts | 27 ++ 11 files changed, 457 insertions(+), 78 deletions(-) create mode 100644 x-pack/plugins/security_solution/public/management/components/console/service/utils.ts diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/command_list.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/command_list.tsx index 9b3052336b790..13e0d06d7a41c 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/command_list.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/command_list.tsx @@ -5,28 +5,63 @@ * 2.0. */ -import React, { memo, useMemo } from 'react'; +import React, { memo, useMemo, useCallback } from 'react'; +import styled from 'styled-components'; +import { groupBy, sortBy } from 'lodash'; import { EuiBadge, + EuiBasicTable, + EuiButtonIcon, EuiCode, EuiDescriptionList, EuiFlexGroup, + EuiFlexGrid, EuiFlexItem, EuiSpacer, EuiText, - EuiTextColor, + EuiCallOut, + EuiLink, + EuiToolTip, } from '@elastic/eui'; +import { i18n } from '@kbn/i18n'; import { FormattedMessage } from '@kbn/i18n-react'; import type { CommandDefinition } from '../types'; import { useTestIdGenerator } from '../../../hooks/use_test_id_generator'; import { useDataTestSubj } from '../hooks/state_selectors/use_data_test_subj'; +import { useConsoleStateDispatch } from '../hooks/state_selectors/use_console_state_dispatch'; +import { COMMON_ARGS, HELP_GROUPS } from '../service/builtin_commands'; +import { getCommandNameWithArgs } from '../service/utils'; + +// @ts-expect-error TS2769 +const StyledEuiBasicTable = styled(EuiBasicTable)` + margin-top: ${({ theme: { eui } }) => eui.euiSizeS}; + .euiTableHeaderCell { + .euiTableCellContent__text { + color: ${({ theme: { eui } }) => eui.euiTextColor}; + font-size: ${({ theme: { eui } }) => eui.euiFontSize}; + padding-bottom: ${({ theme: { eui } }) => eui.euiSizeS}; + padding-left: ${({ theme: { eui } }) => eui.euiSizeS}; + } + } +`; + +const StyledEuiCallOut = styled(EuiCallOut)` + margin: ${({ theme: { eui } }) => eui.euiSize}; + border-radius: ${({ theme: { eui } }) => eui.euiSizeXS}; +`; + +const StyledEuiFlexGroup = styled(EuiFlexGroup)` + padding-left: ${({ theme: { eui } }) => eui.euiSizeS}; +`; export interface CommandListProps { commands: CommandDefinition[]; + display?: 'default' | 'table'; } -export const CommandList = memo(({ commands }) => { +export const CommandList = memo(({ commands, display = 'default' }) => { const getTestId = useTestIdGenerator(useDataTestSubj()); + const dispatch = useConsoleStateDispatch(); const footerMessage = useMemo(() => { return ( @@ -41,26 +76,207 @@ export const CommandList = memo(({ commands }) => { ); }, []); + const otherCommandsGroupLabel = i18n.translate( + 'xpack.securitySolution.console.commandList.otherCommandsGroup.label', + { + defaultMessage: 'Other commands', + } + ); + + const updateInputText = useCallback( + (text) => () => { + dispatch({ + type: 'updateInputTextEnteredState', + payload: () => { + return { + textEntered: text, + }; + }, + }); + }, + [dispatch] + ); + + const commandsByGroups = useMemo(() => { + return Object.values(groupBy(commands, 'helpGroupLabel')).reduce( + (acc, current) => { + if (current[0].helpGroupPosition !== undefined) { + // If it already exists just move it to the end + if (acc[current[0].helpGroupPosition]) { + acc[acc.length] = acc[current[0].helpGroupPosition]; + } + + acc[current[0].helpGroupPosition] = sortBy(current, 'helpCommandPosition'); + } else if (current.length) { + acc.push(current); + } + return acc; + }, + [] + ); + }, [commands]); + + const getTableItems = useCallback( + ( + commandsByGroup: CommandDefinition[] + ): Array<{ + [key: string]: { name: string; about: React.ElementType | string }; + }> => { + if (commandsByGroup[0].helpGroupLabel === HELP_GROUPS.supporting.label) { + return [...COMMON_ARGS, ...commandsByGroup].map((command) => ({ + [commandsByGroup[0]?.helpGroupLabel ?? otherCommandsGroupLabel]: command, + })); + } + return commandsByGroup.map((command) => ({ + [commandsByGroup[0]?.helpGroupLabel ?? otherCommandsGroupLabel]: command, + })); + }, + [otherCommandsGroupLabel] + ); + + const getTableColumns = useCallback( + (commandsByGroup) => { + return [ + { + field: commandsByGroup[0]?.helpGroupLabel ?? otherCommandsGroupLabel, + name: commandsByGroup[0]?.helpGroupLabel ?? otherCommandsGroupLabel, + render: (command: CommandDefinition) => { + const commandNameWithArgs = getCommandNameWithArgs(command); + return ( + + + {commandNameWithArgs}, + description: ( + <> + + + {command.about} + + + ), + }, + ]} + data-test-subj={getTestId('commandList-command')} + /> + + {/* Show EuiButtonIcon if is a command */} + {command.RenderComponent && ( + + + + + + )} + + ); + }, + }, + ]; + }, + [getTestId, otherCommandsGroupLabel, updateInputText] + ); + + if (display === 'table') { + const calloutItems = [ + , + , + , + ]; + + const callout = ( + + } + > +
      + {calloutItems.map((item, index) => ( +
    1. + {item} +
    2. + ))} +
    + {/* //TODO: Add link to the read more page */} + + + +
    + ); + + return ( + <> + {commandsByGroups.map((commandsByGroup) => ( + + ))} + + {callout} + + ); + } + return ( <> - - {commands.map(({ name, about }) => { - return ( - - {name}, description: about }]} - data-test-subj={getTestId('commandList-command')} - /> - - ); - })} - - - - - {footerMessage} + {commandsByGroups.map((commandsByGroup) => { + const groupLabel = commandsByGroup[0].helpGroupLabel; + const groupedCommands = + groupLabel === HELP_GROUPS.supporting.label + ? [...commandsByGroup, ...COMMON_ARGS] + : commandsByGroup; + return ( + + {groupedCommands.map((command) => { + return ( + + {getCommandNameWithArgs(command)}, + description: <>{command.about}, + }, + ]} + data-test-subj={getTestId('commandList-command')} + /> + + ); + })} + + ); + })} + + + {footerMessage} ); diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_header.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/console_header.tsx index 058486e13f0ab..b26b53fd7c2ac 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/console_header.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_header.tsx @@ -6,7 +6,8 @@ */ import React, { memo, useCallback } from 'react'; -import { EuiButtonIcon, EuiFlexGroup, EuiFlexItem } from '@elastic/eui'; +import { EuiButtonEmpty, EuiFlexGroup, EuiFlexItem } from '@elastic/eui'; +import { FormattedMessage } from '@kbn/i18n-react'; import { i18n } from '@kbn/i18n'; import { useConsoleStateDispatch } from '../hooks/state_selectors/use_console_state_dispatch'; import { useWithSidePanel } from '../hooks/state_selectors/use_with_side_panel'; @@ -40,17 +41,23 @@ export const ConsoleHeader = memo(({ TitleComponent }) => { {TitleComponent ? : ''} - - - + {!isHelpOpen && ( + + + + + + )} ); }); diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_state/state_update_handlers/handle_execute_command.test.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/console_state/state_update_handlers/handle_execute_command.test.tsx index 2c7f30a83cd5c..2bb52f04109c9 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/console_state/state_update_handlers/handle_execute_command.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_state/state_update_handlers/handle_execute_command.test.tsx @@ -34,7 +34,8 @@ describe('When a Console command is entered by the user', () => { await waitFor(() => { expect(renderResult.getAllByTestId('test-commandList-command')).toHaveLength( // `+2` to account for builtin commands - commands.length + 2 + // `+2` to account for builtin generic args + commands.length + 4 ); }); }); diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_layout.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_layout.tsx index fc086ce22be0e..82b9fdf5fb849 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_layout.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_layout.tsx @@ -8,12 +8,17 @@ import type { ReactNode } from 'react'; import React, { memo } from 'react'; import { EuiFlexGroup, EuiFlexItem, EuiHorizontalRule } from '@elastic/eui'; +import styled from 'styled-components'; export interface SidePanelContentLayoutProps { children: ReactNode; headerContent?: ReactNode; } +const StyledEuiFlexItemNoPadding = styled(EuiFlexItem)` + padding: 0 !important; +`; + /** * A layout component for displaying content in the right-side panel of the console */ @@ -34,9 +39,9 @@ export const SidePanelContentLayout = memo( )} - +
    {children}
    -
    + ); } diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_manager.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_manager.tsx index 376564ab896a7..7ba9cdedeea23 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_manager.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_content_manager.tsx @@ -6,37 +6,82 @@ */ import type { ReactNode } from 'react'; -import React, { memo, useMemo } from 'react'; -import { EuiText } from '@elastic/eui'; +import React, { memo, useMemo, useCallback } from 'react'; +import styled from 'styled-components'; +import { + EuiText, + EuiIcon, + EuiSpacer, + EuiFlexGroup, + EuiFlexItem, + EuiButtonIcon, + EuiTitle, +} from '@elastic/eui'; + import { FormattedMessage } from '@kbn/i18n-react'; import { CommandList } from '../command_list'; import { useWithCommandList } from '../../hooks/state_selectors/use_with_command_list'; import { SidePanelContentLayout } from './side_panel_content_layout'; import { useWithSidePanel } from '../../hooks/state_selectors/use_with_side_panel'; +import { useConsoleStateDispatch } from '../../hooks/state_selectors/use_console_state_dispatch'; + +const StyledEuiTitle = styled(EuiTitle)` + color: ${({ theme: { eui } }) => eui.euiTextSubduedColor}; +`; export const SidePanelContentManager = memo(() => { + const dispatch = useConsoleStateDispatch(); const commands = useWithCommandList(); const show = useWithSidePanel().show; + const closeHelpPanel = useCallback(() => { + dispatch({ + type: 'showSidePanel', + payload: { show: null }, + }); + }, [dispatch]); + const panelHeader: ReactNode = useMemo(() => { if (show === 'help') { return ( - - + <> + + + +

    + +

    +
    +
    + + + +
    + + }} /> -
    -
    +
    + ); } return null; - }, [show]); + }, [show, closeHelpPanel]); const panelBody: ReactNode = useMemo(() => { if (show === 'help') { - return ; + return ; } return null; diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_flex_item.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_flex_item.tsx index 20cca6401f633..f2c1cc2f3e192 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_flex_item.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/side_panel/side_panel_flex_item.tsx @@ -6,10 +6,18 @@ */ import React, { memo } from 'react'; -import { EuiFlexItem } from '@elastic/eui'; +import styled from 'styled-components'; +import { EuiFlexItem, transparentize } from '@elastic/eui'; import { SidePanelContentManager } from './side_panel_content_manager'; import { useWithSidePanel } from '../../hooks/state_selectors/use_with_side_panel'; +const StyledEuiFlexItemWhite = styled(EuiFlexItem)` + background-color: ${({ theme: { eui } }) => eui.euiHeaderBackgroundColor} !important; + border-radius: ${({ theme: { eui } }) => `0 ${eui.euiSizeXS} ${eui.euiSizeXS} 0`}; + box-shadow: 0 ${({ theme: { eui } }) => eui.euiSizeXS} ${({ theme: { eui } }) => eui.euiSizeXS} + ${({ theme: { eui } }) => transparentize(eui.euiShadowColor, 0.04)}; +`; + export const SidePanelFlexItem = memo((props) => { const isPanelOpened = Boolean(useWithSidePanel().show); @@ -18,9 +26,9 @@ export const SidePanelFlexItem = memo((props) => { } return ( - + - + ); }); SidePanelFlexItem.displayName = 'SidePanelFlexItem'; diff --git a/x-pack/plugins/security_solution/public/management/components/console/console.tsx b/x-pack/plugins/security_solution/public/management/components/console/console.tsx index e8fa86ffda83a..37850e888b126 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/console.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/console.tsx @@ -40,7 +40,7 @@ const ConsoleWindow = styled.div` &-container { padding: ${({ theme: { eui } }) => eui.euiSizeL} ${({ theme: { eui } }) => eui.euiSizeL} - ${({ theme: { eui } }) => eui.euiSizeS} ${({ theme: { eui } }) => eui.euiSizeL}; + ${({ theme: { eui } }) => eui.euiSizeS} ${({ theme: { eui } }) => eui.euiSizeM}; } &-header { @@ -139,46 +139,53 @@ export const Console = memo( dataTestSubj={commonProps['data-test-subj']} > - - - - + + + + + + - - - + - -
    + - -
    -
    - - - - - + +
    + +
    +
    + + + + + + +
    - - {}
    + {}
    diff --git a/x-pack/plugins/security_solution/public/management/components/console/service/builtin_commands.tsx b/x-pack/plugins/security_solution/public/management/components/console/service/builtin_commands.tsx index 485b43115e19b..4906143ff2c36 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/service/builtin_commands.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/service/builtin_commands.tsx @@ -10,6 +10,29 @@ import { ClearCommand } from '../components/builtin_commands/clear_command'; import { HelpCommand } from '../components/builtin_commands/help_command'; import type { CommandDefinition } from '../types'; +export const HELP_GROUPS = Object.freeze({ + supporting: { + label: i18n.translate('xpack.securitySolution.console.builtInCommands.groups.supporting', { + defaultMessage: 'Supporting commands & syntaxes', + }), + }, +}); + +export const COMMON_ARGS = Object.freeze([ + { + name: '--comment', + about: i18n.translate('xpack.securitySolution.console.commandList.commonArgs.comment', { + defaultMessage: 'Add comment to any action Ex: isolate --comment your comment', + }), + }, + { + name: '--help', + about: i18n.translate('xpack.securitySolution.console.commandList.commonArgs.help', { + defaultMessage: 'Command assistance Ex: isolate --help', + }), + }, +]); + export const getBuiltinCommands = (): CommandDefinition[] => { return [ { @@ -18,6 +41,7 @@ export const getBuiltinCommands = (): CommandDefinition[] => { defaultMessage: 'View list of available commands', }), RenderComponent: HelpCommand, + helpGroupLabel: HELP_GROUPS.supporting.label, }, { name: 'cls', @@ -25,6 +49,7 @@ export const getBuiltinCommands = (): CommandDefinition[] => { defaultMessage: 'Clear the console buffer', }), RenderComponent: ClearCommand, + helpGroupLabel: HELP_GROUPS.supporting.label, }, ]; }; diff --git a/x-pack/plugins/security_solution/public/management/components/console/service/utils.ts b/x-pack/plugins/security_solution/public/management/components/console/service/utils.ts new file mode 100644 index 0000000000000..faf7d12d12f80 --- /dev/null +++ b/x-pack/plugins/security_solution/public/management/components/console/service/utils.ts @@ -0,0 +1,30 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { CommandArgs, CommandDefinition } from '../types'; + +export const getCommandNameWithArgs = (command: Partial) => { + if (!command.mustHaveArgs || !command.args) { + return command.name; + } + + let hasAnExclusiveOrArg = false; + const primaryArgs = Object.entries(command.args).reduce((acc, [key, value]) => { + if (value.required) { + acc[key] = value; + return acc; + } + if (value.exclusiveOr && !hasAnExclusiveOrArg) { + hasAnExclusiveOrArg = true; + acc[key] = value; + return acc; + } + return acc; + }, {}); + + return `${command.name} --${Object.keys(primaryArgs).join(' --')}`; +}; diff --git a/x-pack/plugins/security_solution/public/management/components/console/types.ts b/x-pack/plugins/security_solution/public/management/components/console/types.ts index dc3ff45f161e3..d929a8a4b4984 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/types.ts +++ b/x-pack/plugins/security_solution/public/management/components/console/types.ts @@ -35,11 +35,19 @@ export interface CommandArgs { export interface CommandDefinition { name: string; - about: string; + about: ComponentType | string; /** * The Component that will be used to render the Command */ RenderComponent: CommandExecutionComponent; + /** Will be used to sort the commands when building the output for the `help` command */ + helpCommandPosition?: number; + + /** A grouping label for the command */ + helpGroupLabel?: string; + + /** Used only when command help "grouping" is detected. Used to sort the groups of commands */ + helpGroupPosition?: number; /** * If defined, this command's use of `--help` will be displayed using this component instead of * the console's built in output. diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_response_actions_console_commands.ts b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_response_actions_console_commands.ts index fec61d55c5e52..1a8476fb9c51c 100644 --- a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_response_actions_console_commands.ts +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_response_actions_console_commands.ts @@ -23,6 +23,15 @@ const emptyArgumentValidator = (argData: ParsedArgData) => { } }; +const HELP_GROUPS = Object.freeze({ + responseActions: { + position: 0, + label: i18n.translate('xpack.securitySolution.endpointConsoleCommands.groups.responseActions', { + defaultMessage: 'Response actions', + }), + }, +}); + export const getEndpointResponseActionsConsoleCommands = ( endpointAgentId: string ): CommandDefinition[] => { @@ -48,6 +57,9 @@ export const getEndpointResponseActionsConsoleCommands = ( ), }, }, + helpGroupLabel: HELP_GROUPS.responseActions.label, + helpGroupPosition: HELP_GROUPS.responseActions.position, + helpCommandPosition: 0, }, { name: 'release', @@ -70,6 +82,9 @@ export const getEndpointResponseActionsConsoleCommands = ( ), }, }, + helpGroupLabel: HELP_GROUPS.responseActions.label, + helpGroupPosition: HELP_GROUPS.responseActions.position, + helpCommandPosition: 1, }, { name: 'kill-process', @@ -114,6 +129,9 @@ export const getEndpointResponseActionsConsoleCommands = ( validate: emptyArgumentValidator, }, }, + helpGroupLabel: HELP_GROUPS.responseActions.label, + helpGroupPosition: HELP_GROUPS.responseActions.position, + helpCommandPosition: 4, }, { name: 'suspend-process', @@ -161,6 +179,9 @@ export const getEndpointResponseActionsConsoleCommands = ( validate: emptyArgumentValidator, }, }, + helpGroupLabel: HELP_GROUPS.responseActions.label, + helpGroupPosition: HELP_GROUPS.responseActions.position, + helpCommandPosition: 5, }, { name: 'status', @@ -171,6 +192,9 @@ export const getEndpointResponseActionsConsoleCommands = ( meta: { endpointId: endpointAgentId, }, + helpGroupLabel: HELP_GROUPS.responseActions.label, + helpGroupPosition: HELP_GROUPS.responseActions.position, + helpCommandPosition: 2, }, { name: 'processes', @@ -193,6 +217,9 @@ export const getEndpointResponseActionsConsoleCommands = ( ), }, }, + helpGroupLabel: HELP_GROUPS.responseActions.label, + helpGroupPosition: HELP_GROUPS.responseActions.position, + helpCommandPosition: 3, }, ]; }; From fb4c2bcc88215cd798352cf3b2d492edc4a17fc1 Mon Sep 17 00:00:00 2001 From: Lisa Cawley Date: Thu, 14 Jul 2022 09:07:20 -0700 Subject: [PATCH 033/111] [DOCS] Reduce execution terminology in actions readme (#136342) Co-authored-by: Gidi Meir Morris --- x-pack/plugins/actions/README.md | 27 ++++++++++++++------------- 1 file changed, 14 insertions(+), 13 deletions(-) diff --git a/x-pack/plugins/actions/README.md b/x-pack/plugins/actions/README.md index 3c5c459d5a780..c9b60be5e8c14 100644 --- a/x-pack/plugins/actions/README.md +++ b/x-pack/plugins/actions/README.md @@ -3,11 +3,11 @@ The Kibana actions plugin provides a framework to create executable actions. You can: - Register an action type and associate a JavaScript function to run when actions - are executed. + are generated. - Get a list of registered action types - Create an action from an action type and encrypted configuration object. - Get a list of actions that have been created. -- Execute an action, passing it a parameter object. +- Trigger an action, passing it a parameter object. - Perform CRUD operations on actions. --- @@ -81,13 +81,13 @@ Table of Contents **Action Type**: A programatically defined integration with another service, with an expected set of configuration and parameters properties, typically defined with a schema. Plugins can add new action types. -**Action**: A configuration object associated with an action type, that is ready to be executed. The configuration is persisted via Saved Objects, and some/none/all of the configuration properties can be stored encrypted. +**Action**: A configuration object associated with an action type, that is ready to run. The configuration is persisted via Saved Objects, and some/none/all of the configuration properties can be stored encrypted. ## Usage 1. Develop and register an action type (see [Action types -> Example](#example)). 2. Create an action by using the [RESTful API](#restful-api). -3. Use alerts to execute actions or execute manually (see [Firing actions](#firing-actions)). +3. Use alerting rules to generate actions or trigger them manually (see [Firing actions](#firing-actions)). ## Kibana Actions Configuration @@ -99,7 +99,8 @@ Built-In-Actions are configured using the _xpack.actions_ namespace under _kiban #### **allowedHosts** configuration -- You can use the string "*" in the **allowedHosts** configuration in place of a specific hostname to enable Kibana to target any URL, but keep in mind the potential to use such a feature to execute [SSRF](https://www.owasp.org/index.php/Server_Side_Request_Forgery) attacks from your server. +- You can use the string "*" in the **allowedHosts** configuration in place of a specific hostname to enable Kibana to target any URL, but keep in mind the potential to use such a feature to launch [SSRF](https://owasp.org/www-community/attacks/Server_Side_Request_Forgery) attacks from your server. + - The **allowedHosts** configuration applies to built-in action types (such as Slack and PagerDuty). While the _PagerDuty Action Type_ has been configured to support the service's Events API (at _https://events.pagerduty.com/v2/enqueue_, which you can read about in [Pagerduty's documentation](https://v2.developer.pagerduty.com/docs/events-api-v2)), the PagerDuty domain must still be included in the allowedHosts configuration before the action can be used. @@ -130,28 +131,28 @@ The following table describes the properties of the `options` object. | ------------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------------------- | | id | Unique identifier for the action type. For convention, ids starting with `.` are reserved for built in action types. We recommend using a convention like `.mySpecialAction` for your action types. | string | | name | A user-friendly name for the action type. These will be displayed in dropdowns when chosing action types. | string | -| maxAttempts | The maximum number of times this action will attempt to execute when scheduled. | number | +| maxAttempts | The maximum number of times this action will attempt to run when scheduled. | number | | minimumLicenseRequired | The license required to use the action type. | string | | validate.params | When developing an action type, it needs to accept parameters to know what to do with the action. (Example `to`, `from`, `subject`, `body` of an email). See the current built-in email action type for an example of the state-of-the-art validation.

    Technically, the value of this property should have a property named `validate()` which is a function that takes a params object to validate and returns a sanitized version of that object to pass to the execution function. Validation errors should be thrown from the `validate()` function and will be available as an error message | schema / validation function | | validate.config | Similar to params, a config may be required when creating an action (for example `host` and `port` for an email server). | schema / validation function | | validate.secrets | Similar to params, a secrets object may be required when creating an action (for example `user` and `password` for an email server). | schema / validation function | -| executor | This is where the code of an action type lives. This is a function gets called for executing an action from either alerting or manually by using the exposed function (see firing actions). For full details, see executor section below. | Function | +| executor | This is where the code of an action type lives. This is a function gets called for generating an action from either alerting or manually by using the exposed function (see firing actions). For full details, see executor section below. | Function | | renderParameterTemplates | Optionally define a function to provide custom rendering for this action type. | Function | **Important** - The config object is persisted in ElasticSearch and updated via the ElasticSearch update document API. This API allows "partial updates" - and this can cause issues with the encryption used on specified properties. So, a `validate()` function should return values for all configuration properties, so that partial updates do not occur. Setting property values to `null` rather than `undefined`, or not including a property in the config object, is all you need to do to ensure partial updates won't occur. ### Executor -This is the primary function for an action type. Whenever the action needs to execute, this function will perform the action. It receives a variety of parameters. The following table describes the properties that the executor receives. +This is the primary function for an action type. Whenever the action needs to run, this function will perform the action. It receives a variety of parameters. The following table describes the properties that the executor receives. **executor(options)** | Property | Description | | --------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| actionId | The action saved object id that the action type is executing for. | +| actionId | The action saved object id that the connector is generating. | | config | The action configuration. If you would like to validate the config before being passed to the executor, define `validate.config` within the action type. | | secrets | The decrypted secrets object given to an action. This comes from the action saved object that is partially or fully encrypted within the data store. If you would like to validate the secrets object before being passed to the executor, define `validate.secrets` within the action type. | -| params | Parameters for the execution. These will be given at execution time by either an alert or manually provided when calling the plugin provided execute function. | +| params | Parameters for the action. These will be given at run time by either an alert or manually provided when calling the plugin provided execute function. | | services.scopedClusterClient | Use this to do Elasticsearch queries on the cluster Kibana connects to. Serves the same purpose as the normal IClusterClient, but exposes an additional `asCurrentUser` method that doesn't use credentials of the Kibana internal user (as `asInternalUser` does) to request Elasticsearch API, but rather passes HTTP headers extracted from the current user request to the API instead. | | services.savedObjectsClient | This is an instance of the saved objects client. This provides the ability to do CRUD on any saved objects within the same space the alert lives in.

    The scope of the saved objects client is tied to the user in context calling the execute API or the API key provided to the execute plugin function (only when security isenabled). | | services.log(tags, [data], [timestamp]) | Use this to create server logs. (This is the same function as server.log) | @@ -176,7 +177,7 @@ By providing the user's Request you'll receive an instance of the ActionsClient const actionsClient = server.plugins.actions.getActionsClientWithRequest(request); ``` -Once you have a scoped ActionsClient you can execute an action by caling either the `enqueueExecution` which will schedule the action to run later or the `execute` apis which will run it immediately and return the result respectively. +Once you have a scoped ActionsClient you can generate an action by calling either the `enqueueExecution` which will schedule the action to run later or the `execute` apis which will run it immediately and return the result respectively. ### actionsClient.enqueueExecution(options) @@ -191,7 +192,7 @@ The following table describes the properties of the `options` object. | Property | Description | Type | | -------- | ------------------------------------------------------------------------------------------------------ | ---------------- | -| id | The id of the action you want to execute. | string | +| id | The id of the action you want to run. | string | | params | The `params` value to give the action type executor. | object | | spaceId | The space id the action is within. | string | | apiKey | The Elasticsearch API key to use for context. (Note: only required and used when security is enabled). | string | @@ -225,7 +226,7 @@ The following table describes the properties of the `options` object. | Property | Description | Type | | -------- | ------------------------------------------------------------------------------------- | ---------------- | -| id | The id of the action you want to execute. | string | +| id | The id of the action you want to generate. | string | | params | The `params` value to give the action type executor. | object | | source | The source of the execution, either an HTTP request or a reference to a Saved Object. | object, optional | From 17daa51d821fc7b7e762569d2c5c545ced8b1780 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Istv=C3=A1n=20Zolt=C3=A1n=20Szab=C3=B3?= Date: Thu, 14 Jul 2022 18:27:42 +0200 Subject: [PATCH 034/111] [ML] Adjust screenshot creation scenario for regression results (#136411) * [ML] Modifies screenshot creation for flights-regression-results. --- .../apps/ml_docs/data_frame_analytics/regression.ts | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/x-pack/test/screenshot_creation/apps/ml_docs/data_frame_analytics/regression.ts b/x-pack/test/screenshot_creation/apps/ml_docs/data_frame_analytics/regression.ts index ea59c68088363..de3dee3a47905 100644 --- a/x-pack/test/screenshot_creation/apps/ml_docs/data_frame_analytics/regression.ts +++ b/x-pack/test/screenshot_creation/apps/ml_docs/data_frame_analytics/regression.ts @@ -123,8 +123,14 @@ export default function ({ getService }: FtrProviderContext) { await ml.dataFrameAnalyticsResults.expandFeatureImportanceSection(false); await ml.dataFrameAnalyticsResults.expandScatterplotMatrixSection(false); await ml.dataFrameAnalyticsResults.scrollAnalysisIntoView(); + await ml.dataFrameAnalyticsResults.enableResultsTablePreviewHistogramCharts(true); await mlScreenshots.removeFocusFromElement(); - await mlScreenshots.takeScreenshot('flights-regression-results', screenshotDirectories); + await mlScreenshots.takeScreenshot( + 'flights-regression-results', + screenshotDirectories, + 1500, + 1300 + ); await ml.testExecution.logTestStep('expand feature importance section and take screenshot'); await ml.dataFrameAnalyticsResults.expandFeatureImportanceSection(true); From 8e7d411aa457fbd7e766c03e36aacefb3ab50267 Mon Sep 17 00:00:00 2001 From: "Christiane (Tina) Heiligers" Date: Thu, 14 Jul 2022 09:59:24 -0700 Subject: [PATCH 035/111] Migrates core uiSettings client-side service to packages (#136354) --- package.json | 10 ++ packages/BUILD.bazel | 10 ++ .../BUILD.bazel | 113 ++++++++++++++++++ .../README.md | 3 + .../jest.config.js | 13 ++ .../package.json | 8 ++ .../src}/http_test_setup.ts | 0 .../src/index.ts | 10 ++ .../tsconfig.json | 18 +++ .../BUILD.bazel | 113 ++++++++++++++++++ .../README.md | 3 + .../jest.config.js | 13 ++ .../package.json | 8 ++ .../ui_settings_api.test.ts.snap | 0 .../ui_settings_client.test.ts.snap | 0 .../src}/index.ts | 1 - .../src}/ui_settings_api.test.ts | 2 +- .../src}/ui_settings_api.ts | 2 +- .../src}/ui_settings_client.test.ts | 0 .../src}/ui_settings_client.ts | 4 +- .../src}/ui_settings_service.test.ts | 0 .../src}/ui_settings_service.ts | 2 +- .../tsconfig.json | 18 +++ .../BUILD.bazel | 111 +++++++++++++++++ .../core-ui-settings-browser-mocks/README.md | 3 + .../jest.config.js | 13 ++ .../package.json | 8 ++ .../src/index.ts | 9 ++ .../src}/ui_settings_service.mock.ts | 4 +- .../tsconfig.json | 18 +++ .../core-ui-settings-browser/BUILD.bazel | 108 +++++++++++++++++ .../core-ui-settings-browser/README.md | 3 + .../core-ui-settings-browser/jest.config.js | 13 ++ .../core-ui-settings-browser/package.json | 8 ++ .../core-ui-settings-browser/src/index.ts | 9 ++ .../core-ui-settings-browser/src}/types.ts | 4 +- .../core-ui-settings-browser/tsconfig.json | 18 +++ .../core-ui-settings-common/BUILD.bazel | 107 +++++++++++++++++ .../core-ui-settings-common/README.md | 3 + .../core-ui-settings-common/jest.config.js | 13 ++ .../core-ui-settings-common/package.json | 8 ++ .../core-ui-settings-common/src/index.ts | 15 +++ .../src}/ui_settings.ts | 4 +- .../core-ui-settings-common/tsconfig.json | 18 +++ src/core/public/chrome/chrome_service.test.ts | 2 +- src/core/public/core_app/core_app.ts | 2 +- .../core_app/errors/url_overflow.test.ts | 4 +- .../public/core_app/errors/url_overflow.tsx | 2 +- src/core/public/core_system.test.mocks.ts | 4 +- src/core/public/core_system.ts | 2 +- src/core/public/index.ts | 9 +- .../integrations/integrations_service.test.ts | 2 +- .../integrations/integrations_service.ts | 2 +- .../moment/moment_service.test.ts | 2 +- .../integrations/moment/moment_service.ts | 2 +- .../styles/styles_service.test.ts | 2 +- .../integrations/styles/styles_service.ts | 2 +- src/core/public/mocks.ts | 4 +- .../notifications/notifications_service.ts | 2 +- .../notifications/toasts/toasts_api.test.ts | 2 +- .../notifications/toasts/toasts_api.tsx | 2 +- .../toasts/toasts_service.test.tsx | 2 +- .../notifications/toasts/toasts_service.tsx | 2 +- .../overlays/banners/banners_service.test.ts | 2 +- .../overlays/banners/banners_service.tsx | 2 +- .../banners/user_banner_service.test.ts | 2 +- .../overlays/banners/user_banner_service.tsx | 2 +- src/core/public/overlays/overlay_service.ts | 2 +- .../public/plugins/plugins_service.test.ts | 2 +- src/core/public/types.ts | 2 +- src/core/server/ui_settings/types.ts | 10 +- src/core/types/index.ts | 8 +- .../data_views_api_client.test.mock.ts | 2 +- ...thorized_response_http_interceptor.test.ts | 2 +- yarn.lock | 40 +++++++ 75 files changed, 927 insertions(+), 48 deletions(-) create mode 100644 packages/core/test-helpers/core-test-helpers-http-setup-browser/BUILD.bazel create mode 100644 packages/core/test-helpers/core-test-helpers-http-setup-browser/README.md create mode 100644 packages/core/test-helpers/core-test-helpers-http-setup-browser/jest.config.js create mode 100644 packages/core/test-helpers/core-test-helpers-http-setup-browser/package.json rename {src/core/test_helpers => packages/core/test-helpers/core-test-helpers-http-setup-browser/src}/http_test_setup.ts (100%) create mode 100644 packages/core/test-helpers/core-test-helpers-http-setup-browser/src/index.ts create mode 100644 packages/core/test-helpers/core-test-helpers-http-setup-browser/tsconfig.json create mode 100644 packages/core/ui-settings/core-ui-settings-browser-internal/BUILD.bazel create mode 100644 packages/core/ui-settings/core-ui-settings-browser-internal/README.md create mode 100644 packages/core/ui-settings/core-ui-settings-browser-internal/jest.config.js create mode 100644 packages/core/ui-settings/core-ui-settings-browser-internal/package.json rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/__snapshots__/ui_settings_api.test.ts.snap (100%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/__snapshots__/ui_settings_client.test.ts.snap (100%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/index.ts (87%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/ui_settings_api.test.ts (98%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/ui_settings_api.ts (98%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/ui_settings_client.test.ts (100%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/ui_settings_client.ts (96%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/ui_settings_service.test.ts (100%) rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-internal/src}/ui_settings_service.ts (96%) create mode 100644 packages/core/ui-settings/core-ui-settings-browser-internal/tsconfig.json create mode 100644 packages/core/ui-settings/core-ui-settings-browser-mocks/BUILD.bazel create mode 100644 packages/core/ui-settings/core-ui-settings-browser-mocks/README.md create mode 100644 packages/core/ui-settings/core-ui-settings-browser-mocks/jest.config.js create mode 100644 packages/core/ui-settings/core-ui-settings-browser-mocks/package.json create mode 100644 packages/core/ui-settings/core-ui-settings-browser-mocks/src/index.ts rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser-mocks/src}/ui_settings_service.mock.ts (91%) create mode 100644 packages/core/ui-settings/core-ui-settings-browser-mocks/tsconfig.json create mode 100644 packages/core/ui-settings/core-ui-settings-browser/BUILD.bazel create mode 100644 packages/core/ui-settings/core-ui-settings-browser/README.md create mode 100644 packages/core/ui-settings/core-ui-settings-browser/jest.config.js create mode 100644 packages/core/ui-settings/core-ui-settings-browser/package.json create mode 100644 packages/core/ui-settings/core-ui-settings-browser/src/index.ts rename {src/core/public/ui_settings => packages/core/ui-settings/core-ui-settings-browser/src}/types.ts (96%) create mode 100644 packages/core/ui-settings/core-ui-settings-browser/tsconfig.json create mode 100644 packages/core/ui-settings/core-ui-settings-common/BUILD.bazel create mode 100644 packages/core/ui-settings/core-ui-settings-common/README.md create mode 100644 packages/core/ui-settings/core-ui-settings-common/jest.config.js create mode 100644 packages/core/ui-settings/core-ui-settings-common/package.json create mode 100644 packages/core/ui-settings/core-ui-settings-common/src/index.ts rename {src/core/types => packages/core/ui-settings/core-ui-settings-common/src}/ui_settings.ts (96%) create mode 100644 packages/core/ui-settings/core-ui-settings-common/tsconfig.json diff --git a/package.json b/package.json index 5f7e4a706b826..9294089cb355a 100644 --- a/package.json +++ b/package.json @@ -208,9 +208,14 @@ "@kbn/core-preboot-server": "link:bazel-bin/packages/core/preboot/core-preboot-server", "@kbn/core-preboot-server-internal": "link:bazel-bin/packages/core/preboot/core-preboot-server-internal", "@kbn/core-preboot-server-mocks": "link:bazel-bin/packages/core/preboot/core-preboot-server-mocks", + "@kbn/core-test-helpers-http-setup-browser": "link:bazel-bin/packages/core/test-helpers/core-test-helpers-http-setup-browser", "@kbn/core-theme-browser": "link:bazel-bin/packages/core/theme/core-theme-browser", "@kbn/core-theme-browser-internal": "link:bazel-bin/packages/core/theme/core-theme-browser-internal", "@kbn/core-theme-browser-mocks": "link:bazel-bin/packages/core/theme/core-theme-browser-mocks", + "@kbn/core-ui-settings-browser": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser", + "@kbn/core-ui-settings-browser-internal": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-internal", + "@kbn/core-ui-settings-browser-mocks": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-mocks", + "@kbn/core-ui-settings-common": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-common", "@kbn/crypto": "link:bazel-bin/packages/kbn-crypto", "@kbn/crypto-browser": "link:bazel-bin/packages/kbn-crypto-browser", "@kbn/datemath": "link:bazel-bin/packages/kbn-datemath", @@ -791,9 +796,14 @@ "@types/kbn__core-preboot-server-mocks": "link:bazel-bin/packages/core/preboot/core-preboot-server-mocks/npm_module_types", "@types/kbn__core-public-internal-base": "link:bazel-bin/packages/core/public/internal-base/npm_module_types", "@types/kbn__core-server-internal-base": "link:bazel-bin/packages/core/server/internal-base/npm_module_types", + "@types/kbn__core-test-helpers-http-setup-browser": "link:bazel-bin/packages/core/test-helpers/core-test-helpers-http-setup-browser/npm_module_types", "@types/kbn__core-theme-browser": "link:bazel-bin/packages/core/theme/core-theme-browser/npm_module_types", "@types/kbn__core-theme-browser-internal": "link:bazel-bin/packages/core/theme/core-theme-browser-internal/npm_module_types", "@types/kbn__core-theme-browser-mocks": "link:bazel-bin/packages/core/theme/core-theme-browser-mocks/npm_module_types", + "@types/kbn__core-ui-settings-browser": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser/npm_module_types", + "@types/kbn__core-ui-settings-browser-internal": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-internal/npm_module_types", + "@types/kbn__core-ui-settings-browser-mocks": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-mocks/npm_module_types", + "@types/kbn__core-ui-settings-common": "link:bazel-bin/packages/core/ui-settings/core-ui-settings-common/npm_module_types", "@types/kbn__crypto": "link:bazel-bin/packages/kbn-crypto/npm_module_types", "@types/kbn__crypto-browser": "link:bazel-bin/packages/kbn-crypto-browser/npm_module_types", "@types/kbn__datemath": "link:bazel-bin/packages/kbn-datemath/npm_module_types", diff --git a/packages/BUILD.bazel b/packages/BUILD.bazel index 96786d77dd80f..fb1f7a6bdb146 100644 --- a/packages/BUILD.bazel +++ b/packages/BUILD.bazel @@ -76,9 +76,14 @@ filegroup( "//packages/core/preboot/core-preboot-server-internal:build", "//packages/core/preboot/core-preboot-server-mocks:build", "//packages/core/preboot/core-preboot-server:build", + "//packages/core/test-helpers/core-test-helpers-http-setup-browser:build", "//packages/core/theme/core-theme-browser-internal:build", "//packages/core/theme/core-theme-browser-mocks:build", "//packages/core/theme/core-theme-browser:build", + "//packages/core/ui-settings/core-ui-settings-browser-internal:build", + "//packages/core/ui-settings/core-ui-settings-browser-mocks:build", + "//packages/core/ui-settings/core-ui-settings-browser:build", + "//packages/core/ui-settings/core-ui-settings-common:build", "//packages/elastic-apm-synthtrace:build", "//packages/elastic-safer-lodash-set:build", "//packages/home/sample_data_cards:build", @@ -277,9 +282,14 @@ filegroup( "//packages/core/preboot/core-preboot-server-internal:build_types", "//packages/core/preboot/core-preboot-server-mocks:build_types", "//packages/core/preboot/core-preboot-server:build_types", + "//packages/core/test-helpers/core-test-helpers-http-setup-browser:build_types", "//packages/core/theme/core-theme-browser-internal:build_types", "//packages/core/theme/core-theme-browser-mocks:build_types", "//packages/core/theme/core-theme-browser:build_types", + "//packages/core/ui-settings/core-ui-settings-browser-internal:build_types", + "//packages/core/ui-settings/core-ui-settings-browser-mocks:build_types", + "//packages/core/ui-settings/core-ui-settings-browser:build_types", + "//packages/core/ui-settings/core-ui-settings-common:build_types", "//packages/elastic-apm-synthtrace:build_types", "//packages/elastic-safer-lodash-set:build_types", "//packages/home/sample_data_cards:build_types", diff --git a/packages/core/test-helpers/core-test-helpers-http-setup-browser/BUILD.bazel b/packages/core/test-helpers/core-test-helpers-http-setup-browser/BUILD.bazel new file mode 100644 index 0000000000000..b802747956bda --- /dev/null +++ b/packages/core/test-helpers/core-test-helpers-http-setup-browser/BUILD.bazel @@ -0,0 +1,113 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-test-helpers-http-setup-browser" +PKG_REQUIRE_NAME = "@kbn/core-test-helpers-http-setup-browser" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ + "//packages/core/execution-context/core-execution-context-browser-mocks", + "//packages/core/fatal-errors/core-fatal-errors-browser-mocks", + "//packages/core/injected-metadata/core-injected-metadata-browser-mocks", + "//packages/core/http/core-http-browser-internal" +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "//packages/core/execution-context/core-execution-context-browser-mocks:npm_module_types", + "//packages/core/fatal-errors/core-fatal-errors-browser-mocks:npm_module_types", + "//packages/core/injected-metadata/core-injected-metadata-browser-mocks:npm_module_types", + "//packages/core/http/core-http-browser-internal:npm_module_types" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/test-helpers/core-test-helpers-http-setup-browser/README.md b/packages/core/test-helpers/core-test-helpers-http-setup-browser/README.md new file mode 100644 index 0000000000000..f4e1825d67d05 --- /dev/null +++ b/packages/core/test-helpers/core-test-helpers-http-setup-browser/README.md @@ -0,0 +1,3 @@ +# @kbn/core-test-helpers-http-setup-browser + +This package contains Core's browser-side test helpers. diff --git a/packages/core/test-helpers/core-test-helpers-http-setup-browser/jest.config.js b/packages/core/test-helpers/core-test-helpers-http-setup-browser/jest.config.js new file mode 100644 index 0000000000000..06aa6045ec68b --- /dev/null +++ b/packages/core/test-helpers/core-test-helpers-http-setup-browser/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/test-helpers/core-test-helpers-http-setup-browser'], +}; diff --git a/packages/core/test-helpers/core-test-helpers-http-setup-browser/package.json b/packages/core/test-helpers/core-test-helpers-http-setup-browser/package.json new file mode 100644 index 0000000000000..b6c321f96c8fc --- /dev/null +++ b/packages/core/test-helpers/core-test-helpers-http-setup-browser/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-test-helpers-http-setup-browser", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/src/core/test_helpers/http_test_setup.ts b/packages/core/test-helpers/core-test-helpers-http-setup-browser/src/http_test_setup.ts similarity index 100% rename from src/core/test_helpers/http_test_setup.ts rename to packages/core/test-helpers/core-test-helpers-http-setup-browser/src/http_test_setup.ts diff --git a/packages/core/test-helpers/core-test-helpers-http-setup-browser/src/index.ts b/packages/core/test-helpers/core-test-helpers-http-setup-browser/src/index.ts new file mode 100644 index 0000000000000..db5c37cc1ecac --- /dev/null +++ b/packages/core/test-helpers/core-test-helpers-http-setup-browser/src/index.ts @@ -0,0 +1,10 @@ +/* + * 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. + */ + +export type { SetupTap } from './http_test_setup'; +export { setup } from './http_test_setup'; diff --git a/packages/core/test-helpers/core-test-helpers-http-setup-browser/tsconfig.json b/packages/core/test-helpers/core-test-helpers-http-setup-browser/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/test-helpers/core-test-helpers-http-setup-browser/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/core/ui-settings/core-ui-settings-browser-internal/BUILD.bazel b/packages/core/ui-settings/core-ui-settings-browser-internal/BUILD.bazel new file mode 100644 index 0000000000000..79c90204e03c2 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/BUILD.bazel @@ -0,0 +1,113 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-ui-settings-browser-internal" +PKG_REQUIRE_NAME = "@kbn/core-ui-settings-browser-internal" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ + "@npm//rxjs", + "@npm//lodash", + "//packages/core/test-helpers/core-test-helpers-http-setup-browser" +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "@npm//rxjs", + "@npm//lodash", + "//packages/core/test-helpers/core-test-helpers-http-setup-browser:npm_module_types", + "//packages/core/http/core-http-browser:npm_module_types", + "//packages/core/ui-settings/core-ui-settings-browser:npm_module_types" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/ui-settings/core-ui-settings-browser-internal/README.md b/packages/core/ui-settings/core-ui-settings-browser-internal/README.md new file mode 100644 index 0000000000000..0ca0464803902 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/README.md @@ -0,0 +1,3 @@ +# @kbn/core-ui-settings-browser-internal + +This package contains the internal types and implementation for Core's browser-side uiSettings service. diff --git a/packages/core/ui-settings/core-ui-settings-browser-internal/jest.config.js b/packages/core/ui-settings/core-ui-settings-browser-internal/jest.config.js new file mode 100644 index 0000000000000..286747d11869e --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/ui-settings/core-ui-settings-browser-internal'], +}; diff --git a/packages/core/ui-settings/core-ui-settings-browser-internal/package.json b/packages/core/ui-settings/core-ui-settings-browser-internal/package.json new file mode 100644 index 0000000000000..a333808e2fe63 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-ui-settings-browser-internal", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/src/core/public/ui_settings/__snapshots__/ui_settings_api.test.ts.snap b/packages/core/ui-settings/core-ui-settings-browser-internal/src/__snapshots__/ui_settings_api.test.ts.snap similarity index 100% rename from src/core/public/ui_settings/__snapshots__/ui_settings_api.test.ts.snap rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/__snapshots__/ui_settings_api.test.ts.snap diff --git a/src/core/public/ui_settings/__snapshots__/ui_settings_client.test.ts.snap b/packages/core/ui-settings/core-ui-settings-browser-internal/src/__snapshots__/ui_settings_client.test.ts.snap similarity index 100% rename from src/core/public/ui_settings/__snapshots__/ui_settings_client.test.ts.snap rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/__snapshots__/ui_settings_client.test.ts.snap diff --git a/src/core/public/ui_settings/index.ts b/packages/core/ui-settings/core-ui-settings-browser-internal/src/index.ts similarity index 87% rename from src/core/public/ui_settings/index.ts rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/index.ts index 7c7bdae34a3c1..b57cef6053106 100644 --- a/src/core/public/ui_settings/index.ts +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/src/index.ts @@ -8,4 +8,3 @@ export { UiSettingsService } from './ui_settings_service'; export type { UiSettingsClient } from './ui_settings_client'; -export type { UiSettingsState, IUiSettingsClient } from './types'; diff --git a/src/core/public/ui_settings/ui_settings_api.test.ts b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_api.test.ts similarity index 98% rename from src/core/public/ui_settings/ui_settings_api.test.ts rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_api.test.ts index d5f0f1175b9e5..c250b78d68ce5 100644 --- a/src/core/public/ui_settings/ui_settings_api.test.ts +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_api.test.ts @@ -11,7 +11,7 @@ import fetchMock from 'fetch-mock/es5/client'; import * as Rx from 'rxjs'; import { takeUntil, toArray } from 'rxjs/operators'; -import { setup as httpSetup } from '../../test_helpers/http_test_setup'; +import { setup as httpSetup } from '@kbn/core-test-helpers-http-setup-browser'; import { UiSettingsApi } from './ui_settings_api'; function setup() { diff --git a/src/core/public/ui_settings/ui_settings_api.ts b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_api.ts similarity index 98% rename from src/core/public/ui_settings/ui_settings_api.ts rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_api.ts index 0428de810cca9..2686307357723 100644 --- a/src/core/public/ui_settings/ui_settings_api.ts +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_api.ts @@ -9,7 +9,7 @@ import { BehaviorSubject } from 'rxjs'; import type { HttpSetup } from '@kbn/core-http-browser'; -import type { UiSettingsState } from './types'; +import type { UiSettingsState } from '@kbn/core-ui-settings-browser'; export interface UiSettingsApiResponse { settings: UiSettingsState; diff --git a/src/core/public/ui_settings/ui_settings_client.test.ts b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_client.test.ts similarity index 100% rename from src/core/public/ui_settings/ui_settings_client.test.ts rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_client.test.ts diff --git a/src/core/public/ui_settings/ui_settings_client.ts b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_client.ts similarity index 96% rename from src/core/public/ui_settings/ui_settings_client.ts rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_client.ts index 979f6be5ebe2c..d5b6b7f1513b2 100644 --- a/src/core/public/ui_settings/ui_settings_client.ts +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_client.ts @@ -10,8 +10,8 @@ import { cloneDeep, defaultsDeep } from 'lodash'; import { Observable, Subject, concat, defer, of } from 'rxjs'; import { filter, map } from 'rxjs/operators'; -import { UserProvidedValues, PublicUiSettingsParams } from '../../server/types'; -import { IUiSettingsClient, UiSettingsState } from './types'; +import { UserProvidedValues, PublicUiSettingsParams } from '@kbn/core-ui-settings-common'; +import { IUiSettingsClient, UiSettingsState } from '@kbn/core-ui-settings-browser'; import { UiSettingsApi } from './ui_settings_api'; diff --git a/src/core/public/ui_settings/ui_settings_service.test.ts b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_service.test.ts similarity index 100% rename from src/core/public/ui_settings/ui_settings_service.test.ts rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_service.test.ts diff --git a/src/core/public/ui_settings/ui_settings_service.ts b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_service.ts similarity index 96% rename from src/core/public/ui_settings/ui_settings_service.ts rename to packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_service.ts index 5117ac3247af8..3ff66d8216967 100644 --- a/src/core/public/ui_settings/ui_settings_service.ts +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/src/ui_settings_service.ts @@ -11,9 +11,9 @@ import { Subject } from 'rxjs'; import type { InternalInjectedMetadataSetup } from '@kbn/core-injected-metadata-browser-internal'; import type { HttpSetup } from '@kbn/core-http-browser'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { UiSettingsApi } from './ui_settings_api'; import { UiSettingsClient } from './ui_settings_client'; -import type { IUiSettingsClient } from './types'; export interface UiSettingsServiceDeps { http: HttpSetup; diff --git a/packages/core/ui-settings/core-ui-settings-browser-internal/tsconfig.json b/packages/core/ui-settings/core-ui-settings-browser-internal/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-internal/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/core/ui-settings/core-ui-settings-browser-mocks/BUILD.bazel b/packages/core/ui-settings/core-ui-settings-browser-mocks/BUILD.bazel new file mode 100644 index 0000000000000..c9c564ccc620a --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-mocks/BUILD.bazel @@ -0,0 +1,111 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-ui-settings-browser-mocks" +PKG_REQUIRE_NAME = "@kbn/core-ui-settings-browser-mocks" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ + "@npm//rxjs", + "//packages/core/ui-settings/core-ui-settings-browser-internal" +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "@npm//rxjs", + "//packages/kbn-utility-types:npm_module_types", + "//packages/core/ui-settings/core-ui-settings-browser-internal:npm_module_types", + "//packages/core/ui-settings/core-ui-settings-browser:npm_module_types", +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/ui-settings/core-ui-settings-browser-mocks/README.md b/packages/core/ui-settings/core-ui-settings-browser-mocks/README.md new file mode 100644 index 0000000000000..15e17139c444f --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-mocks/README.md @@ -0,0 +1,3 @@ +# @kbn/core-ui-settings-browser-mocks + +This package contains the mocks for the browser-side uiSettings service. diff --git a/packages/core/ui-settings/core-ui-settings-browser-mocks/jest.config.js b/packages/core/ui-settings/core-ui-settings-browser-mocks/jest.config.js new file mode 100644 index 0000000000000..a585eb84171ea --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-mocks/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/ui-settings/core-ui-settings-browser-mocks'], +}; diff --git a/packages/core/ui-settings/core-ui-settings-browser-mocks/package.json b/packages/core/ui-settings/core-ui-settings-browser-mocks/package.json new file mode 100644 index 0000000000000..7d88d26720d3f --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-mocks/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-ui-settings-browser-mocks", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/packages/core/ui-settings/core-ui-settings-browser-mocks/src/index.ts b/packages/core/ui-settings/core-ui-settings-browser-mocks/src/index.ts new file mode 100644 index 0000000000000..1eaa0bff3a4c7 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-mocks/src/index.ts @@ -0,0 +1,9 @@ +/* + * 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. + */ + +export { uiSettingsServiceMock } from './ui_settings_service.mock'; diff --git a/src/core/public/ui_settings/ui_settings_service.mock.ts b/packages/core/ui-settings/core-ui-settings-browser-mocks/src/ui_settings_service.mock.ts similarity index 91% rename from src/core/public/ui_settings/ui_settings_service.mock.ts rename to packages/core/ui-settings/core-ui-settings-browser-mocks/src/ui_settings_service.mock.ts index d0633c4fca1fc..834a86d03e049 100644 --- a/src/core/public/ui_settings/ui_settings_service.mock.ts +++ b/packages/core/ui-settings/core-ui-settings-browser-mocks/src/ui_settings_service.mock.ts @@ -8,8 +8,8 @@ import * as Rx from 'rxjs'; import type { PublicMethodsOf } from '@kbn/utility-types'; -import { UiSettingsService } from '.'; -import { IUiSettingsClient } from './types'; +import type { UiSettingsService } from '@kbn/core-ui-settings-browser-internal'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; const createSetupContractMock = () => { const setupContract: jest.Mocked = { diff --git a/packages/core/ui-settings/core-ui-settings-browser-mocks/tsconfig.json b/packages/core/ui-settings/core-ui-settings-browser-mocks/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser-mocks/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/core/ui-settings/core-ui-settings-browser/BUILD.bazel b/packages/core/ui-settings/core-ui-settings-browser/BUILD.bazel new file mode 100644 index 0000000000000..fb495d492646f --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser/BUILD.bazel @@ -0,0 +1,108 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-ui-settings-browser" +PKG_REQUIRE_NAME = "@kbn/core-ui-settings-browser" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ + "@npm//rxjs", +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "@npm//rxjs", + "//packages/core/ui-settings/core-ui-settings-common:npm_module_types" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/ui-settings/core-ui-settings-browser/README.md b/packages/core/ui-settings/core-ui-settings-browser/README.md new file mode 100644 index 0000000000000..7bc7eb409096b --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser/README.md @@ -0,0 +1,3 @@ +# @kbn/core-ui-settings-browser + +This package contains the public types for the browser-side ui-settings service. diff --git a/packages/core/ui-settings/core-ui-settings-browser/jest.config.js b/packages/core/ui-settings/core-ui-settings-browser/jest.config.js new file mode 100644 index 0000000000000..7ab068830f85d --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/ui-settings/core-ui-settings-browser'], +}; diff --git a/packages/core/ui-settings/core-ui-settings-browser/package.json b/packages/core/ui-settings/core-ui-settings-browser/package.json new file mode 100644 index 0000000000000..e40aeeac64196 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-ui-settings-browser", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/packages/core/ui-settings/core-ui-settings-browser/src/index.ts b/packages/core/ui-settings/core-ui-settings-browser/src/index.ts new file mode 100644 index 0000000000000..99150ded40035 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser/src/index.ts @@ -0,0 +1,9 @@ +/* + * 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. + */ + +export type { UiSettingsState, IUiSettingsClient } from './types'; diff --git a/src/core/public/ui_settings/types.ts b/packages/core/ui-settings/core-ui-settings-browser/src/types.ts similarity index 96% rename from src/core/public/ui_settings/types.ts rename to packages/core/ui-settings/core-ui-settings-browser/src/types.ts index 243ac82ed14ab..4d23814c2b35d 100644 --- a/src/core/public/ui_settings/types.ts +++ b/packages/core/ui-settings/core-ui-settings-browser/src/types.ts @@ -6,8 +6,8 @@ * Side Public License, v 1. */ -import { Observable } from 'rxjs'; -import { PublicUiSettingsParams, UserProvidedValues } from '../../server/types'; +import type { Observable } from 'rxjs'; +import type { PublicUiSettingsParams, UserProvidedValues } from '@kbn/core-ui-settings-common'; /** @public */ export interface UiSettingsState { diff --git a/packages/core/ui-settings/core-ui-settings-browser/tsconfig.json b/packages/core/ui-settings/core-ui-settings-browser/tsconfig.json new file mode 100644 index 0000000000000..4c665fe2ba49a --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-browser/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node", + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/core/ui-settings/core-ui-settings-common/BUILD.bazel b/packages/core/ui-settings/core-ui-settings-common/BUILD.bazel new file mode 100644 index 0000000000000..92ffc8188cae5 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-common/BUILD.bazel @@ -0,0 +1,107 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "core-ui-settings-common" +PKG_REQUIRE_NAME = "@kbn/core-ui-settings-common" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + "src/**/*.tsx", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +RUNTIME_DEPS = [ +] + +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", + "//packages/kbn-config-schema:npm_module_types", + "//packages/kbn-analytics:npm_module_types" +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +jsts_transpiler( + name = "target_web", + srcs = SRCS, + build_pkg_name = package_name(), + web = True, +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node", ":target_web"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/core/ui-settings/core-ui-settings-common/README.md b/packages/core/ui-settings/core-ui-settings-common/README.md new file mode 100644 index 0000000000000..aa9cf61a0bc88 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-common/README.md @@ -0,0 +1,3 @@ +# @kbn/core-ui-settings-common + +This package contains the common types for Core's uiSettings service. diff --git a/packages/core/ui-settings/core-ui-settings-common/jest.config.js b/packages/core/ui-settings/core-ui-settings-common/jest.config.js new file mode 100644 index 0000000000000..1d7330c330d26 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-common/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test', + rootDir: '../../../..', + roots: ['/packages/core/ui-settings/core-ui-settings-common'], +}; diff --git a/packages/core/ui-settings/core-ui-settings-common/package.json b/packages/core/ui-settings/core-ui-settings-common/package.json new file mode 100644 index 0000000000000..1476582f96d07 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-common/package.json @@ -0,0 +1,8 @@ +{ + "name": "@kbn/core-ui-settings-common", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "browser": "./target_web/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0" +} diff --git a/packages/core/ui-settings/core-ui-settings-common/src/index.ts b/packages/core/ui-settings/core-ui-settings-common/src/index.ts new file mode 100644 index 0000000000000..da84668311cd2 --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-common/src/index.ts @@ -0,0 +1,15 @@ +/* + * 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. + */ + +export type { + UiSettingsType, + DeprecationSettings, + UiSettingsParams, + PublicUiSettingsParams, + UserProvidedValues, +} from './ui_settings'; diff --git a/src/core/types/ui_settings.ts b/packages/core/ui-settings/core-ui-settings-common/src/ui_settings.ts similarity index 96% rename from src/core/types/ui_settings.ts rename to packages/core/ui-settings/core-ui-settings-common/src/ui_settings.ts index 469f43327e498..ea1e5f92a7491 100644 --- a/src/core/types/ui_settings.ts +++ b/packages/core/ui-settings/core-ui-settings-common/src/ui_settings.ts @@ -6,8 +6,8 @@ * Side Public License, v 1. */ -import { Type } from '@kbn/config-schema'; -import { UiCounterMetricType } from '@kbn/analytics'; +import type { Type } from '@kbn/config-schema'; +import type { UiCounterMetricType } from '@kbn/analytics'; /** * UI element type to represent the settings. diff --git a/packages/core/ui-settings/core-ui-settings-common/tsconfig.json b/packages/core/ui-settings/core-ui-settings-common/tsconfig.json new file mode 100644 index 0000000000000..39d3c7097814a --- /dev/null +++ b/packages/core/ui-settings/core-ui-settings-common/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/src/core/public/chrome/chrome_service.test.ts b/src/core/public/chrome/chrome_service.test.ts index f5d276ef25172..737b561bed8e3 100644 --- a/src/core/public/chrome/chrome_service.test.ts +++ b/src/core/public/chrome/chrome_service.test.ts @@ -16,7 +16,7 @@ import { httpServiceMock } from '@kbn/core-http-browser-mocks'; import { App, PublicAppInfo } from '../application'; import { applicationServiceMock } from '../application/application_service.mock'; import { notificationServiceMock } from '../notifications/notifications_service.mock'; -import { uiSettingsServiceMock } from '../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import { ChromeService } from './chrome_service'; import { getAppInfo } from '../application/utils'; diff --git a/src/core/public/core_app/core_app.ts b/src/core/public/core_app/core_app.ts index 82ae595f86477..d834ece6e76cf 100644 --- a/src/core/public/core_app/core_app.ts +++ b/src/core/public/core_app/core_app.ts @@ -11,6 +11,7 @@ import type { CoreContext } from '@kbn/core-base-browser-internal'; import type { InternalInjectedMetadataSetup } from '@kbn/core-injected-metadata-browser-internal'; import type { DocLinksStart } from '@kbn/core-doc-links-browser'; import type { HttpSetup, HttpStart } from '@kbn/core-http-browser'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { type InternalApplicationSetup, type InternalApplicationStart, @@ -18,7 +19,6 @@ import { type AppMountParameters, } from '../application'; import type { NotificationsSetup, NotificationsStart } from '../notifications'; -import type { IUiSettingsClient } from '../ui_settings'; import { renderApp as renderErrorApp, setupPublicBaseUrlConfigWarning, diff --git a/src/core/public/core_app/errors/url_overflow.test.ts b/src/core/public/core_app/errors/url_overflow.test.ts index 0e166e5d5e7ee..e68b80931d2ec 100644 --- a/src/core/public/core_app/errors/url_overflow.test.ts +++ b/src/core/public/core_app/errors/url_overflow.test.ts @@ -11,9 +11,9 @@ import type { IBasePath } from '@kbn/core-http-browser'; import { BasePath } from '@kbn/core-http-browser-internal'; import { notificationServiceMock } from '../../notifications/notifications_service.mock'; -import { uiSettingsServiceMock } from '../../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import type { IToasts } from '../../notifications'; -import type { IUiSettingsClient } from '../../ui_settings'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { setupUrlOverflowDetection, URL_MAX_LENGTH, URL_WARNING_LENGTH } from './url_overflow'; diff --git a/src/core/public/core_app/errors/url_overflow.tsx b/src/core/public/core_app/errors/url_overflow.tsx index f2a525a9c2e68..4925cf18c0f77 100644 --- a/src/core/public/core_app/errors/url_overflow.tsx +++ b/src/core/public/core_app/errors/url_overflow.tsx @@ -13,9 +13,9 @@ import { i18n } from '@kbn/i18n'; import { FormattedMessage } from '@kbn/i18n-react'; import type { IBasePath } from '@kbn/core-http-browser'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { mountReactNode } from '../../utils'; import { IToasts } from '../../notifications'; -import { IUiSettingsClient } from '../../ui_settings'; const IE_REGEX = /(; ?MSIE |Edge\/\d|Trident\/[\d+\.]+;.*rv:*11\.\d+)/; export const IS_IE = IE_REGEX.test(window.navigator.userAgent); diff --git a/src/core/public/core_system.test.mocks.ts b/src/core/public/core_system.test.mocks.ts index 0d46af80b34eb..baf4c28401c06 100644 --- a/src/core/public/core_system.test.mocks.ts +++ b/src/core/public/core_system.test.mocks.ts @@ -18,7 +18,7 @@ import { i18nServiceMock } from '@kbn/core-i18n-browser-mocks'; import { notificationServiceMock } from './notifications/notifications_service.mock'; import { overlayServiceMock } from './overlays/overlay_service.mock'; import { pluginsServiceMock } from './plugins/plugins_service.mock'; -import { uiSettingsServiceMock } from './ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import { renderingServiceMock } from './rendering/rendering_service.mock'; import { integrationsServiceMock } from './integrations/integrations_service.mock'; import { coreAppMock } from './core_app/core_app.mock'; @@ -76,7 +76,7 @@ export const MockUiSettingsService = uiSettingsServiceMock.create(); export const UiSettingsServiceConstructor = jest .fn() .mockImplementation(() => MockUiSettingsService); -jest.doMock('./ui_settings', () => ({ +jest.doMock('@kbn/core-ui-settings-browser-internal', () => ({ UiSettingsService: UiSettingsServiceConstructor, })); diff --git a/src/core/public/core_system.ts b/src/core/public/core_system.ts index 834927ae7f541..710d7b90c4c30 100644 --- a/src/core/public/core_system.ts +++ b/src/core/public/core_system.ts @@ -23,13 +23,13 @@ import { ExecutionContextService } from '@kbn/core-execution-context-browser-int import type { FatalErrorsSetup } from '@kbn/core-fatal-errors-browser'; import { FatalErrorsService } from '@kbn/core-fatal-errors-browser-internal'; import { HttpService } from '@kbn/core-http-browser-internal'; +import { UiSettingsService } from '@kbn/core-ui-settings-browser-internal'; import { DeprecationsService } from '@kbn/core-deprecations-browser-internal'; import { CoreSetup, CoreStart } from '.'; import { ChromeService } from './chrome'; import { NotificationsService } from './notifications'; import { OverlayService } from './overlays'; import { PluginsService } from './plugins'; -import { UiSettingsService } from './ui_settings'; import { ApplicationService } from './application'; import { RenderingService } from './rendering'; import { SavedObjectsService } from './saved_objects'; diff --git a/src/core/public/index.ts b/src/core/public/index.ts index b3ffc84a51f58..ccde84105ea89 100644 --- a/src/core/public/index.ts +++ b/src/core/public/index.ts @@ -42,6 +42,7 @@ import type { FatalErrorsStart, FatalErrorInfo, } from '@kbn/core-fatal-errors-browser'; +import type { UiSettingsState, IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import type { DeprecationsServiceStart } from '@kbn/core-deprecations-browser'; import type { ChromeBadge, @@ -73,7 +74,6 @@ import type { PluginInitializerContext, PluginOpaqueId, } from './plugins'; -import type { UiSettingsState, IUiSettingsClient } from './ui_settings'; import type { ApplicationSetup, Capabilities, ApplicationStart } from './application'; import type { SavedObjectsStart } from './saved_objects'; @@ -82,7 +82,12 @@ export type { DomainDeprecationDetails } from '@kbn/core-deprecations-common'; export type { CoreContext } from '@kbn/core-base-browser-internal'; export type { CoreSystem } from './core_system'; export { DEFAULT_APP_CATEGORIES, APP_WRAPPER_CLASS } from '../utils'; -export type { AppCategory, UiSettingsParams, UserProvidedValues, UiSettingsType } from '../types'; +export type { AppCategory } from '../types'; +export type { + UiSettingsParams, + UserProvidedValues, + UiSettingsType, +} from '@kbn/core-ui-settings-common'; export type { AnalyticsServiceSetup, AnalyticsServiceStart } from '@kbn/core-analytics-browser'; export type { diff --git a/src/core/public/integrations/integrations_service.test.ts b/src/core/public/integrations/integrations_service.test.ts index 9543012833feb..a98e5bf1d7bc2 100644 --- a/src/core/public/integrations/integrations_service.test.ts +++ b/src/core/public/integrations/integrations_service.test.ts @@ -9,7 +9,7 @@ import { styleServiceMock, momentServiceMock } from './integrations_service.test.mocks'; import { IntegrationsService } from './integrations_service'; -import { uiSettingsServiceMock } from '../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; describe('IntegrationsService', () => { test('it wires up styles and moment', async () => { diff --git a/src/core/public/integrations/integrations_service.ts b/src/core/public/integrations/integrations_service.ts index e03546998ba7e..ca01e1b86ce7e 100644 --- a/src/core/public/integrations/integrations_service.ts +++ b/src/core/public/integrations/integrations_service.ts @@ -7,7 +7,7 @@ */ import type { CoreService } from '@kbn/core-base-browser-internal'; -import { IUiSettingsClient } from '../ui_settings'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { MomentService } from './moment'; import { StylesService } from './styles'; diff --git a/src/core/public/integrations/moment/moment_service.test.ts b/src/core/public/integrations/moment/moment_service.test.ts index 4e7c345e7e05d..d3c4d44f100e8 100644 --- a/src/core/public/integrations/moment/moment_service.test.ts +++ b/src/core/public/integrations/moment/moment_service.test.ts @@ -8,7 +8,7 @@ import { momentMock } from './moment_service.test.mocks'; import { MomentService } from './moment_service'; -import { uiSettingsServiceMock } from '../../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import { BehaviorSubject } from 'rxjs'; describe('MomentService', () => { diff --git a/src/core/public/integrations/moment/moment_service.ts b/src/core/public/integrations/moment/moment_service.ts index 0f58c8d7fb19f..633223864f202 100644 --- a/src/core/public/integrations/moment/moment_service.ts +++ b/src/core/public/integrations/moment/moment_service.ts @@ -11,7 +11,7 @@ import { merge, Subscription } from 'rxjs'; import { tap } from 'rxjs/operators'; import type { CoreService } from '@kbn/core-base-browser-internal'; -import { IUiSettingsClient } from '../../ui_settings'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; interface StartDeps { uiSettings: IUiSettingsClient; diff --git a/src/core/public/integrations/styles/styles_service.test.ts b/src/core/public/integrations/styles/styles_service.test.ts index 5fae4b976c59e..20625dcbc3b94 100644 --- a/src/core/public/integrations/styles/styles_service.test.ts +++ b/src/core/public/integrations/styles/styles_service.test.ts @@ -11,7 +11,7 @@ import { BehaviorSubject } from 'rxjs'; jest.mock('!!raw-loader!./disable_animations.css', () => 'MOCK DISABLE ANIMATIONS CSS'); import { StylesService } from './styles_service'; -import { uiSettingsServiceMock } from '../../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; describe('StylesService', () => { const flushPromises = () => new Promise((resolve) => setTimeout(resolve, 100)); diff --git a/src/core/public/integrations/styles/styles_service.ts b/src/core/public/integrations/styles/styles_service.ts index 3e8f02739a8d0..9bbed46ff12f5 100644 --- a/src/core/public/integrations/styles/styles_service.ts +++ b/src/core/public/integrations/styles/styles_service.ts @@ -9,7 +9,7 @@ import { Subscription } from 'rxjs'; import type { CoreService } from '@kbn/core-base-browser-internal'; -import { IUiSettingsClient } from '../../ui_settings'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; // @ts-expect-error import disableAnimationsCss from '!!raw-loader!./disable_animations.css'; diff --git a/src/core/public/mocks.ts b/src/core/public/mocks.ts index 97f3af9f33cca..73e4a5a80fbde 100644 --- a/src/core/public/mocks.ts +++ b/src/core/public/mocks.ts @@ -17,6 +17,7 @@ import { executionContextServiceMock } from '@kbn/core-execution-context-browser import { i18nServiceMock } from '@kbn/core-i18n-browser-mocks'; import { fatalErrorsServiceMock } from '@kbn/core-fatal-errors-browser-mocks'; import { httpServiceMock } from '@kbn/core-http-browser-mocks'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import { deprecationsServiceMock } from '@kbn/core-deprecations-browser-mocks'; import type { PluginInitializerContext, AppMountParameters } from '.'; // Import values from their individual modules instead. @@ -25,7 +26,6 @@ import { applicationServiceMock } from './application/application_service.mock'; import { chromeServiceMock } from './chrome/chrome_service.mock'; import { notificationServiceMock } from './notifications/notifications_service.mock'; import { overlayServiceMock } from './overlays/overlay_service.mock'; -import { uiSettingsServiceMock } from './ui_settings/ui_settings_service.mock'; import { savedObjectsServiceMock } from './saved_objects/saved_objects_service.mock'; export { injectedMetadataServiceMock } from '@kbn/core-injected-metadata-browser-mocks'; @@ -39,7 +39,7 @@ export { httpServiceMock } from '@kbn/core-http-browser-mocks'; export { i18nServiceMock } from '@kbn/core-i18n-browser-mocks'; export { notificationServiceMock } from './notifications/notifications_service.mock'; export { overlayServiceMock } from './overlays/overlay_service.mock'; -export { uiSettingsServiceMock } from './ui_settings/ui_settings_service.mock'; +export { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; export { savedObjectsServiceMock } from './saved_objects/saved_objects_service.mock'; export { scopedHistoryMock } from './application/scoped_history.mock'; export { applicationServiceMock } from './application/application_service.mock'; diff --git a/src/core/public/notifications/notifications_service.ts b/src/core/public/notifications/notifications_service.ts index 859e21de5ffed..6a5a5f81f1a40 100644 --- a/src/core/public/notifications/notifications_service.ts +++ b/src/core/public/notifications/notifications_service.ts @@ -11,8 +11,8 @@ import { i18n } from '@kbn/i18n'; import { Subscription } from 'rxjs'; import type { ThemeServiceStart } from '@kbn/core-theme-browser'; import type { I18nStart } from '@kbn/core-i18n-browser'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { ToastsService, ToastsSetup, ToastsStart } from './toasts'; -import { IUiSettingsClient } from '../ui_settings'; import { OverlayStart } from '../overlays'; export interface SetupDeps { diff --git a/src/core/public/notifications/toasts/toasts_api.test.ts b/src/core/public/notifications/toasts/toasts_api.test.ts index d6b67bdb63f7a..ec07f32d2f1c9 100644 --- a/src/core/public/notifications/toasts/toasts_api.test.ts +++ b/src/core/public/notifications/toasts/toasts_api.test.ts @@ -10,7 +10,7 @@ import { firstValueFrom } from 'rxjs'; import { ToastsApi } from './toasts_api'; -import { uiSettingsServiceMock } from '../../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import { i18nServiceMock } from '@kbn/core-i18n-browser-mocks'; async function getCurrentToasts(toasts: ToastsApi) { diff --git a/src/core/public/notifications/toasts/toasts_api.tsx b/src/core/public/notifications/toasts/toasts_api.tsx index ecf32d442931c..f78927c7f7579 100644 --- a/src/core/public/notifications/toasts/toasts_api.tsx +++ b/src/core/public/notifications/toasts/toasts_api.tsx @@ -12,10 +12,10 @@ import * as Rx from 'rxjs'; import { omitBy, isUndefined } from 'lodash'; import type { I18nStart } from '@kbn/core-i18n-browser'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { ErrorToast } from './error_toast'; import { MountPoint } from '../../types'; import { mountReactNode } from '../../utils'; -import { IUiSettingsClient } from '../../ui_settings'; import { OverlayStart } from '../../overlays'; /** diff --git a/src/core/public/notifications/toasts/toasts_service.test.tsx b/src/core/public/notifications/toasts/toasts_service.test.tsx index d2694d076e8c0..a6854f679d086 100644 --- a/src/core/public/notifications/toasts/toasts_service.test.tsx +++ b/src/core/public/notifications/toasts/toasts_service.test.tsx @@ -12,7 +12,7 @@ import { ToastsService } from './toasts_service'; import { ToastsApi } from './toasts_api'; import { overlayServiceMock } from '../../overlays/overlay_service.mock'; import { themeServiceMock } from '@kbn/core-theme-browser-mocks'; -import { uiSettingsServiceMock } from '../../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; const mockI18n: any = { Context: function I18nContext() { diff --git a/src/core/public/notifications/toasts/toasts_service.tsx b/src/core/public/notifications/toasts/toasts_service.tsx index 63edd56085797..692e6ec9dd504 100644 --- a/src/core/public/notifications/toasts/toasts_service.tsx +++ b/src/core/public/notifications/toasts/toasts_service.tsx @@ -12,7 +12,7 @@ import { render, unmountComponentAtNode } from 'react-dom'; import type { ThemeServiceStart } from '@kbn/core-theme-browser'; import type { I18nStart } from '@kbn/core-i18n-browser'; import { CoreContextProvider } from '@kbn/core-theme-browser-internal'; -import { IUiSettingsClient } from '../../ui_settings'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { GlobalToastList } from './global_toast_list'; import { ToastsApi, IToasts } from './toasts_api'; import { OverlayStart } from '../../overlays'; diff --git a/src/core/public/overlays/banners/banners_service.test.ts b/src/core/public/overlays/banners/banners_service.test.ts index d3093879f8715..69f30d99b9826 100644 --- a/src/core/public/overlays/banners/banners_service.test.ts +++ b/src/core/public/overlays/banners/banners_service.test.ts @@ -9,7 +9,7 @@ import { OverlayBannersService, OverlayBannersStart } from './banners_service'; import { take } from 'rxjs/operators'; import { i18nServiceMock } from '@kbn/core-i18n-browser-mocks'; -import { uiSettingsServiceMock } from '../../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; describe('OverlayBannersService', () => { let service: OverlayBannersStart; diff --git a/src/core/public/overlays/banners/banners_service.tsx b/src/core/public/overlays/banners/banners_service.tsx index a5436d21ef45e..11bc995c059f8 100644 --- a/src/core/public/overlays/banners/banners_service.tsx +++ b/src/core/public/overlays/banners/banners_service.tsx @@ -11,9 +11,9 @@ import { BehaviorSubject, Observable } from 'rxjs'; import { map } from 'rxjs/operators'; import type { I18nStart } from '@kbn/core-i18n-browser'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { PriorityMap } from './priority_map'; import { BannersList } from './banners_list'; -import { IUiSettingsClient } from '../../ui_settings'; import { MountPoint } from '../../types'; import { UserBannerService } from './user_banner_service'; diff --git a/src/core/public/overlays/banners/user_banner_service.test.ts b/src/core/public/overlays/banners/user_banner_service.test.ts index 52d6d00171261..e0a46cbb7fd6a 100644 --- a/src/core/public/overlays/banners/user_banner_service.test.ts +++ b/src/core/public/overlays/banners/user_banner_service.test.ts @@ -6,7 +6,7 @@ * Side Public License, v 1. */ -import { uiSettingsServiceMock } from '../../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import { UserBannerService } from './user_banner_service'; import { overlayBannersServiceMock } from './banners_service.mock'; import { i18nServiceMock } from '@kbn/core-i18n-browser-mocks'; diff --git a/src/core/public/overlays/banners/user_banner_service.tsx b/src/core/public/overlays/banners/user_banner_service.tsx index 175d43ea8ba59..7d3c9eab9b17f 100644 --- a/src/core/public/overlays/banners/user_banner_service.tsx +++ b/src/core/public/overlays/banners/user_banner_service.tsx @@ -15,7 +15,7 @@ import { FormattedMessage } from '@kbn/i18n-react'; import { EuiCallOut, EuiButton, EuiLoadingSpinner } from '@elastic/eui'; import type { I18nStart } from '@kbn/core-i18n-browser'; -import { IUiSettingsClient } from '../../ui_settings'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { OverlayBannersStart } from './banners_service'; interface StartDeps { diff --git a/src/core/public/overlays/overlay_service.ts b/src/core/public/overlays/overlay_service.ts index 35e839b0e175b..07a8cbea29a37 100644 --- a/src/core/public/overlays/overlay_service.ts +++ b/src/core/public/overlays/overlay_service.ts @@ -8,7 +8,7 @@ import type { ThemeServiceStart } from '@kbn/core-theme-browser'; import type { I18nStart } from '@kbn/core-i18n-browser'; -import { IUiSettingsClient } from '../ui_settings'; +import type { IUiSettingsClient } from '@kbn/core-ui-settings-browser'; import { OverlayBannersStart, OverlayBannersService } from './banners'; import { FlyoutService, OverlayFlyoutStart } from './flyout'; import { ModalService, OverlayModalStart } from './modal'; diff --git a/src/core/public/plugins/plugins_service.test.ts b/src/core/public/plugins/plugins_service.test.ts index d6b7810f44cd6..dbc3fd253a1c1 100644 --- a/src/core/public/plugins/plugins_service.test.ts +++ b/src/core/public/plugins/plugins_service.test.ts @@ -34,7 +34,7 @@ import { applicationServiceMock } from '../application/application_service.mock' import { overlayServiceMock } from '../overlays/overlay_service.mock'; import { chromeServiceMock } from '../chrome/chrome_service.mock'; import { fatalErrorsServiceMock } from '@kbn/core-fatal-errors-browser-mocks'; -import { uiSettingsServiceMock } from '../ui_settings/ui_settings_service.mock'; +import { uiSettingsServiceMock } from '@kbn/core-ui-settings-browser-mocks'; import { httpServiceMock } from '@kbn/core-http-browser-mocks'; import type { CoreSetup, CoreStart, PluginInitializerContext } from '..'; import { savedObjectsServiceMock } from '../saved_objects/saved_objects_service.mock'; diff --git a/src/core/public/types.ts b/src/core/public/types.ts index 5b594373e3523..8df8b2c10f179 100644 --- a/src/core/public/types.ts +++ b/src/core/public/types.ts @@ -11,7 +11,7 @@ export type { PublicUiSettingsParams, UserProvidedValues, UiSettingsType, -} from '../types'; +} from '@kbn/core-ui-settings-common'; /** * A function that should mount DOM content inside the provided container element diff --git a/src/core/server/ui_settings/types.ts b/src/core/server/ui_settings/types.ts index c442e37c4b022..a7405e8b75731 100644 --- a/src/core/server/ui_settings/types.ts +++ b/src/core/server/ui_settings/types.ts @@ -5,16 +5,20 @@ * in compliance with, at your election, the Elastic License 2.0 or the Server * Side Public License, v 1. */ +import { + UiSettingsParams, + UserProvidedValues, + PublicUiSettingsParams, +} from '@kbn/core-ui-settings-common'; import { SavedObjectsClientContract } from '../saved_objects/types'; -import { UiSettingsParams, UserProvidedValues, PublicUiSettingsParams } from '../../types'; export type { UiSettingsParams, - PublicUiSettingsParams, DeprecationSettings, + PublicUiSettingsParams, UiSettingsType, UserProvidedValues, -} from '../../types'; +} from '@kbn/core-ui-settings-common'; /** * Server-side client that provides access to the advanced settings stored in elasticsearch. diff --git a/src/core/types/index.ts b/src/core/types/index.ts index 7b9df84770365..005e5fb611cfb 100644 --- a/src/core/types/index.ts +++ b/src/core/types/index.ts @@ -12,6 +12,12 @@ */ export * from './capabilities'; export * from './app_category'; -export * from './ui_settings'; export * from './saved_objects'; export type { KibanaExecutionContext } from '@kbn/core-execution-context-common'; +export type { + UiSettingsType, + DeprecationSettings, + UiSettingsParams, + PublicUiSettingsParams, + UserProvidedValues, +} from '@kbn/core-ui-settings-common'; diff --git a/src/plugins/data_views/public/data_views/data_views_api_client.test.mock.ts b/src/plugins/data_views/public/data_views/data_views_api_client.test.mock.ts index 5880bd9fd36fa..fd12291a2bc16 100644 --- a/src/plugins/data_views/public/data_views/data_views_api_client.test.mock.ts +++ b/src/plugins/data_views/public/data_views/data_views_api_client.test.mock.ts @@ -6,7 +6,7 @@ * Side Public License, v 1. */ -import { setup } from '@kbn/core/test_helpers/http_test_setup'; +import { setup } from '@kbn/core-test-helpers-http-setup-browser'; export const { http } = setup((injectedMetadata) => { injectedMetadata.getBasePath.mockReturnValue('/hola/daro/'); diff --git a/x-pack/plugins/security/public/session/unauthorized_response_http_interceptor.test.ts b/x-pack/plugins/security/public/session/unauthorized_response_http_interceptor.test.ts index d82a041a4fe28..b77ceb6bf1882 100644 --- a/x-pack/plugins/security/public/session/unauthorized_response_http_interceptor.test.ts +++ b/x-pack/plugins/security/public/session/unauthorized_response_http_interceptor.test.ts @@ -8,8 +8,8 @@ // @ts-ignore import fetchMock from 'fetch-mock/es5/client'; +import { setup } from '@kbn/core-test-helpers-http-setup-browser'; import { applicationServiceMock } from '@kbn/core/public/mocks'; -import { setup } from '@kbn/core/test_helpers/http_test_setup'; import { SessionExpired } from './session_expired'; import { UnauthorizedResponseHttpInterceptor } from './unauthorized_response_http_interceptor'; diff --git a/yarn.lock b/yarn.lock index 20a306f722661..f8f09a1dab087 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3319,6 +3319,10 @@ version "0.0.0" uid "" +"@kbn/core-test-helpers-http-setup-browser@link:bazel-bin/packages/core/test-helpers/core-test-helpers-http-setup-browser": + version "0.0.0" + uid "" + "@kbn/core-theme-browser-internal@link:bazel-bin/packages/core/theme/core-theme-browser-internal": version "0.0.0" uid "" @@ -3331,6 +3335,22 @@ version "0.0.0" uid "" +"@kbn/core-ui-settings-browser-internal@link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-internal": + version "0.0.0" + uid "" + +"@kbn/core-ui-settings-browser-mocks@link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-mocks": + version "0.0.0" + uid "" + +"@kbn/core-ui-settings-browser@link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser": + version "0.0.0" + uid "" + +"@kbn/core-ui-settings-common@link:bazel-bin/packages/core/ui-settings/core-ui-settings-common": + version "0.0.0" + uid "" + "@kbn/crypto-browser@link:bazel-bin/packages/kbn-crypto-browser": version "0.0.0" uid "" @@ -6978,6 +6998,10 @@ version "0.0.0" uid "" +"@types/kbn__core-test-helpers-http-setup-browser@link:bazel-bin/packages/core/test-helpers/core-test-helpers-http-setup-browser/npm_module_types": + version "0.0.0" + uid "" + "@types/kbn__core-theme-browser-internal@link:bazel-bin/packages/core/theme/core-theme-browser-internal/npm_module_types": version "0.0.0" uid "" @@ -6990,6 +7014,22 @@ version "0.0.0" uid "" +"@types/kbn__core-ui-settings-browser-internal@link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-internal/npm_module_types": + version "0.0.0" + uid "" + +"@types/kbn__core-ui-settings-browser-mocks@link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser-mocks/npm_module_types": + version "0.0.0" + uid "" + +"@types/kbn__core-ui-settings-browser@link:bazel-bin/packages/core/ui-settings/core-ui-settings-browser/npm_module_types": + version "0.0.0" + uid "" + +"@types/kbn__core-ui-settings-common@link:bazel-bin/packages/core/ui-settings/core-ui-settings-common/npm_module_types": + version "0.0.0" + uid "" + "@types/kbn__crypto-browser@link:bazel-bin/packages/kbn-crypto-browser/npm_module_types": version "0.0.0" uid "" From 4e043fb9034800d88574c8d4e42e2fba4cf0f204 Mon Sep 17 00:00:00 2001 From: Rashmi Kulkarni Date: Thu, 14 Jul 2022 10:03:32 -0700 Subject: [PATCH 036/111] trying to unskip a flaky test (#136353) --- x-pack/test/accessibility/apps/tags.ts | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/x-pack/test/accessibility/apps/tags.ts b/x-pack/test/accessibility/apps/tags.ts index dd992b191e436..2d0e9278e7e7d 100644 --- a/x-pack/test/accessibility/apps/tags.ts +++ b/x-pack/test/accessibility/apps/tags.ts @@ -15,10 +15,11 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { const testSubjects = getService('testSubjects'); const retry = getService('retry'); const toasts = getService('toasts'); + const kibanaServer = getService('kibanaServer'); - // FLAKY: https://github.com/elastic/kibana/issues/136033 - describe.skip('Kibana Tags Page Accessibility', () => { + describe('Kibana Tags Page Accessibility', () => { before(async () => { + await kibanaServer.savedObjects.cleanStandardList(); await PageObjects.common.navigateToUrl('home', '/tutorial_directory/sampleData', { useActualUrl: true, }); @@ -34,6 +35,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { }); await PageObjects.header.waitUntilLoadingHasFinished(); await PageObjects.home.removeSampleDataSet('flights'); + await kibanaServer.savedObjects.cleanStandardList(); }); it('tags main page meets a11y validations', async () => { @@ -72,8 +74,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { await a11y.testAppSnapshot(); }); - // https://github.com/elastic/kibana/issues/135985 inconsistent test failure - it.skip('tag assignment panel meets a11y requirements', async () => { + it('tag assignment panel meets a11y requirements', async () => { await testSubjects.click('euiCollapsedItemActionsButton'); const actionOnTag = 'assign'; await PageObjects.tagManagement.clickActionItem(actionOnTag); @@ -81,14 +82,9 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { }); it('tag management page with connections column populated meets a11y requirements', async () => { - await testSubjects.click('euiCollapsedItemActionsButton'); - const actionOnTag = 'assign'; - await PageObjects.tagManagement.clickActionItem(actionOnTag); await testSubjects.click('assignFlyout-selectAllButton'); - await testSubjects.click('assignFlyoutConfirmButton'); await toasts.dismissAllToasts(); - await retry.try(async () => { await a11y.testAppSnapshot(); }); From a91aeb42ffef8d34f1fa0c8af81877e9dfa7f66a Mon Sep 17 00:00:00 2001 From: Jonathan Budzenski Date: Thu, 14 Jul 2022 12:03:49 -0500 Subject: [PATCH 037/111] Remove percy based visual regression tests (#136359) * Remove percy based visual regression tests These have been disabled for ~3 years, the agent is deprecated, and our snapshot environment is inactive. * [CI] Auto-commit changed files from 'yarn kbn run build -i @kbn/pm' * update codeowners Co-authored-by: kibanamachine <42973632+kibanamachine@users.noreply.github.com> --- .buildkite/ftr_configs.yml | 2 - .eslintrc.js | 1 - .github/CODEOWNERS | 1 - package.json | 1 - packages/kbn-pm/dist/index.js | 88 ++-- test/visual_regression/config.ts | 30 -- .../visual_regression/ftr_provider_context.ts | 15 - test/visual_regression/services/index.ts | 15 - .../services/visual_testing/index.ts | 9 - .../visual_testing/take_percy_snapshot.js | 102 ----- .../services/visual_testing/visual_testing.ts | 114 ----- test/visual_regression/tests/console_app.ts | 71 --- .../tests/discover/chart_visualization.ts | 117 ----- .../visual_regression/tests/discover/index.ts | 25 -- test/visual_regression/tests/vega/index.ts | 25 -- .../tests/vega/vega_map_visualization.ts | 39 -- x-pack/test/visual_regression/config.ts | 31 -- .../ftr_provider_context.d.ts | 13 - x-pack/test/visual_regression/page_objects.ts | 10 - x-pack/test/visual_regression/services.ts | 14 - .../tests/canvas/fullscreen.js | 25 -- .../visual_regression/tests/canvas/index.js | 30 -- .../visual_regression/tests/infra/index.js | 19 - .../tests/infra/saved_views.js | 87 ---- .../tests/infra/waffle_map.js | 27 -- .../visual_regression/tests/login_page.ts | 58 --- .../visual_regression/tests/maps/index.js | 61 --- .../tests/maps/vector_styling.js | 49 --- yarn.lock | 415 +----------------- 29 files changed, 66 insertions(+), 1428 deletions(-) delete mode 100644 test/visual_regression/config.ts delete mode 100644 test/visual_regression/ftr_provider_context.ts delete mode 100644 test/visual_regression/services/index.ts delete mode 100644 test/visual_regression/services/visual_testing/index.ts delete mode 100644 test/visual_regression/services/visual_testing/take_percy_snapshot.js delete mode 100644 test/visual_regression/services/visual_testing/visual_testing.ts delete mode 100644 test/visual_regression/tests/console_app.ts delete mode 100644 test/visual_regression/tests/discover/chart_visualization.ts delete mode 100644 test/visual_regression/tests/discover/index.ts delete mode 100644 test/visual_regression/tests/vega/index.ts delete mode 100644 test/visual_regression/tests/vega/vega_map_visualization.ts delete mode 100644 x-pack/test/visual_regression/config.ts delete mode 100644 x-pack/test/visual_regression/ftr_provider_context.d.ts delete mode 100644 x-pack/test/visual_regression/page_objects.ts delete mode 100644 x-pack/test/visual_regression/services.ts delete mode 100644 x-pack/test/visual_regression/tests/canvas/fullscreen.js delete mode 100644 x-pack/test/visual_regression/tests/canvas/index.js delete mode 100644 x-pack/test/visual_regression/tests/infra/index.js delete mode 100644 x-pack/test/visual_regression/tests/infra/saved_views.js delete mode 100644 x-pack/test/visual_regression/tests/infra/waffle_map.js delete mode 100644 x-pack/test/visual_regression/tests/login_page.ts delete mode 100644 x-pack/test/visual_regression/tests/maps/index.js delete mode 100644 x-pack/test/visual_regression/tests/maps/vector_styling.js diff --git a/.buildkite/ftr_configs.yml b/.buildkite/ftr_configs.yml index 39a8b8b9f0a66..ef21725869c3e 100644 --- a/.buildkite/ftr_configs.yml +++ b/.buildkite/ftr_configs.yml @@ -44,8 +44,6 @@ disabled: - x-pack/plugins/observability/e2e/synthetics_run.ts # Configs that exist but weren't running in CI when this file was introduced - - test/visual_regression/config.ts - - x-pack/test/visual_regression/config.ts - x-pack/test/alerting_api_integration/security_and_spaces/group2/tests/actions/config.ts - x-pack/test/alerting_api_integration/security_and_spaces/group2/tests/telemetry/config.ts - x-pack/test/alerting_api_integration/spaces_only_legacy/config.ts diff --git a/.eslintrc.js b/.eslintrc.js index 385d241e52fff..9ed08807b8e23 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -702,7 +702,6 @@ module.exports = { 'test/*/config_open.ts', 'test/*/*.config.ts', 'test/*/{tests,test_suites,apis,apps}/**/*', - 'test/visual_regression/tests/**/*', 'x-pack/test/*/{tests,test_suites,apis,apps}/**/*', 'x-pack/test/*/*config.*ts', 'x-pack/test/saved_object_api_integration/*/apis/**/*', diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 670fc3a7a4cac..8b0af587e0032 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -210,7 +210,6 @@ /x-pack/test/api_integration/apis/maps/ @elastic/kibana-gis /x-pack/test/functional/apps/maps/ @elastic/kibana-gis /x-pack/test/functional/es_archives/maps/ @elastic/kibana-gis -/x-pack/test/visual_regression/tests/maps/index.js @elastic/kibana-gis /x-pack/plugins/stack_alerts/server/alert_types/geo_containment @elastic/kibana-gis /x-pack/plugins/stack_alerts/public/alert_types/geo_containment @elastic/kibana-gis #CC# /x-pack/plugins/file_upload @elastic/kibana-gis diff --git a/package.json b/package.json index 9294089cb355a..42da0114078f0 100644 --- a/package.json +++ b/package.json @@ -616,7 +616,6 @@ "@mapbox/vector-tile": "1.3.1", "@octokit/rest": "^16.35.0", "@openpgp/web-stream-tools": "^0.0.10", - "@percy/agent": "^0.28.6", "@storybook/addon-a11y": "^6.4.22", "@storybook/addon-actions": "^6.4.22", "@storybook/addon-controls": "^6.4.22", diff --git a/packages/kbn-pm/dist/index.js b/packages/kbn-pm/dist/index.js index 647e8a8d4bbbe..e9e0fd88618fe 100644 --- a/packages/kbn-pm/dist/index.js +++ b/packages/kbn-pm/dist/index.js @@ -23844,7 +23844,7 @@ module.exports.sync = (patterns, {force, dryRun, cwd = process.cwd(), ...options "use strict"; -const indentString = __webpack_require__("../../node_modules/del/node_modules/indent-string/index.js"); +const indentString = __webpack_require__("../../node_modules/indent-string/index.js"); const cleanStack = __webpack_require__("../../node_modules/clean-stack/index.js"); const cleanInternalStack = stack => stack.replace(/\s+at .*aggregate-error\/index.js:\d+:\d+\)?/g, ''); @@ -24257,49 +24257,6 @@ module.exports = { }; -/***/ }), - -/***/ "../../node_modules/del/node_modules/indent-string/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = (string, count = 1, options) => { - options = { - indent: ' ', - includeEmptyLines: false, - ...options - }; - - if (typeof string !== 'string') { - throw new TypeError( - `Expected \`input\` to be a \`string\`, got \`${typeof string}\`` - ); - } - - if (typeof count !== 'number') { - throw new TypeError( - `Expected \`count\` to be a \`number\`, got \`${typeof count}\`` - ); - } - - if (typeof options.indent !== 'string') { - throw new TypeError( - `Expected \`options.indent\` to be a \`string\`, got \`${typeof options.indent}\`` - ); - } - - if (count === 0) { - return string; - } - - const regex = options.includeEmptyLines ? /^/gm : /^(?!\s*$)/gm; - - return string.replace(regex, options.indent.repeat(count)); -}; - - /***/ }), /***/ "../../node_modules/del/node_modules/p-map/index.js": @@ -34349,6 +34306,49 @@ if ( }()); +/***/ }), + +/***/ "../../node_modules/indent-string/index.js": +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +module.exports = (string, count = 1, options) => { + options = { + indent: ' ', + includeEmptyLines: false, + ...options + }; + + if (typeof string !== 'string') { + throw new TypeError( + `Expected \`input\` to be a \`string\`, got \`${typeof string}\`` + ); + } + + if (typeof count !== 'number') { + throw new TypeError( + `Expected \`count\` to be a \`number\`, got \`${typeof count}\`` + ); + } + + if (typeof options.indent !== 'string') { + throw new TypeError( + `Expected \`options.indent\` to be a \`string\`, got \`${typeof options.indent}\`` + ); + } + + if (count === 0) { + return string; + } + + const regex = options.includeEmptyLines ? /^/gm : /^(?!\s*$)/gm; + + return string.replace(regex, options.indent.repeat(count)); +}; + + /***/ }), /***/ "../../node_modules/inflight/inflight.js": diff --git a/test/visual_regression/config.ts b/test/visual_regression/config.ts deleted file mode 100644 index 294848246e7c8..0000000000000 --- a/test/visual_regression/config.ts +++ /dev/null @@ -1,30 +0,0 @@ -/* - * 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 { FtrConfigProviderContext } from '@kbn/test'; -import { services } from './services'; - -export default async function ({ readConfigFile }: FtrConfigProviderContext) { - const functionalConfig = await readConfigFile(require.resolve('../functional/config.base.js')); - - return { - ...functionalConfig.getAll(), - - testFiles: [ - require.resolve('./tests/console_app'), - require.resolve('./tests/discover'), - require.resolve('./tests/vega'), - ], - - services, - - junit: { - reportName: 'Kibana Visual Regression Tests', - }, - }; -} diff --git a/test/visual_regression/ftr_provider_context.ts b/test/visual_regression/ftr_provider_context.ts deleted file mode 100644 index 28bedd1ca6bc3..0000000000000 --- a/test/visual_regression/ftr_provider_context.ts +++ /dev/null @@ -1,15 +0,0 @@ -/* - * 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 { GenericFtrProviderContext, GenericFtrService } from '@kbn/test'; - -import { pageObjects } from '../functional/page_objects'; -import { services } from './services'; - -export type FtrProviderContext = GenericFtrProviderContext; -export class FtrService extends GenericFtrService {} diff --git a/test/visual_regression/services/index.ts b/test/visual_regression/services/index.ts deleted file mode 100644 index 9aefe1f8de780..0000000000000 --- a/test/visual_regression/services/index.ts +++ /dev/null @@ -1,15 +0,0 @@ -/* - * 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 { services as functionalServices } from '../../functional/services'; -import { VisualTestingService } from './visual_testing'; - -export const services = { - ...functionalServices, - visualTesting: VisualTestingService, -}; diff --git a/test/visual_regression/services/visual_testing/index.ts b/test/visual_regression/services/visual_testing/index.ts deleted file mode 100644 index 156e3814d8a1d..0000000000000 --- a/test/visual_regression/services/visual_testing/index.ts +++ /dev/null @@ -1,9 +0,0 @@ -/* - * 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. - */ - -export * from './visual_testing'; diff --git a/test/visual_regression/services/visual_testing/take_percy_snapshot.js b/test/visual_regression/services/visual_testing/take_percy_snapshot.js deleted file mode 100644 index 5325765c8d06b..0000000000000 --- a/test/visual_regression/services/visual_testing/take_percy_snapshot.js +++ /dev/null @@ -1,102 +0,0 @@ -/* - * 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 { readFileSync } from 'fs'; -import { agentJsFilename } from '@percy/agent/dist/utils/sdk-utils'; - -export function takePercySnapshot(show, hide) { - if (!window.PercyAgent) { - return false; - } - - // add percy styles to hide/show specific elements - const styleElement = document.createElement('style'); - styleElement.appendChild( - document.createTextNode(` - .hideInPercy { - visibility: hidden; - - .showInPercy { - visibility: visible; - } - } - - .showInPercy { - visibility: visible; - - .hideInPercy { - visibility: hidden; - } - } - `) - ); - document.head.appendChild(styleElement); - - const add = (selectors, className) => { - for (const selector of selectors) { - for (const element of document.querySelectorAll(selector)) { - element.classList.add(className); - } - } - }; - - const remove = (selectors, className) => { - for (const selector of selectors) { - for (const element of document.querySelectorAll(selector)) { - element.classList.remove(className); - } - } - }; - - // set Percy visibility on elements - add(hide, 'hideInPercy'); - if (show.length > 0) { - // hide the body by default - add(['body'], 'hideInPercy'); - add(show, 'showInPercy'); - } - - // convert canvas elements into static images - const replacements = []; - for (const canvas of document.querySelectorAll('canvas')) { - const image = document.createElement('img'); - image.classList.value = canvas.classList.value; - image.src = canvas.toDataURL(); - image.style.cssText = window.getComputedStyle(canvas).cssText; - canvas.parentElement.replaceChild(image, canvas); - replacements.push({ canvas, image }); - } - - try { - const agent = new window.PercyAgent({ - handleAgentCommunication: false, - }); - - // cache the dom snapshot containing the images - return agent.snapshot(document, { - widths: [document.documentElement.clientWidth], - }); - } finally { - // restore replaced canvases - for (const { image, canvas } of replacements) { - image.parentElement.replaceChild(canvas, image); - } - - // restore element visibility - document.head.removeChild(styleElement); - remove(['body'], 'hideInPercy'); - remove(show, 'showInPercy'); - remove(hide, 'hideInPercy'); - } -} - -export const takePercySnapshotWithAgent = ` - ${readFileSync(agentJsFilename(), 'utf8')} - - return (${takePercySnapshot.toString()}).apply(null, arguments); -`; diff --git a/test/visual_regression/services/visual_testing/visual_testing.ts b/test/visual_regression/services/visual_testing/visual_testing.ts deleted file mode 100644 index 59c601e6a2b6e..0000000000000 --- a/test/visual_regression/services/visual_testing/visual_testing.ts +++ /dev/null @@ -1,114 +0,0 @@ -/* - * 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 { postSnapshot } from '@percy/agent/dist/utils/sdk-utils'; -import testSubjSelector from '@kbn/test-subj-selector'; -import { Test } from '@kbn/test'; -import { kibanaPackageJson as pkg } from '@kbn/utils'; -import { FtrService, FtrProviderContext } from '../../ftr_provider_context'; - -// @ts-ignore internal js that is passed to the browser as is -import { takePercySnapshot, takePercySnapshotWithAgent } from './take_percy_snapshot'; - -export const DEFAULT_OPTIONS = { - widths: [1200], -}; - -export interface SnapshotOptions { - /** - * name to append to visual test name - */ - name?: string; - /** - * test subject selectiors to __show__ in screenshot - */ - show?: string[]; - /** - * test subject selectiors to __hide__ in screenshot - */ - hide?: string[]; -} - -const statsCache = new WeakMap(); - -function getStats(test: Test) { - if (!statsCache.has(test)) { - statsCache.set(test, { - snapshotCount: 0, - }); - } - - return statsCache.get(test)!; -} - -export class VisualTestingService extends FtrService { - private readonly browser = this.ctx.getService('browser'); - private readonly log = this.ctx.getService('log'); - - private currentTest: Test | undefined; - - constructor(ctx: FtrProviderContext) { - super(ctx); - - this.ctx.getService('lifecycle').beforeEachTest.add((test) => { - this.currentTest = test; - }); - } - - public async snapshot(options: SnapshotOptions = {}) { - if (process.env.DISABLE_VISUAL_TESTING) { - this.log.warning( - 'Capturing of percy snapshots disabled, would normally capture a snapshot here!' - ); - return; - } - - this.log.debug('Capturing percy snapshot'); - - if (!this.currentTest) { - throw new Error('unable to determine current test'); - } - - const [domSnapshot, url] = await Promise.all([ - this.getSnapshot(options.show, options.hide), - this.browser.getCurrentUrl(), - ]); - const stats = getStats(this.currentTest); - stats.snapshotCount += 1; - - const { name } = options; - const success = await postSnapshot({ - name: `${this.currentTest.fullTitle()} [${name ? name : stats.snapshotCount}]`, - url, - domSnapshot, - clientInfo: `kibana-ftr:${pkg.version}`, - ...DEFAULT_OPTIONS, - }); - - if (!success) { - throw new Error('Percy snapshot failed'); - } - } - - private async getSnapshot(show: string[] = [], hide: string[] = []) { - const showSelectors = show.map(testSubjSelector); - const hideSelectors = hide.map(testSubjSelector); - const snapshot = await this.browser.execute<[string[], string[]], string | false>( - takePercySnapshot, - showSelectors, - hideSelectors - ); - return snapshot !== false - ? snapshot - : await this.browser.execute<[string[], string[]], string>( - takePercySnapshotWithAgent, - showSelectors, - hideSelectors - ); - } -} diff --git a/test/visual_regression/tests/console_app.ts b/test/visual_regression/tests/console_app.ts deleted file mode 100644 index 2c2351b76ad4f..0000000000000 --- a/test/visual_regression/tests/console_app.ts +++ /dev/null @@ -1,71 +0,0 @@ -/* - * 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 expect from '@kbn/expect'; -import { FtrProviderContext } from '../ftr_provider_context'; - -const DEFAULT_REQUEST = ` - -GET _search -{ - "query": { - "match_all": {} - } -} - -`.trim(); - -export default function ({ getService, getPageObjects }: FtrProviderContext) { - const retry = getService('retry'); - const log = getService('log'); - const visualTesting = getService('visualTesting'); - const PageObjects = getPageObjects(['common', 'console']); - - describe.skip('console app', function describeIndexTests() { - before(async () => { - log.debug('navigateTo console'); - await PageObjects.common.navigateToApp('console'); - }); - - it('should show the default request', async () => { - // collapse the help pane because we only get the VISIBLE TEXT, not the part that is scrolled - await PageObjects.console.collapseHelp(); - await retry.try(async () => { - const actualRequest = await PageObjects.console.getRequest(); - log.debug(actualRequest); - expect(actualRequest.trim()).to.eql(DEFAULT_REQUEST); - }); - - await visualTesting.snapshot(); - }); - - it('default request response should include `"timed_out" : false`', async () => { - const expectedResponseContains = '"timed_out" : false,'; - await PageObjects.console.clickPlay(); - await retry.try(async () => { - const actualResponse = await PageObjects.console.getResponse(); - log.debug(actualResponse); - expect(actualResponse).to.contain(expectedResponseContains); - }); - }); - - it('settings should allow changing the text size', async () => { - await PageObjects.console.setFontSizeSetting(20); - await retry.try(async () => { - // the settings are not applied synchronously, so we retry for a time - expect(await PageObjects.console.getRequestFontSize()).to.be('20px'); - }); - - await PageObjects.console.setFontSizeSetting(24); - await retry.try(async () => { - // the settings are not applied synchronously, so we retry for a time - expect(await PageObjects.console.getRequestFontSize()).to.be('24px'); - }); - }); - }); -} diff --git a/test/visual_regression/tests/discover/chart_visualization.ts b/test/visual_regression/tests/discover/chart_visualization.ts deleted file mode 100644 index f8390064732b9..0000000000000 --- a/test/visual_regression/tests/discover/chart_visualization.ts +++ /dev/null @@ -1,117 +0,0 @@ -/* - * 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 expect from '@kbn/expect'; - -import { FtrProviderContext } from '../../ftr_provider_context'; - -export default function ({ getService, getPageObjects }: FtrProviderContext) { - const retry = getService('retry'); - const esArchiver = getService('esArchiver'); - const browser = getService('browser'); - const kibanaServer = getService('kibanaServer'); - const PageObjects = getPageObjects(['common', 'discover', 'header', 'timePicker']); - const visualTesting = getService('visualTesting'); - const defaultSettings = { - defaultIndex: 'logstash-*', - 'discover:sampleSize': 1, - }; - - describe('discover', function describeIndexTests() { - before(async function () { - await kibanaServer.savedObjects.cleanStandardList(); - await kibanaServer.importExport.load( - 'test/functional/fixtures/kbn_archiver/discover/visual_regression' - ); - - // and load a set of makelogs data - await esArchiver.loadIfNeeded('test/functional/fixtures/es_archiver/logstash_functional'); - await kibanaServer.uiSettings.replace(defaultSettings); - await PageObjects.common.navigateToApp('discover'); - await PageObjects.timePicker.setDefaultAbsoluteRange(); - }); - - after(async function unloadMakelogs() { - await esArchiver.unload('test/functional/fixtures/es_archiver/logstash_functional'); - await kibanaServer.savedObjects.cleanStandardList(); - }); - - async function refreshDiscover() { - await browser.refresh(); - await PageObjects.header.awaitKibanaChrome(); - await PageObjects.header.awaitGlobalLoadingIndicatorHidden(); - await PageObjects.discover.waitUntilSearchingHasFinished(); - await PageObjects.discover.waitForChartLoadingComplete(1); - } - - async function takeSnapshot() { - await refreshDiscover(); - await visualTesting.snapshot({ - show: ['discoverChart'], - }); - } - - describe('query', function () { - this.tags(['skipFirefox']); - - it('should show bars in the correct time zone', async function () { - await PageObjects.header.awaitGlobalLoadingIndicatorHidden(); - await PageObjects.discover.waitUntilSearchingHasFinished(); - await takeSnapshot(); - }); - - it('should show correct data for chart interval Hour', async function () { - await PageObjects.discover.setChartInterval('Hour'); - await takeSnapshot(); - }); - - it('should show correct data for chart interval Day', async function () { - await PageObjects.discover.setChartInterval('Day'); - await takeSnapshot(); - }); - - it('should show correct data for chart interval Week', async function () { - await PageObjects.discover.setChartInterval('Week'); - await takeSnapshot(); - }); - - it('browser back button should show previous interval Day', async function () { - await browser.goBack(); - await retry.try(async function tryingForTime() { - const actualInterval = await PageObjects.discover.getChartInterval(); - expect(actualInterval).to.be('Day'); - }); - await takeSnapshot(); - }); - - it('should show correct data for chart interval Month', async function () { - await PageObjects.discover.setChartInterval('Month'); - await takeSnapshot(); - }); - - it('should show correct data for chart interval Year', async function () { - await PageObjects.discover.setChartInterval('Year'); - await takeSnapshot(); - }); - - it('should show correct data for chart interval Auto', async function () { - await PageObjects.discover.setChartInterval('Auto'); - await takeSnapshot(); - }); - }); - - describe('time zone switch', () => { - it('should show bars in the correct time zone after switching', async function () { - await kibanaServer.uiSettings.replace({ 'dateFormat:tz': 'America/Phoenix' }); - await refreshDiscover(); - await PageObjects.timePicker.setDefaultAbsoluteRange(); - await takeSnapshot(); - }); - }); - }); -} diff --git a/test/visual_regression/tests/discover/index.ts b/test/visual_regression/tests/discover/index.ts deleted file mode 100644 index 9142a430f963b..0000000000000 --- a/test/visual_regression/tests/discover/index.ts +++ /dev/null @@ -1,25 +0,0 @@ -/* - * 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 { DEFAULT_OPTIONS } from '../../services/visual_testing/visual_testing'; -import { FtrProviderContext } from '../../ftr_provider_context'; - -// Width must be the same as visual_testing or canvas image widths will get skewed -const [SCREEN_WIDTH] = DEFAULT_OPTIONS.widths || []; - -export default function ({ getService, loadTestFile }: FtrProviderContext) { - const browser = getService('browser'); - - describe('discover app', function () { - before(function () { - return browser.setWindowSize(SCREEN_WIDTH, 1000); - }); - - loadTestFile(require.resolve('./chart_visualization')); - }); -} diff --git a/test/visual_regression/tests/vega/index.ts b/test/visual_regression/tests/vega/index.ts deleted file mode 100644 index 9ab4e199439a4..0000000000000 --- a/test/visual_regression/tests/vega/index.ts +++ /dev/null @@ -1,25 +0,0 @@ -/* - * 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 { DEFAULT_OPTIONS } from '../../services/visual_testing/visual_testing'; -import { FtrProviderContext } from '../../ftr_provider_context'; - -// Width must be the same as visual_testing or canvas image widths will get skewed -const [SCREEN_WIDTH] = DEFAULT_OPTIONS.widths || []; - -export default function ({ getService, loadTestFile }: FtrProviderContext) { - const browser = getService('browser'); - - describe('vega app', function () { - before(function () { - return browser.setWindowSize(SCREEN_WIDTH, 1000); - }); - - loadTestFile(require.resolve('./vega_map_visualization')); - }); -} diff --git a/test/visual_regression/tests/vega/vega_map_visualization.ts b/test/visual_regression/tests/vega/vega_map_visualization.ts deleted file mode 100644 index d891e7f2bab6b..0000000000000 --- a/test/visual_regression/tests/vega/vega_map_visualization.ts +++ /dev/null @@ -1,39 +0,0 @@ -/* - * 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 { FtrProviderContext } from '../../ftr_provider_context'; - -export default function ({ getService, getPageObjects }: FtrProviderContext) { - const esArchiver = getService('esArchiver'); - const kibanaServer = getService('kibanaServer'); - const PageObjects = getPageObjects(['common', 'visualize', 'visChart', 'visEditor', 'vegaChart']); - const visualTesting = getService('visualTesting'); - - describe('vega chart in visualize app', () => { - before(async () => { - await esArchiver.loadIfNeeded( - 'test/functional/fixtures/es_archiver/kibana_sample_data_flights' - ); - await kibanaServer.importExport.load('test/functional/fixtures/kbn_archiver/visualize.json'); - }); - - after(async () => { - await esArchiver.unload('test/functional/fixtures/es_archiver/kibana_sample_data_flights'); - await kibanaServer.importExport.unload( - 'test/functional/fixtures/kbn_archiver/visualize.json' - ); - }); - - it('should show map with vega layer', async function () { - await PageObjects.visualize.gotoVisualizationLandingPage(); - await PageObjects.visualize.openSavedVisualization('VegaMap'); - await PageObjects.visChart.waitForVisualizationRenderingStabilized(); - await visualTesting.snapshot(); - }); - }); -} diff --git a/x-pack/test/visual_regression/config.ts b/x-pack/test/visual_regression/config.ts deleted file mode 100644 index c7f0d8203833e..0000000000000 --- a/x-pack/test/visual_regression/config.ts +++ /dev/null @@ -1,31 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { FtrConfigProviderContext } from '@kbn/test'; - -import { services } from './services'; - -export default async function ({ readConfigFile }: FtrConfigProviderContext) { - const functionalConfig = await readConfigFile(require.resolve('../functional/config.base.js')); - - return { - ...functionalConfig.getAll(), - - testFiles: [ - require.resolve('./tests/canvas'), - require.resolve('./tests/login_page'), - require.resolve('./tests/maps'), - require.resolve('./tests/infra'), - ], - - services, - - junit: { - reportName: 'X-Pack Visual Regression Tests', - }, - }; -} diff --git a/x-pack/test/visual_regression/ftr_provider_context.d.ts b/x-pack/test/visual_regression/ftr_provider_context.d.ts deleted file mode 100644 index 24f5087ef7fe2..0000000000000 --- a/x-pack/test/visual_regression/ftr_provider_context.d.ts +++ /dev/null @@ -1,13 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { GenericFtrProviderContext } from '@kbn/test'; - -import { pageObjects } from './page_objects'; -import { services } from './services'; - -export type FtrProviderContext = GenericFtrProviderContext; diff --git a/x-pack/test/visual_regression/page_objects.ts b/x-pack/test/visual_regression/page_objects.ts deleted file mode 100644 index c8b0c9050dbb9..0000000000000 --- a/x-pack/test/visual_regression/page_objects.ts +++ /dev/null @@ -1,10 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { pageObjects } from '../functional/page_objects'; - -export { pageObjects }; diff --git a/x-pack/test/visual_regression/services.ts b/x-pack/test/visual_regression/services.ts deleted file mode 100644 index 7d58bd3f35b32..0000000000000 --- a/x-pack/test/visual_regression/services.ts +++ /dev/null @@ -1,14 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { services as ossVisualRegressionServices } from '../../../test/visual_regression/services'; -import { services as functionalServices } from '../functional/services'; - -export const services = { - ...functionalServices, - visualTesting: ossVisualRegressionServices.visualTesting, -}; diff --git a/x-pack/test/visual_regression/tests/canvas/fullscreen.js b/x-pack/test/visual_regression/tests/canvas/fullscreen.js deleted file mode 100644 index 6a20db5bccdec..0000000000000 --- a/x-pack/test/visual_regression/tests/canvas/fullscreen.js +++ /dev/null @@ -1,25 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -export default function ({ getPageObjects, getService }) { - const PageObjects = getPageObjects(['common', 'canvas']); - const visualTesting = getService('visualTesting'); - - describe('fullscreen', () => { - it('workpad should display properly in fullscreen mode', async () => { - await PageObjects.common.navigateToApp('canvas', { - hash: '/workpad/workpad-1705f884-6224-47de-ba49-ca224fe6ec31/page/1', - }); - - await PageObjects.canvas.enterFullscreen(); - - await PageObjects.canvas.waitForWorkpadElements(); - - await visualTesting.snapshot(); - }); - }); -} diff --git a/x-pack/test/visual_regression/tests/canvas/index.js b/x-pack/test/visual_regression/tests/canvas/index.js deleted file mode 100644 index 20a262fef10fe..0000000000000 --- a/x-pack/test/visual_regression/tests/canvas/index.js +++ /dev/null @@ -1,30 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { DEFAULT_OPTIONS } from '../../../../../test/visual_regression/services/visual_testing/visual_testing'; - -const [SCREEN_WIDTH] = DEFAULT_OPTIONS.widths || []; - -export default function ({ loadTestFile, getService }) { - const esArchiver = getService('esArchiver'); - const browser = getService('browser'); - - describe('canvas app visual regression', function () { - before(async () => { - await esArchiver.loadIfNeeded('x-pack/test/functional/es_archives/logstash_functional'); - await esArchiver.load('x-pack/test/functional/es_archives/canvas/default'); - - await browser.setWindowSize(SCREEN_WIDTH, 1000); - }); - - after(async () => { - await esArchiver.unload('x-pack/test/functional/es_archives/canvas/default'); - }); - - loadTestFile(require.resolve('./fullscreen')); - }); -} diff --git a/x-pack/test/visual_regression/tests/infra/index.js b/x-pack/test/visual_regression/tests/infra/index.js deleted file mode 100644 index 13669c50953f9..0000000000000 --- a/x-pack/test/visual_regression/tests/infra/index.js +++ /dev/null @@ -1,19 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -export default function ({ loadTestFile, getService }) { - const browser = getService('browser'); - - describe.skip('InfraUI Visual Regression', function () { - before(async () => { - await browser.setWindowSize(1600, 1000); - }); - - loadTestFile(require.resolve('./waffle_map')); - loadTestFile(require.resolve('./saved_views')); - }); -} diff --git a/x-pack/test/visual_regression/tests/infra/saved_views.js b/x-pack/test/visual_regression/tests/infra/saved_views.js deleted file mode 100644 index a2fb3fda206da..0000000000000 --- a/x-pack/test/visual_regression/tests/infra/saved_views.js +++ /dev/null @@ -1,87 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { DATES } from '../../../functional/apps/infra/constants'; -const DATE_WITH_DATA = DATES.metricsAndLogs.hosts.withData; - -export default function ({ getPageObjects, getService }) { - const PageObjects = getPageObjects(['common', 'infraHome', 'infraMetricsExplorer']); - const visualTesting = getService('visualTesting'); - const esArchiver = getService('esArchiver'); - - describe('saved views', () => { - before(() => esArchiver.load('x-pack/test/functional/es_archives/infra/metrics_and_logs')); - after(() => esArchiver.unload('x-pack/test/functional/es_archives/infra/metrics_and_logs')); - describe('Inverntory Test save functionality', () => { - it('should have save and load controls', async () => { - await PageObjects.common.navigateToApp('infraOps'); - await PageObjects.infraHome.goToTime(DATE_WITH_DATA); - await PageObjects.infraHome.getSaveViewButton(); - await PageObjects.infraHome.getLoadViewsButton(); - await visualTesting.snapshot(); - }); - - it('should open flyout list', async () => { - await PageObjects.infraHome.openSaveViewsFlyout(); - await visualTesting.snapshot(); - await PageObjects.infraHome.closeSavedViewFlyout(); - }); - - it('should open saved view modal', async () => { - await PageObjects.infraHome.openCreateSaveViewModal(); - await visualTesting.snapshot(); - }); - - it('should be able to enter a view name', async () => { - await PageObjects.infraHome.openEnterViewNameAndSave(); - await visualTesting.snapshot(); - }); - - it('should see a saved view in list', async () => { - await PageObjects.infraHome.openSaveViewsFlyout(); - await visualTesting.snapshot(); - }); - }); - - describe('Metric Explorer Test Saved Views', () => { - before(() => esArchiver.load('x-pack/test/functional/es_archives/infra/metrics_and_logs')); - after(() => esArchiver.unload('x-pack/test/functional/es_archives/infra/metrics_and_logs')); - describe('save functionality', () => { - it('should have saved views component', async () => { - await PageObjects.common.navigateToApp('infraOps'); - await PageObjects.infraHome.goToMetricExplorer(); - await PageObjects.infraSavedViews.getSavedViewsButton(); - await PageObjects.infraSavedViews.ensureViewIsLoaded('Default view'); - await visualTesting.snapshot(); - }); - - it('should open popover', async () => { - await PageObjects.infraSavedViews.clickSavedViewsButton(); - await visualTesting.snapshot(); - await PageObjects.infraSavedViews.closeSavedViewsPopover(); - }); - - it('should create new saved view and load it', async () => { - await PageObjects.infraSavedViews.clickSavedViewsButton(); - await PageObjects.infraSavedViews.clickSaveNewViewButton(); - await PageObjects.infraSavedViews.getCreateSavedViewModal(); - await PageObjects.infraSavedViews.createNewSavedView('view1'); - await PageObjects.infraSavedViews.ensureViewIsLoaded('view1'); - await visualTesting.snapshot(); - }); - - it('should new views should be listed in the load views list', async () => { - await PageObjects.infraSavedViews.clickSavedViewsButton(); - await PageObjects.infraSavedViews.clickLoadViewButton(); - await PageObjects.infraSavedViews.ensureViewIsLoadable('view1'); - await visualTesting.snapshot(); - await PageObjects.infraSavedViews.closeSavedViewsLoadModal(); - }); - }); - }); - }); -} diff --git a/x-pack/test/visual_regression/tests/infra/waffle_map.js b/x-pack/test/visual_regression/tests/infra/waffle_map.js deleted file mode 100644 index 70aaf89a059eb..0000000000000 --- a/x-pack/test/visual_regression/tests/infra/waffle_map.js +++ /dev/null @@ -1,27 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { DATES } from '../../../functional/apps/infra/constants'; -const DATE_WITH_DATA = DATES.metricsAndLogs.hosts.withData; - -export default function ({ getPageObjects, getService }) { - const PageObjects = getPageObjects(['common', 'infraHome']); - const visualTesting = getService('visualTesting'); - const esArchiver = getService('esArchiver'); - - describe('waffle map', () => { - before(() => esArchiver.load('x-pack/test/functional/es_archives/infra/metrics_and_logs')); - after(() => esArchiver.unload('x-pack/test/functional/es_archives/infra/metrics_and_logs')); - - it('should just work', async () => { - await PageObjects.common.navigateToApp('infraOps'); - await PageObjects.infraHome.goToTime(DATE_WITH_DATA); - await PageObjects.infraHome.getWaffleMap(); - await visualTesting.snapshot(); - }); - }); -} diff --git a/x-pack/test/visual_regression/tests/login_page.ts b/x-pack/test/visual_regression/tests/login_page.ts deleted file mode 100644 index 34e1132134744..0000000000000 --- a/x-pack/test/visual_regression/tests/login_page.ts +++ /dev/null @@ -1,58 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { FtrProviderContext } from '../ftr_provider_context'; - -export default function ({ getService, getPageObjects }: FtrProviderContext) { - const esArchiver = getService('esArchiver'); - const visualTesting = getService('visualTesting'); - const testSubjects = getService('testSubjects'); - const retry = getService('retry'); - const PageObjects = getPageObjects(['common', 'security']); - - describe.skip('Security', () => { - describe('Login Page', () => { - before(async () => { - await esArchiver.load('x-pack/test/functional/es_archives/empty_kibana'); - await PageObjects.security.forceLogout(); - }); - - after(async () => { - await esArchiver.unload('x-pack/test/functional/es_archives/empty_kibana'); - }); - - afterEach(async () => { - // NOTE: Logout needs to happen before anything else to avoid flaky behavior - await PageObjects.security.forceLogout(); - }); - - it('renders login page', async () => { - await PageObjects.common.navigateToApp('login'); - - await retry.waitFor( - 'login page visible', - async () => await testSubjects.exists('loginSubmit') - ); - - await visualTesting.snapshot(); - }); - - it('renders failed login', async () => { - await PageObjects.security.loginPage.login('wrong-user', 'wrong-password', { - expectSuccess: false, - }); - - await retry.waitFor( - 'login error visible', - async () => await testSubjects.exists('loginErrorMessage') - ); - - await visualTesting.snapshot(); - }); - }); - }); -} diff --git a/x-pack/test/visual_regression/tests/maps/index.js b/x-pack/test/visual_regression/tests/maps/index.js deleted file mode 100644 index 9d53d70ad2abc..0000000000000 --- a/x-pack/test/visual_regression/tests/maps/index.js +++ /dev/null @@ -1,61 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -export default function ({ loadTestFile, getService }) { - const kibanaServer = getService('kibanaServer'); - const esArchiver = getService('esArchiver'); - const browser = getService('browser'); - const log = getService('log'); - const supertest = getService('supertest'); - - describe('maps app visual regression', function () { - before(async () => { - await esArchiver.loadIfNeeded('x-pack/test/functional/es_archives/logstash_functional'); - await kibanaServer.importExport.load( - 'x-pack/test/functional/fixtures/kbn_archiver/maps.json' - ); - // Functional tests verify behavior when referenced index pattern saved objects can not be found. - // However, saved object import fails when reference saved objects can not be found. - // To prevent import errors, index pattern saved object references exist during import - // but are then deleted afterwards to enable testing of missing reference index pattern saved objects. - - log.info('Delete index pattern'); - log.debug('id: ' + 'idThatDoesNotExitForESGeoGridSource'); - log.debug('id: ' + 'idThatDoesNotExitForESSearchSource'); - log.debug('id: ' + 'idThatDoesNotExitForESJoinSource'); - await supertest - .delete('/api/index_patterns/index_pattern/' + 'idThatDoesNotExitForESGeoGridSource') - .set('kbn-xsrf', 'true') - .expect(200); - - await supertest - .delete('/api/index_patterns/index_pattern/' + 'idThatDoesNotExitForESSearchSource') - .set('kbn-xsrf', 'true') - .expect(200); - - await supertest - .delete('/api/index_patterns/index_pattern/' + 'idThatDoesNotExitForESJoinSource') - .set('kbn-xsrf', 'true') - .expect(200); - - await esArchiver.load('x-pack/test/functional/es_archives/maps/data'); - await kibanaServer.uiSettings.replace({ - defaultIndex: 'c698b940-e149-11e8-a35a-370a8516603a', - }); - await browser.setWindowSize(1600, 1000); - }); - - after(async () => { - await esArchiver.unload('x-pack/test/functional/es_archives/maps/data'); - await kibanaServer.importExport.unload( - 'x-pack/test/functional/fixtures/kbn_archiver/maps.json' - ); - }); - - loadTestFile(require.resolve('./vector_styling')); - }); -} diff --git a/x-pack/test/visual_regression/tests/maps/vector_styling.js b/x-pack/test/visual_regression/tests/maps/vector_styling.js deleted file mode 100644 index 092ae603117d9..0000000000000 --- a/x-pack/test/visual_regression/tests/maps/vector_styling.js +++ /dev/null @@ -1,49 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -export default function ({ getPageObjects, getService }) { - const PageObjects = getPageObjects(['maps']); - const visualTesting = getService('visualTesting'); - - describe('vector styling', () => { - describe('symbolize as icon', () => { - before(async () => { - await PageObjects.maps.loadSavedMap('vector styling icon demo'); - await PageObjects.maps.enterFullScreen(); - await PageObjects.maps.closeLegend(); - }); - - it('should symbolize points as icons with expected color, size, and orientation', async () => { - await visualTesting.snapshot(); - }); - }); - - describe('dynamic coloring', () => { - before(async () => { - await PageObjects.maps.loadSavedMap('join and dynamic coloring demo'); - await PageObjects.maps.enterFullScreen(); - await PageObjects.maps.closeLegend(); - }); - - it('should symbolize fill color with custom steps from join value and border color with dynamic color ramp from prop value', async () => { - await visualTesting.snapshot(); - }); - }); - - describe('dynamic line coloring', () => { - before(async () => { - await PageObjects.maps.loadSavedMap('pew pew demo'); - await PageObjects.maps.enterFullScreen(); - await PageObjects.maps.closeLegend(); - }); - - it('should symbolize pew pew lines', async () => { - await visualTesting.snapshot(); - }); - }); - }); -} diff --git a/yarn.lock b/yarn.lock index f8f09a1dab087..a7f74c0b215b0 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4087,90 +4087,6 @@ dependencies: mkdirp "^1.0.4" -"@oclif/color@^0.0.0": - version "0.0.0" - resolved "https://registry.yarnpkg.com/@oclif/color/-/color-0.0.0.tgz#54939bbd16d1387511bf1a48ccda1a417248e6a9" - integrity sha512-KKd3W7eNwfNF061tr663oUNdt8EMnfuyf5Xv55SGWA1a0rjhWqS/32P7OeB7CbXcJUBdfVrPyR//1afaW12AWw== - dependencies: - ansi-styles "^3.2.1" - supports-color "^5.4.0" - tslib "^1" - -"@oclif/command@1.5.19", "@oclif/command@^1.5.13", "@oclif/command@^1.5.3": - version "1.5.19" - resolved "https://registry.yarnpkg.com/@oclif/command/-/command-1.5.19.tgz#13f472450eb83bd6c6871a164c03eadb5e1a07ed" - integrity sha512-6+iaCMh/JXJaB2QWikqvGE9//wLEVYYwZd5sud8aLoLKog1Q75naZh2vlGVtg5Mq/NqpqGQvdIjJb3Bm+64AUQ== - dependencies: - "@oclif/config" "^1" - "@oclif/errors" "^1.2.2" - "@oclif/parser" "^3.8.3" - "@oclif/plugin-help" "^2" - debug "^4.1.1" - semver "^5.6.0" - -"@oclif/config@^1": - version "1.13.0" - resolved "https://registry.yarnpkg.com/@oclif/config/-/config-1.13.0.tgz#fc2bd82a9cb30a73faf7d2aa5ae937c719492bd1" - integrity sha512-ttb4l85q7SBx+WlUJY4A9eXLgv4i7hGDNGaXnY9fDKrYD7PBMwNOQ3Ssn2YT2yARAjyOxVE/5LfcwhQGq4kzqg== - dependencies: - debug "^4.1.1" - tslib "^1.9.3" - -"@oclif/errors@^1.2.2": - version "1.2.2" - resolved "https://registry.yarnpkg.com/@oclif/errors/-/errors-1.2.2.tgz#9d8f269b15f13d70aa93316fed7bebc24688edc2" - integrity sha512-Eq8BFuJUQcbAPVofDxwdE0bL14inIiwt5EaKRVY9ZDIG11jwdXZqiQEECJx0VfnLyUZdYfRd/znDI/MytdJoKg== - dependencies: - clean-stack "^1.3.0" - fs-extra "^7.0.0" - indent-string "^3.2.0" - strip-ansi "^5.0.0" - wrap-ansi "^4.0.0" - -"@oclif/linewrap@^1.0.0": - version "1.0.0" - resolved "https://registry.yarnpkg.com/@oclif/linewrap/-/linewrap-1.0.0.tgz#aedcb64b479d4db7be24196384897b5000901d91" - integrity sha512-Ups2dShK52xXa8w6iBWLgcjPJWjais6KPJQq3gQ/88AY6BXoTX+MIGFPrWQO1KLMiQfoTpcLnUwloN4brrVUHw== - -"@oclif/parser@^3.8.3": - version "3.8.4" - resolved "https://registry.yarnpkg.com/@oclif/parser/-/parser-3.8.4.tgz#1a90fc770a42792e574fb896325618aebbe8c9e4" - integrity sha512-cyP1at3l42kQHZtqDS3KfTeyMvxITGwXwH1qk9ktBYvqgMp5h4vHT+cOD74ld3RqJUOZY/+Zi9lb4Tbza3BtuA== - dependencies: - "@oclif/linewrap" "^1.0.0" - chalk "^2.4.2" - tslib "^1.9.3" - -"@oclif/plugin-help@^2": - version "2.2.0" - resolved "https://registry.yarnpkg.com/@oclif/plugin-help/-/plugin-help-2.2.0.tgz#8dfc1c80deae47a205fbc70b018747ba93f31cc3" - integrity sha512-56iIgE7NQfwy/ZrWrvrEfJGb5rrMUt409yoQGw4feiU101UudA1btN1pbUbcKBr7vY9KFeqZZcftXEGxOp7zBg== - dependencies: - "@oclif/command" "^1.5.13" - chalk "^2.4.1" - indent-string "^3.2.0" - lodash.template "^4.4.0" - string-width "^3.0.0" - strip-ansi "^5.0.0" - widest-line "^2.0.1" - wrap-ansi "^4.0.0" - -"@oclif/plugin-not-found@^1.2": - version "1.2.2" - resolved "https://registry.yarnpkg.com/@oclif/plugin-not-found/-/plugin-not-found-1.2.2.tgz#3e601f6e4264d7a0268cd03c152d90aa9c0cec6d" - integrity sha512-SPlmiJFmTFltQT/owdzQwKgq6eq5AEKVwVK31JqbzK48bRWvEL1Ye60cgztXyZ4bpPn2Fl+KeL3FWFQX41qJuA== - dependencies: - "@oclif/color" "^0.0.0" - "@oclif/command" "^1.5.3" - cli-ux "^4.9.0" - fast-levenshtein "^2.0.6" - lodash "^4.17.11" - -"@oclif/screen@^1.0.3": - version "1.0.4" - resolved "https://registry.yarnpkg.com/@oclif/screen/-/screen-1.0.4.tgz#b740f68609dfae8aa71c3a6cab15d816407ba493" - integrity sha512-60CHpq+eqnTxLZQ4PGHYNwUX572hgpMHGPtTWMjdTMsAvlm69lZV/4ly6O3sAYkomo4NggGcomrDpBe34rxUqw== - "@octokit/app@^2.2.2": version "2.2.2" resolved "https://registry.yarnpkg.com/@octokit/app/-/app-2.2.2.tgz#a1b8248f64159eeccbe4000d888fdae4163c4ad8" @@ -4529,34 +4445,6 @@ resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.4.0.tgz#facf2c67d6063b9918d5a5e3fdf25f3a30d547b6" integrity sha512-Hzl8soGpmyzja9w3kiFFcYJ7n5HNETpplY6cb67KR4QPlxp4FTTresO06qXHgHDhyIInmbLJXuwARjjpsKYGuQ== -"@percy/agent@^0.28.6": - version "0.28.6" - resolved "https://registry.yarnpkg.com/@percy/agent/-/agent-0.28.6.tgz#b220fab6ddcf63ae4e6c343108ba6955a772ce1c" - integrity sha512-SDAyBiUmfQMVTayjvEjQ0IJIA7Y3AoeyWn0jmUxNOMRRIJWo4lQJghfhFCgzCkhXDCm67NMN2nAQAsvXrlIdkQ== - dependencies: - "@oclif/command" "1.5.19" - "@oclif/config" "^1" - "@oclif/plugin-help" "^2" - "@oclif/plugin-not-found" "^1.2" - axios "^0.21.1" - body-parser "^1.18.3" - colors "^1.3.2" - cors "^2.8.4" - cosmiconfig "^5.2.1" - cross-spawn "^7.0.2" - deepmerge "^4.0.0" - express "^4.16.3" - follow-redirects "1.12.1" - generic-pool "^3.7.1" - globby "^10.0.1" - image-size "^0.8.2" - js-yaml "^3.13.1" - percy-client "^3.2.0" - puppeteer "^5.3.1" - retry-axios "^1.0.1" - which "^2.0.1" - winston "^3.0.0" - "@pmmmwh/react-refresh-webpack-plugin@^0.5.1": version "0.5.5" resolved "https://registry.yarnpkg.com/@pmmmwh/react-refresh-webpack-plugin/-/react-refresh-webpack-plugin-0.5.5.tgz#e77aac783bd079f548daa0a7f080ab5b5a9741ca" @@ -8790,11 +8678,6 @@ agent-base@4: dependencies: es6-promisify "^5.0.0" -agent-base@5: - version "5.1.1" - resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-5.1.1.tgz#e8fb3f242959db44d63be665db7a8e739537a32c" - integrity sha512-TMeqbNl2fMW0nMjTEPOwe3J/PRFP4vqeoNuQMG0HlMrtm5QxKqdvAkZ1pRBQ/ulIyDD5Yq0nJ7YbdD8ey0TO3g== - agent-base@6, agent-base@^6.0.2: version "6.0.2" resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" @@ -8965,7 +8848,7 @@ ansi-colors@^3.0.0: resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-3.2.4.tgz#e3a3da4bfbae6c86a9c285625de124a234026fbf" integrity sha512-hHUXGagefjN2iRrID63xckIvotOXOojhQKWIPUZ4mNUZ9nLZW+7FMNoE1lOkEhNWYsx/7ysGIuJYCiMAA9FnrA== -ansi-escapes@^3.0.0, ansi-escapes@^3.1.0: +ansi-escapes@^3.0.0: version "3.2.0" resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-3.2.0.tgz#8780b98ff9dbf5638152d1f1fe5c1d7b4442976b" integrity sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ== @@ -9065,11 +8948,6 @@ ansi-wrap@0.1.0, ansi-wrap@^0.1.0: resolved "https://registry.yarnpkg.com/ansi-wrap/-/ansi-wrap-0.1.0.tgz#a82250ddb0015e9a27ca82e82ea603bbfa45efaf" integrity sha1-qCJQ3bABXponyoLoLqYDu/pF768= -ansicolors@~0.3.2: - version "0.3.2" - resolved "https://registry.yarnpkg.com/ansicolors/-/ansicolors-0.3.2.tgz#665597de86a9ffe3aa9bfbe6cae5c6ea426b4979" - integrity sha1-ZlWX3oap/+Oqm/vmyuXG6kJrSXk= - antlr4ts-cli@^0.5.0-alpha.3: version "0.5.0-alpha.3" resolved "https://registry.yarnpkg.com/antlr4ts-cli/-/antlr4ts-cli-0.5.0-alpha.3.tgz#1f581b2a3c840d3921a2f3b1e739e48c7e7c18cd" @@ -10163,12 +10041,7 @@ blob-util@^2.0.2: resolved "https://registry.yarnpkg.com/blob-util/-/blob-util-2.0.2.tgz#3b4e3c281111bb7f11128518006cdc60b403a1eb" integrity sha512-T7JQa+zsXXEa6/8ZhHcQEW1UFfVM49Ts65uBkFL6fz2QmrElqmbajIDJvuA0tEhRe5eIjpV9ZF+0RfZR9voJFQ== -bluebird-retry@^0.11.0: - version "0.11.0" - resolved "https://registry.yarnpkg.com/bluebird-retry/-/bluebird-retry-0.11.0.tgz#1289ab22cbbc3a02587baad35595351dd0c1c047" - integrity sha1-EomrIsu8OgJYe6rTVZU1HdDBwEc= - -bluebird@3.7.2, bluebird@^3.3.5, bluebird@^3.5.0, bluebird@^3.5.1, bluebird@^3.5.5, bluebird@^3.7.1, bluebird@^3.7.2: +bluebird@3.7.2, bluebird@^3.3.5, bluebird@^3.5.5, bluebird@^3.7.1, bluebird@^3.7.2: version "3.7.2" resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-3.7.2.tgz#9f229c15be272454ffa973ace0dbee79a1b0c36f" integrity sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg== @@ -10183,7 +10056,7 @@ bn.js@^4.0.0, bn.js@^4.1.0, bn.js@^4.1.1, bn.js@^4.11.9: resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.11.9.tgz#26d556829458f9d1e81fc48952493d0ba3507828" integrity sha512-E6QoYqCKZfgatHTdHzs1RRKP7ip4vvm+EyRUeE2RF0NblwVvb0p6jSVeNTOFxPn26QXN2o6SMfNxKp6kU8zQaw== -body-parser@1.19.0, body-parser@^1.18.3: +body-parser@1.19.0: version "1.19.0" resolved "https://registry.yarnpkg.com/body-parser/-/body-parser-1.19.0.tgz#96b2709e57c9c4e09a6fd66a8fd979844f69f08a" integrity sha512-dhEPs72UPbDnAQJ9ZKMNTP6ptJaionhP5cBb541nXPlW60Jepo9RV/a4fX4XWW9CuFNK22krhrj1+rgzifNCsw== @@ -10898,14 +10771,6 @@ capture-exit@^2.0.0: dependencies: rsvp "^4.8.4" -cardinal@^2.1.1: - version "2.1.1" - resolved "https://registry.yarnpkg.com/cardinal/-/cardinal-2.1.1.tgz#7cc1055d822d212954d07b085dea251cc7bc5505" - integrity sha1-fMEFXYItISlU0HsIXeolHMe8VQU= - dependencies: - ansicolors "~0.3.2" - redeyed "~2.1.0" - case-sensitive-paths-webpack-plugin@^2.3.0: version "2.3.0" resolved "https://registry.yarnpkg.com/case-sensitive-paths-webpack-plugin/-/case-sensitive-paths-webpack-plugin-2.3.0.tgz#23ac613cc9a856e4f88ff8bb73bbb5e989825cf7" @@ -11152,11 +11017,6 @@ clean-css@^4.2.3: dependencies: source-map "~0.6.0" -clean-stack@^1.3.0: - version "1.3.0" - resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-1.3.0.tgz#9e821501ae979986c46b1d66d2d432db2fd4ae31" - integrity sha1-noIVAa6XmYbEax1m0tQy2y/UrjE= - clean-stack@^2.0.0: version "2.2.0" resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b" @@ -11219,33 +11079,6 @@ cli-truncate@^2.1.0: slice-ansi "^3.0.0" string-width "^4.2.0" -cli-ux@^4.9.0: - version "4.9.3" - resolved "https://registry.yarnpkg.com/cli-ux/-/cli-ux-4.9.3.tgz#4c3e070c1ea23eef010bbdb041192e0661be84ce" - integrity sha512-/1owvF0SZ5Gn54cgrikJ0QskgTzeg30HGjkmjFoaHDJzAqFpuX1DBpFR8aLvsE1J5s9MgeYRENQK4BFwOag5VA== - dependencies: - "@oclif/errors" "^1.2.2" - "@oclif/linewrap" "^1.0.0" - "@oclif/screen" "^1.0.3" - ansi-escapes "^3.1.0" - ansi-styles "^3.2.1" - cardinal "^2.1.1" - chalk "^2.4.1" - clean-stack "^2.0.0" - extract-stack "^1.0.0" - fs-extra "^7.0.0" - hyperlinker "^1.0.0" - indent-string "^3.2.0" - is-wsl "^1.1.0" - lodash "^4.17.11" - password-prompt "^1.0.7" - semver "^5.6.0" - strip-ansi "^5.0.0" - supports-color "^5.5.0" - supports-hyperlinks "^1.0.1" - treeify "^1.1.0" - tslib "^1.9.3" - cli-width@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/cli-width/-/cli-width-3.0.0.tgz#a2f48437a2caa9a22436e794bf071ec9e61cedf6" @@ -11484,7 +11317,7 @@ colorette@^1.2.0, colorette@^1.2.1, colorette@^1.2.2: resolved "https://registry.yarnpkg.com/colorette/-/colorette-1.2.2.tgz#cbcc79d5e99caea2dbf10eb3a26fd8b3e6acfa94" integrity sha512-MKGMzyfeuutC/ZJ1cba9NqcNpfeqMUcYmyF1ZFY6/Cn7CNSAKx6a+s48sqLqyAiZuaP2TcqMhoo+dlwFnVxT9w== -colors@1.4.0, colors@^1.3.2: +colors@1.4.0: version "1.4.0" resolved "https://registry.yarnpkg.com/colors/-/colors-1.4.0.tgz#c50491479d4c1bdaed2c9ced32cf7c7dc2360f78" integrity sha512-a+UqTh4kgZg/SlGvfbzDHpgRu7AAQOmmqRHJnxhRZICKFUT91brVhNNt58CMWU9PsBbv3PDCZUHbVxuDiH2mtA== @@ -11877,14 +11710,6 @@ core-util-is@1.0.2, core-util-is@^1.0.2, core-util-is@~1.0.0: resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.2.tgz#b5fd54220aa2bc5ab57aab7140c940754503c1a7" integrity sha1-tf1UIgqivFq1eqtxQMlAdUUDwac= -cors@^2.8.4: - version "2.8.5" - resolved "https://registry.yarnpkg.com/cors/-/cors-2.8.5.tgz#eac11da51592dd86b9f06f6e7ac293b3df875d29" - integrity sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g== - dependencies: - object-assign "^4" - vary "^1" - cosmiconfig@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/cosmiconfig/-/cosmiconfig-4.0.0.tgz#760391549580bbd2df1e562bc177b13c290972dc" @@ -11895,7 +11720,7 @@ cosmiconfig@^4.0.0: parse-json "^4.0.0" require-from-string "^2.0.1" -cosmiconfig@^5.0.0, cosmiconfig@^5.2.1: +cosmiconfig@^5.0.0: version "5.2.1" resolved "https://registry.yarnpkg.com/cosmiconfig/-/cosmiconfig-5.2.1.tgz#040f726809c591e77a17c0a3626ca45b4f168b1a" integrity sha512-H65gsXo1SKjf8zmrJ67eJk8aIRKV5ff2D4uKZIBZShbhGSpEmsQOPW/SKMKYhSTrqR7ufy6RP69rPogdaPh/kA== @@ -13119,7 +12944,7 @@ deep-object-diff@^1.1.0: resolved "https://registry.yarnpkg.com/deep-object-diff/-/deep-object-diff-1.1.0.tgz#d6fabf476c2ed1751fc94d5ca693d2ed8c18bc5a" integrity sha512-b+QLs5vHgS+IoSNcUE4n9HP2NwcHj7aqnJWsjPtuG75Rh5TOaGt0OjAYInh77d5T16V5cRDC+Pw/6ZZZiETBGw== -deepmerge@3.2.0, deepmerge@^2.1.1, deepmerge@^4.0.0, deepmerge@^4.2.2: +deepmerge@3.2.0, deepmerge@^2.1.1, deepmerge@^4.2.2: version "4.2.2" resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.2.2.tgz#44d2ea3679b8f4d4ffba33f03d865fc1e7bf4955" integrity sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg== @@ -13400,11 +13225,6 @@ detective@^5.0.2, detective@^5.2.0: defined "^1.0.0" minimist "^1.1.1" -devtools-protocol@0.0.818844: - version "0.0.818844" - resolved "https://registry.yarnpkg.com/devtools-protocol/-/devtools-protocol-0.0.818844.tgz#d1947278ec85b53e4c8ca598f607a28fa785ba9e" - integrity sha512-AD1hi7iVJ8OD0aMLQU5VK0XH9LDlA1+BcPIgrAxPfaibx2DbWucuyOhc4oyQCbnvDDO68nN6/LcKfqTP343Jjg== - devtools-protocol@0.0.901419: version "0.0.901419" resolved "https://registry.yarnpkg.com/devtools-protocol/-/devtools-protocol-0.0.901419.tgz#79b5459c48fe7e1c5563c02bd72f8fec3e0cebcd" @@ -13640,7 +13460,7 @@ domhandler@^3.0.0: dependencies: domelementtype "^2.0.1" -domhandler@^4.0.0, domhandler@^4.0, domhandler@^4.2.0, domhandler@^4.2.2: +domhandler@^4.0, domhandler@^4.0.0, domhandler@^4.2.0, domhandler@^4.2.2: version "4.3.0" resolved "https://registry.yarnpkg.com/domhandler/-/domhandler-4.3.0.tgz#16c658c626cf966967e306f966b431f77d4a5626" integrity sha512-fC0aXNQXqKSFTr2wDNZDhsEYjCiYsDWl3D01kwt25hm1YIPyDGHvvi3rw+PLqHAl/m71MaiF7d5zvBr0p5UB2g== @@ -13704,7 +13524,7 @@ dotenv@^16.0.1: resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-16.0.1.tgz#8f8f9d94876c35dac989876a5d3a82a267fdce1d" integrity sha512-1K6hR6wtk2FviQ4kEiSjFiH5rpzEVi8WW0x96aztHVMhEspNpc4DVOUTEHtEva5VThQ8IaBX1Pe4gSzpVVUsKQ== -dotenv@^8.0.0, dotenv@^8.1.0: +dotenv@^8.0.0: version "8.2.0" resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-8.2.0.tgz#97e619259ada750eea3e4ea3e26bceea5424b16a" integrity sha512-8sJ78ElpbDJBHNeBzUbUVLsqKdccaa/BXF1uPTw3GrvQTBgrQrtObr2mUrE38vzYd8cEv+m/JBfDLioYcfXoaw== @@ -14257,11 +14077,6 @@ es6-map@^0.1.5: es6-symbol "~3.1.1" event-emitter "~0.3.5" -es6-promise-pool@^2.5.0: - version "2.5.0" - resolved "https://registry.yarnpkg.com/es6-promise-pool/-/es6-promise-pool-2.5.0.tgz#147c612b36b47f105027f9d2bf54a598a99d9ccb" - integrity sha1-FHxhKza0fxBQJ/nSv1SlmKmdnMs= - es6-promise@^4.0.3, es6-promise@^4.2.8: version "4.2.8" resolved "https://registry.yarnpkg.com/es6-promise/-/es6-promise-4.2.8.tgz#4eb21594c972bc40553d276e510539143db53e0a" @@ -14672,7 +14487,7 @@ espree@^7.3.0, espree@^7.3.1: acorn-jsx "^5.3.1" eslint-visitor-keys "^1.3.0" -esprima@^4.0.0, esprima@^4.0.1, esprima@~4.0.0: +esprima@^4.0.0, esprima@^4.0.1: version "4.0.1" resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.1.tgz#13b04cdb3e6c5d19df91ab6987a8695619b0aa71" integrity sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A== @@ -14955,7 +14770,7 @@ expose-loader@^0.7.5: resolved "https://registry.yarnpkg.com/expose-loader/-/expose-loader-0.7.5.tgz#e29ea2d9aeeed3254a3faa1b35f502db9f9c3f6f" integrity sha512-iPowgKUZkTPX5PznYsmifVj9Bob0w2wTHVkt/eYNPSzyebkUgIedmskf/kcfEIWpiWjg3JRjnW+a17XypySMuw== -express@^4.16.3, express@^4.17.1: +express@^4.17.1: version "4.17.1" resolved "https://registry.yarnpkg.com/express/-/express-4.17.1.tgz#4491fc38605cf51f8629d39c2b5d026f98a4c134" integrity sha512-mHJ9O79RqluphRrcw2X/GTh3k9tVv8YcoyY4Kkh4WDMUYKRZUq0h1o0w2rrrxBqM7VoeUVqgb27xlEMXTnYt4g== @@ -15034,12 +14849,7 @@ extglob@^2.0.4: snapdragon "^0.8.1" to-regex "^3.0.1" -extract-stack@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/extract-stack/-/extract-stack-1.0.0.tgz#b97acaf9441eea2332529624b732fc5a1c8165fa" - integrity sha1-uXrK+UQe6iMyUpYktzL8WhyBZfo= - -extract-zip@2.0.1, extract-zip@^2.0.0, extract-zip@^2.0.1: +extract-zip@2.0.1, extract-zip@^2.0.1: version "2.0.1" resolved "https://registry.yarnpkg.com/extract-zip/-/extract-zip-2.0.1.tgz#663dca56fe46df890d5f131ef4a06d22bb8ba13a" integrity sha512-GDhU9ntwuKyGXdZBUgTIe+vXnWj0fppUEtMDL0+idd5Sta8TGpHssn/eusA9mrPr9qNDym6SxAYZjNvCn/9RBg== @@ -15538,11 +15348,6 @@ folktale@2.3.2: resolved "https://registry.yarnpkg.com/folktale/-/folktale-2.3.2.tgz#38231b039e5ef36989920cbf805bf6b227bf4fd4" integrity sha512-+8GbtQBwEqutP0v3uajDDoN64K2ehmHd0cjlghhxh0WpcfPzAIjPA03e1VvHlxL02FVGR0A6lwXsNQKn3H1RNQ== -follow-redirects@1.12.1: - version "1.12.1" - resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.12.1.tgz#de54a6205311b93d60398ebc01cf7015682312b6" - integrity sha512-tmRv0AVuR7ZyouUHLeNSiO6pqulF7dYa3s19c6t+wz9LD69/uSzdMxJ2S91nTI9U3rt/IldxpzMOFejp6f0hjg== - follow-redirects@^1.0.0, follow-redirects@^1.14.0, follow-redirects@^1.14.9: version "1.15.0" resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.0.tgz#06441868281c86d0dda4ad8bdaead2d02dca89d4" @@ -15577,11 +15382,6 @@ foreach@^2.0.5: resolved "https://registry.yarnpkg.com/foreach/-/foreach-2.0.5.tgz#0bee005018aeb260d0a3af3ae658dd0136ec1b99" integrity sha1-C+4AUBiusmDQo6865ljdATbsG5k= -foreachasync@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/foreachasync/-/foreachasync-3.0.0.tgz#5502987dc8714be3392097f32e0071c9dee07cf6" - integrity sha1-VQKYfchxS+M5IJfzLgBxyd7gfPY= - foreground-child@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/foreground-child/-/foreground-child-2.0.0.tgz#71b32800c9f15aa8f2f83f4a6bd9bff35d861a53" @@ -15747,7 +15547,7 @@ fs-extra@^10.0.0: jsonfile "^6.0.1" universalify "^2.0.0" -fs-extra@^7.0.0, fs-extra@^7.0.1: +fs-extra@^7.0.1: version "7.0.1" resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== @@ -15917,11 +15717,6 @@ geckodriver@^3.0.1: https-proxy-agent "5.0.0" tar "6.1.11" -generic-pool@^3.7.1: - version "3.7.1" - resolved "https://registry.yarnpkg.com/generic-pool/-/generic-pool-3.7.1.tgz#36fe5bb83e7e0e032e5d32cd05dc00f5ff119aa8" - integrity sha512-ug6DAZoNgWm6q5KhPFA+hzXfBLFQu5sTXxPpv44DmE0A2g+CiHoq9LTVdkXpZMkYVMoGw83F6W+WT0h0MFMK/w== - gensync@^1.0.0-beta.1: version "1.0.0-beta.1" resolved "https://registry.yarnpkg.com/gensync/-/gensync-1.0.0-beta.1.tgz#58f4361ff987e5ff6e1e7a210827aa371eaac269" @@ -16663,11 +16458,6 @@ has-bigints@^1.0.1: resolved "https://registry.yarnpkg.com/has-bigints/-/has-bigints-1.0.1.tgz#64fe6acb020673e3b78db035a5af69aa9d07b113" integrity sha512-LSBS2LjbNBTf6287JEbEzvJgftkF5qFkmCo9hDRpAzKhUOlJ+hx8dd4USs00SgsUNwc4617J9ki5YtEClM2ffA== -has-flag@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-2.0.0.tgz#e8207af1cc7b30d446cc70b734b5e8be18f88d51" - integrity sha1-6CB68cx7MNRGzHC3NLXovhj4jVE= - has-flag@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" @@ -17285,14 +17075,6 @@ https-proxy-agent@5.0.0, https-proxy-agent@^5.0.0: agent-base "6" debug "4" -https-proxy-agent@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-4.0.0.tgz#702b71fb5520a132a66de1f67541d9e62154d82b" - integrity sha512-zoDhWrkR3of1l9QAL8/scJZyLu8j/gBkcwcaQOZh7Gyh/+uJQzGVETdgT30akuwkpL8HTRfssqI3BZuV18teDg== - dependencies: - agent-base "5" - debug "4" - human-signals@^1.1.1: version "1.1.1" resolved "https://registry.yarnpkg.com/human-signals/-/human-signals-1.1.1.tgz#c5b1cd14f50aeae09ab6c59fe63ba3395fe4dfa3" @@ -17305,11 +17087,6 @@ humanize-ms@^1.2.1: dependencies: ms "^2.0.0" -hyperlinker@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/hyperlinker/-/hyperlinker-1.0.0.tgz#23dc9e38a206b208ee49bc2d6c8ef47027df0c0e" - integrity sha512-Ty8UblRWFEcfSuIaajM34LdPXIhbs1ajEX/BBPv24J+enSVaEVY63xQ6lTO9VRYS5LAoghIG0IDJ+p+IPzKUQQ== - hyphenate-style-name@^1.0.2: version "1.0.3" resolved "https://registry.yarnpkg.com/hyphenate-style-name/-/hyphenate-style-name-1.0.3.tgz#097bb7fa0b8f1a9cf0bd5c734cf95899981a9b48" @@ -17383,13 +17160,6 @@ image-q@^1.1.1: resolved "https://registry.yarnpkg.com/image-q/-/image-q-1.1.1.tgz#fc84099664460b90ca862d9300b6bfbbbfbf8056" integrity sha1-/IQJlmRGC5DKhi2TALa/u7+/gFY= -image-size@^0.8.2: - version "0.8.3" - resolved "https://registry.yarnpkg.com/image-size/-/image-size-0.8.3.tgz#f0b568857e034f29baffd37013587f2c0cad8b46" - integrity sha512-SMtq1AJ+aqHB45c3FsB4ERK0UCiA2d3H1uq8s+8T0Pf8A3W4teyBQyaFaktH6xvZqh+npwlKU7i4fJo0r7TYTg== - dependencies: - queue "6.0.1" - immediate@~3.0.5: version "3.0.6" resolved "https://registry.yarnpkg.com/immediate/-/immediate-3.0.6.tgz#9db1dbd0faf8de6fbe0f5dd5e56bb606280de69b" @@ -17461,7 +17231,7 @@ imurmurhash@^0.1.4: resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea" integrity sha1-khi5srkoojixPcT7a21XbyMUU+o= -indent-string@^3.0.0, indent-string@^3.2.0: +indent-string@^3.0.0: version "3.2.0" resolved "https://registry.yarnpkg.com/indent-string/-/indent-string-3.2.0.tgz#4a5fd6d27cc332f37e5419a504dbb837105c9289" integrity sha1-Sl/W0nzDMvN+VBmlBNu4NxBckok= @@ -19537,11 +19307,6 @@ jsprim@^2.0.2: json-schema "0.4.0" verror "1.10.0" -jssha@^2.1.0: - version "2.3.1" - resolved "https://registry.yarnpkg.com/jssha/-/jssha-2.3.1.tgz#147b2125369035ca4b2f7d210dc539f009b3de9a" - integrity sha1-FHshJTaQNcpLL30hDcU58Amz3po= - jsts@^1.6.2: version "1.6.2" resolved "https://registry.yarnpkg.com/jsts/-/jsts-1.6.2.tgz#c0efc885edae06ae84f78cbf2a0110ba929c5925" @@ -20027,11 +19792,6 @@ lodash-es@^4.17.11, lodash-es@^4.17.21: resolved "https://registry.yarnpkg.com/lodash-es/-/lodash-es-4.17.21.tgz#43e626c46e6591b7750beb2b50117390c609e3ee" integrity sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw== -lodash._reinterpolate@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz#0ccf2d89166af03b3663c796538b75ac6e114d9d" - integrity sha1-DM8tiRZq8Ds2Y8eWU4t1rG4RTZ0= - lodash.camelcase@^4.3.0: version "4.3.0" resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6" @@ -20157,21 +19917,6 @@ lodash.sortby@^4.7.0: resolved "https://registry.yarnpkg.com/lodash.sortby/-/lodash.sortby-4.7.0.tgz#edd14c824e2cc9c1e0b0a1b42bb5210516a42438" integrity sha1-7dFMgk4sycHgsKG0K7UhBRakJDg= -lodash.template@^4.4.0: - version "4.5.0" - resolved "https://registry.yarnpkg.com/lodash.template/-/lodash.template-4.5.0.tgz#f976195cf3f347d0d5f52483569fe8031ccce8ab" - integrity sha512-84vYFxIkmidUiFxidA/KjjH9pAycqW+h980j7Fuz5qxRtO9pgB7MDFTdys1N7A5mcucRiDyEq4fusljItR1T/A== - dependencies: - lodash._reinterpolate "^3.0.0" - lodash.templatesettings "^4.0.0" - -lodash.templatesettings@^4.0.0: - version "4.2.0" - resolved "https://registry.yarnpkg.com/lodash.templatesettings/-/lodash.templatesettings-4.2.0.tgz#e481310f049d3cf6d47e912ad09313b154f0fb33" - integrity sha512-stgLz+i3Aa9mZgnjr/O+v9ruKZsPsndy7qPZOchbqk2cnTU1ZaldKK+v7m54WoKIyxiuMZTKT2H81F8BeAc3ZQ== - dependencies: - lodash._reinterpolate "^3.0.0" - lodash.toarray@^4.4.0: version "4.4.0" resolved "https://registry.yarnpkg.com/lodash.toarray/-/lodash.toarray-4.4.0.tgz#24c4bfcd6b2fba38bfd0594db1179d8e9b656561" @@ -21962,7 +21707,7 @@ oauth-sign@~0.9.0: resolved "https://registry.yarnpkg.com/oauth-sign/-/oauth-sign-0.9.0.tgz#47a7b016baa68b5fa0ecf3dee08a85c679ac6455" integrity sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ== -object-assign@4.X, object-assign@^4, object-assign@^4.0.1, object-assign@^4.1.0, object-assign@^4.1.1: +object-assign@4.X, object-assign@^4.0.1, object-assign@^4.1.0, object-assign@^4.1.1: version "4.1.1" resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" integrity sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM= @@ -22729,14 +22474,6 @@ pascalcase@^0.1.1: resolved "https://registry.yarnpkg.com/pascalcase/-/pascalcase-0.1.1.tgz#b363e55e8006ca6fe21784d2db22bd15d7917f14" integrity sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ= -password-prompt@^1.0.7: - version "1.1.2" - resolved "https://registry.yarnpkg.com/password-prompt/-/password-prompt-1.1.2.tgz#85b2f93896c5bd9e9f2d6ff0627fa5af3dc00923" - integrity sha512-bpuBhROdrhuN3E7G/koAju0WjVw9/uQOG5Co5mokNj0MiOSBVZS1JTwM4zl55hu0WFmIEFvO9cU9sJQiBIYeIA== - dependencies: - ansi-escapes "^3.1.0" - cross-spawn "^6.0.5" - path-browserify@0.0.1, path-browserify@~0.0.0: version "0.0.1" resolved "https://registry.yarnpkg.com/path-browserify/-/path-browserify-0.0.1.tgz#e6c4ddd7ed3aa27c68a20cc4e50e1a4ee83bbc4a" @@ -22895,21 +22632,6 @@ pend@~1.2.0: resolved "https://registry.yarnpkg.com/pend/-/pend-1.2.0.tgz#7a57eb550a6783f9115331fcf4663d5c8e007a50" integrity sha1-elfrVQpng/kRUzH89GY9XI4AelA= -percy-client@^3.2.0: - version "3.7.0" - resolved "https://registry.yarnpkg.com/percy-client/-/percy-client-3.7.0.tgz#780e7d780c7f646e59ffb6ee9d3d16e8237851ff" - integrity sha512-5levWR/nfVuSDL9YPN9Sn1M41I2/FmC/FndhD84s6W+mrVC4mB0cc9cT9F58hLuh7/133I/YvyI9Vc6NN41+2g== - dependencies: - bluebird "^3.5.1" - bluebird-retry "^0.11.0" - dotenv "^8.1.0" - es6-promise-pool "^2.5.0" - jssha "^2.1.0" - regenerator-runtime "^0.13.1" - request "^2.87.0" - request-promise "^4.2.2" - walk "^2.3.14" - performance-now@^0.2.0: version "0.2.0" resolved "https://registry.yarnpkg.com/performance-now/-/performance-now-0.2.0.tgz#33ef30c5c77d4ea21c5a53869d91b56d8f2555e5" @@ -23810,7 +23532,7 @@ progress@^1.1.8: resolved "https://registry.yarnpkg.com/progress/-/progress-1.1.8.tgz#e260c78f6161cdd9b0e56cc3e0a85de17c7a57be" integrity sha1-4mDHj2Fhzdmw5WzD4Khd4Xx6V74= -progress@^2.0.0, progress@^2.0.1, progress@^2.0.3: +progress@^2.0.0, progress@^2.0.3: version "2.0.3" resolved "https://registry.yarnpkg.com/progress/-/progress-2.0.3.tgz#7e8cf8d8f5b8f239c1bc68beb4eb78567d572ef8" integrity sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA== @@ -23993,7 +23715,7 @@ proxy-from-env@1.0.0: resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.0.0.tgz#33c50398f70ea7eb96d21f7b817630a55791c7ee" integrity sha1-M8UDmPcOp+uW0h97gXYwpVeRx+4= -proxy-from-env@1.1.0, proxy-from-env@^1.0.0, proxy-from-env@^1.1.0: +proxy-from-env@1.1.0, proxy-from-env@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.1.0.tgz#e102f16ca355424865755d2c9e8ea4f24d58c3e2" integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== @@ -24099,24 +23821,6 @@ puppeteer@^10.2.0: unbzip2-stream "1.3.3" ws "7.4.6" -puppeteer@^5.3.1: - version "5.5.0" - resolved "https://registry.yarnpkg.com/puppeteer/-/puppeteer-5.5.0.tgz#331a7edd212ca06b4a556156435f58cbae08af00" - integrity sha512-OM8ZvTXAhfgFA7wBIIGlPQzvyEETzDjeRa4mZRCRHxYL+GNH5WAuYUQdja3rpWZvkX/JKqmuVgbsxDNsDFjMEg== - dependencies: - debug "^4.1.0" - devtools-protocol "0.0.818844" - extract-zip "^2.0.0" - https-proxy-agent "^4.0.0" - node-fetch "^2.6.1" - pkg-dir "^4.2.0" - progress "^2.0.1" - proxy-from-env "^1.0.0" - rimraf "^3.0.2" - tar-fs "^2.0.0" - unbzip2-stream "^1.3.3" - ws "^7.2.3" - q@^1.1.2, q@^1.5.1: version "1.5.1" resolved "https://registry.yarnpkg.com/q/-/q-1.5.1.tgz#7e32f75b41381291d04611f1bf14109ac00651d7" @@ -24175,13 +23879,6 @@ querystringify@^2.1.1: resolved "https://registry.yarnpkg.com/querystringify/-/querystringify-2.1.1.tgz#60e5a5fd64a7f8bfa4d2ab2ed6fdf4c85bad154e" integrity sha512-w7fLxIRCRT7U8Qu53jQnJyPkYZIaR4n5151KMfcJlO/A9397Wxb1amJvROTK6TOnp7PfoAmg/qXiNHI+08jRfA== -queue@6.0.1: - version "6.0.1" - resolved "https://registry.yarnpkg.com/queue/-/queue-6.0.1.tgz#abd5a5b0376912f070a25729e0b6a7d565683791" - integrity sha512-AJBQabRCCNr9ANq8v77RJEv73DPbn55cdTb+Giq4X0AVnNVZvMHlYp7XlQiN+1npCZj1DuSmaA2hYVUUDgxFDg== - dependencies: - inherits "~2.0.3" - quick-format-unescaped@^4.0.3: version "4.0.3" resolved "https://registry.yarnpkg.com/quick-format-unescaped/-/quick-format-unescaped-4.0.3.tgz#6d6b66b8207aa2b35eef12be1421bb24c428f652" @@ -25209,13 +24906,6 @@ redent@^3.0.0: indent-string "^4.0.0" strip-indent "^3.0.0" -redeyed@~2.1.0: - version "2.1.1" - resolved "https://registry.yarnpkg.com/redeyed/-/redeyed-2.1.1.tgz#8984b5815d99cb220469c99eeeffe38913e6cc0b" - integrity sha1-iYS1gV2ZyyIEacme7v/jiRPmzAs= - dependencies: - esprima "~4.0.0" - reduce-reducers@*, reduce-reducers@^1.0.4: version "1.0.4" resolved "https://registry.yarnpkg.com/reduce-reducers/-/reduce-reducers-1.0.4.tgz#fb77e751a9eb0201760ac5a605ca8c9c2d0537f8" @@ -25332,7 +25022,7 @@ regenerator-runtime@^0.11.0: resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz#be05ad7f9bf7d22e056f9726cee5017fbf19e2e9" integrity sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg== -regenerator-runtime@^0.13.1, regenerator-runtime@^0.13.3, regenerator-runtime@^0.13.4, regenerator-runtime@^0.13.7: +regenerator-runtime@^0.13.3, regenerator-runtime@^0.13.4, regenerator-runtime@^0.13.7: version "0.13.7" resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.13.7.tgz#cac2dacc8a1ea675feaabaeb8ae833898ae46f55" integrity sha512-a54FxoJDIr27pgf7IgeQGxmqUNYrcV338lf/6gH456HZ/PhX+5BcwHXG9ajESmwe6WRO0tAzRUrRmNONWgkrew== @@ -25688,13 +25378,6 @@ request-progress@^3.0.0: dependencies: throttleit "^1.0.0" -request-promise-core@1.1.2: - version "1.1.2" - resolved "https://registry.yarnpkg.com/request-promise-core/-/request-promise-core-1.1.2.tgz#339f6aababcafdb31c799ff158700336301d3346" - integrity sha512-UHYyq1MO8GsefGEt7EprS8UrXsm1TxEvFUX1IMTuSLU2Rh7fTIdFtl8xD7JiEYiWU2dl+NYAjCTksTehQUxPag== - dependencies: - lodash "^4.17.11" - request-promise-core@1.1.4: version "1.1.4" resolved "https://registry.yarnpkg.com/request-promise-core/-/request-promise-core-1.1.4.tgz#3eedd4223208d419867b78ce815167d10593a22f" @@ -25711,17 +25394,7 @@ request-promise-native@^1.0.5, request-promise-native@^1.0.8: stealthy-require "^1.1.1" tough-cookie "^2.3.3" -request-promise@^4.2.2: - version "4.2.4" - resolved "https://registry.yarnpkg.com/request-promise/-/request-promise-4.2.4.tgz#1c5ed0d71441e38ad58c7ce4ea4ea5b06d54b310" - integrity sha512-8wgMrvE546PzbR5WbYxUQogUnUDfM0S7QIFZMID+J73vdFARkFy+HElj4T+MWYhpXwlLp0EQ8Zoj8xUA0he4Vg== - dependencies: - bluebird "^3.5.0" - request-promise-core "1.1.2" - stealthy-require "^1.1.1" - tough-cookie "^2.3.3" - -request@^2.44.0, request@^2.87.0, request@^2.88.0, request@^2.88.2: +request@^2.44.0, request@^2.88.0, request@^2.88.2: version "2.88.2" resolved "https://registry.yarnpkg.com/request/-/request-2.88.2.tgz#d73c918731cb5a87da047e207234146f664d12b3" integrity sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw== @@ -25938,11 +25611,6 @@ ret@~0.1.10: resolved "https://registry.yarnpkg.com/ret/-/ret-0.1.15.tgz#b8a4825d5bdb1fc3f6f53c2bc33f81388681c7bc" integrity sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg== -retry-axios@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/retry-axios/-/retry-axios-1.0.1.tgz#c1e465126416d8aee7a0a2d4be28401cc0135029" - integrity sha512-aVnENElFbdmbsv1WbTi610Ukdper88yUPz4Y3eg/DUyHV7vNaLrj9orB6FOjvmFoXL9wZvbMAsOD87BmcyBVOw== - retry@0.12.0, retry@^0.12.0: version "0.12.0" resolved "https://registry.yarnpkg.com/retry/-/retry-0.12.0.tgz#1b42a6266a21f07421d1b0b54b7dc167b01c013b" @@ -27804,7 +27472,7 @@ supports-color@^2.0.0: resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-2.0.0.tgz#535d045ce6b6363fa40117084629995e9df324c7" integrity sha1-U10EXOa2Nj+kARcIRimZXp3zJMc= -supports-color@^5.0.0, supports-color@^5.3.0, supports-color@^5.4.0, supports-color@^5.5.0: +supports-color@^5.3.0, supports-color@^5.5.0: version "5.5.0" resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== @@ -27825,14 +27493,6 @@ supports-color@^7.0.0, supports-color@^7.1.0: dependencies: has-flag "^4.0.0" -supports-hyperlinks@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/supports-hyperlinks/-/supports-hyperlinks-1.0.1.tgz#71daedf36cc1060ac5100c351bb3da48c29c0ef7" - integrity sha512-HHi5kVSefKaJkGYXbDuKbUGRVxqnWGn3J2e39CYcNJEfWciGq2zYtOhXLTlvrOZW1QU7VX67w7fMmWafHX9Pfw== - dependencies: - has-flag "^2.0.0" - supports-color "^5.0.0" - supports-hyperlinks@^2.0.0: version "2.1.0" resolved "https://registry.yarnpkg.com/supports-hyperlinks/-/supports-hyperlinks-2.1.0.tgz#f663df252af5f37c5d49bbd7eeefa9e0b9e59e47" @@ -28604,7 +28264,7 @@ tslib@2.3.1, tslib@^2.0.3, tslib@^2.1.0, tslib@^2.3.1, tslib@~2.3.1: resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.3.1.tgz#e8a335add5ceae51aa261d32a490158ef042ef01" integrity sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw== -tslib@^1, tslib@^1.0.0, tslib@^1.10.0, tslib@^1.8.1, tslib@^1.9.0, tslib@^1.9.3: +tslib@^1.0.0, tslib@^1.10.0, tslib@^1.8.1, tslib@^1.9.0, tslib@^1.9.3: version "1.13.0" resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.13.0.tgz#c881e13cc7015894ed914862d276436fa9a47043" integrity sha512-i/6DQjL8Xf3be4K/E6Wgpekn5Qasl1usyw++dAA35Ue5orEn65VIxOA+YvNNl9HV3qv70T7CNwjODHZrLwvd1Q== @@ -28804,14 +28464,6 @@ unbzip2-stream@1.3.3: buffer "^5.2.1" through "^2.3.8" -unbzip2-stream@^1.3.3: - version "1.4.3" - resolved "https://registry.yarnpkg.com/unbzip2-stream/-/unbzip2-stream-1.4.3.tgz#b0da04c4371311df771cdc215e87f2130991ace7" - integrity sha512-mlExGW4w71ebDJviH16lQLtZS32VKqsSfk80GCfUlwT/4/hNRFsoscrF/c++9xinkMzECL1uL9DDwXqFWkruPg== - dependencies: - buffer "^5.2.1" - through "^2.3.8" - unc-path-regex@^0.1.2: version "0.1.2" resolved "https://registry.yarnpkg.com/unc-path-regex/-/unc-path-regex-0.1.2.tgz#e73dd3d7b0d7c5ed86fbac6b0ae7d8c6a69d50fa" @@ -29522,7 +29174,7 @@ variable-diff@1.1.0: chalk "^1.1.1" object-assign "^4.0.1" -vary@^1, vary@~1.1.2: +vary@~1.1.2: version "1.1.2" resolved "https://registry.yarnpkg.com/vary/-/vary-1.1.2.tgz#2299f02c6ded30d4a5961b0b9f74524a18f634fc" integrity sha1-IpnwLG3tMNSllhsLn3RSShj2NPw= @@ -30048,13 +29700,6 @@ w3c-xmlserializer@^2.0.0: dependencies: xml-name-validator "^3.0.0" -walk@^2.3.14: - version "2.3.14" - resolved "https://registry.yarnpkg.com/walk/-/walk-2.3.14.tgz#60ec8631cfd23276ae1e7363ce11d626452e1ef3" - integrity sha512-5skcWAUmySj6hkBdH6B6+3ddMjVQYH5Qy9QGbPmN8kVmLteXk+yVXg+yfk1nbX30EYakahLrr8iPcCxJQSCBeg== - dependencies: - foreachasync "^3.0.0" - walker@^1.0.7, walker@~1.0.5: version "1.0.7" resolved "https://registry.yarnpkg.com/walker/-/walker-1.0.7.tgz#2f7f9b8fd10d677262b18a884e28d19618e028fb" @@ -30456,13 +30101,6 @@ wide-align@^1.1.0, wide-align@^1.1.2, wide-align@^1.1.5: dependencies: string-width "^1.0.2 || 2 || 3 || 4" -widest-line@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/widest-line/-/widest-line-2.0.1.tgz#7438764730ec7ef4381ce4df82fb98a53142a3fc" - integrity sha512-Ba5m9/Fa4Xt9eb2ELXt77JxVDV8w7qQrH0zS/TWSJdLyAwQjWoOzpzj5lwVftDz6n/EOu3tNACS84v509qwnJA== - dependencies: - string-width "^2.1.1" - widest-line@^3.1.0: version "3.1.0" resolved "https://registry.yarnpkg.com/widest-line/-/widest-line-3.1.0.tgz#8292333bbf66cb45ff0de1603b136b7ae1496eca" @@ -30491,7 +30129,7 @@ winston-transport@^4.4.2, winston-transport@^4.5.0: readable-stream "^3.6.0" triple-beam "^1.3.0" -winston@^3.0.0, winston@^3.3.3: +winston@^3.3.3: version "3.5.1" resolved "https://registry.yarnpkg.com/winston/-/winston-3.5.1.tgz#b25cc899d015836dbf8c583dec8c4c4483a0da2e" integrity sha512-tbRtVy+vsSSCLcZq/8nXZaOie/S2tPXPFt4be/Q3vI/WtYwm7rrwidxVw2GRa38FIXcJ1kUM6MOZ9Jmnk3F3UA== @@ -30573,15 +30211,6 @@ wrap-ansi@^3.0.1: string-width "^2.1.1" strip-ansi "^4.0.0" -wrap-ansi@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-4.0.0.tgz#b3570d7c70156159a2d42be5cc942e957f7b1131" - integrity sha512-uMTsj9rDb0/7kk1PbcbCcwvHUxp60fGDB/NNXpVa0Q+ic/e7y5+BwTxKfQ33VYgDppSwi/FBzpetYzo8s6tfbg== - dependencies: - ansi-styles "^3.2.0" - string-width "^2.1.1" - strip-ansi "^4.0.0" - wrap-ansi@^5.1.0: version "5.1.0" resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-5.1.0.tgz#1fd1f67235d5b6d0fee781056001bfb694c03b09" From 44d29d26892b6598c63118e731e3689471ab2735 Mon Sep 17 00:00:00 2001 From: Alexey Antonov Date: Thu, 14 Jul 2022 20:46:09 +0300 Subject: [PATCH 038/111] [Visualizations] Fix 'Data View' value is not populated when re-creating a visualization (#136305) * [UnifiedSearch] Fix 'Data View' value is not populated when re-creating a visualization * version -> isPersisted() Co-authored-by: Joe Reuter --- src/plugins/visualizations/public/visualize_app/utils/utils.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/plugins/visualizations/public/visualize_app/utils/utils.ts b/src/plugins/visualizations/public/visualize_app/utils/utils.ts index 70ffae134aacf..f122b301af1f8 100644 --- a/src/plugins/visualizations/public/visualize_app/utils/utils.ts +++ b/src/plugins/visualizations/public/visualize_app/utils/utils.ts @@ -102,5 +102,5 @@ export function getVizEditorOriginatingAppUrl(history: History) { } export function isFallbackDataView(dataView?: DataView): dataView is DataView { - return Boolean(dataView && !Object.keys(dataView.getOriginalSavedObjectBody() ?? {}).length); + return Boolean(dataView && !dataView.isPersisted()); } From 8ed5aaf92d171ac60944d3f7bfe00fc10f441edd Mon Sep 17 00:00:00 2001 From: Jonathan Budzenski Date: Thu, 14 Jul 2022 12:57:22 -0500 Subject: [PATCH 039/111] skip flaky suite. #136272 --- .../policy_response/policy_response_wrapper.test.tsx | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx b/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx index dbd604d4c2c54..a4ef569c0a0c5 100644 --- a/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx @@ -23,7 +23,8 @@ import { useGetEndpointDetails } from '../../hooks'; jest.mock('../../hooks/endpoint/use_get_endpoint_policy_response'); jest.mock('../../hooks/endpoint/use_get_endpoint_details'); -describe('when on the policy response', () => { +// FLAKY: https://github.com/elastic/kibana/issues/136272 +describe.skip('when on the policy response', () => { const docGenerator = new EndpointDocGenerator(); const createPolicyResponse = ( overallStatus: HostPolicyResponseActionStatus = HostPolicyResponseActionStatus.success, From 7231d7c5a18cb4e88f0acbcc38d90c668c4d10b4 Mon Sep 17 00:00:00 2001 From: Spencer Date: Thu, 14 Jul 2022 13:14:59 -0500 Subject: [PATCH 040/111] [ftr] use correct script path when running outside of repo root (#136397) --- packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts b/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts index 76346f3618a51..54e01a6b7916b 100644 --- a/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts +++ b/packages/kbn-test/src/functional_tests/lib/run_kibana_server.ts @@ -68,7 +68,7 @@ export async function runKibanaServer({ }; const prefixArgs = devMode - ? [Path.relative(process.cwd(), Path.resolve(REPO_ROOT, 'scripts/kibana'))] + ? [Path.relative(procRunnerOpts.cwd, Path.resolve(REPO_ROOT, 'scripts/kibana'))] : []; const buildArgs: string[] = config.get('kbnTestServer.buildArgs') || []; From 93f6f897950fbb14e0c625bdb23b67fc094fb618 Mon Sep 17 00:00:00 2001 From: Lisa Cawley Date: Thu, 14 Jul 2022 11:45:39 -0700 Subject: [PATCH 041/111] Add open API specification for get case API (#136315) --- docs/api/cases/cases-api-get-case.asciidoc | 84 +- .../plugins/cases/docs/openapi/bundled.json | 1834 ++++++++++++----- .../plugins/cases/docs/openapi/bundled.yaml | 581 +++++- .../examples/get_case_response.yaml | 44 + ...t_status.yaml => get_status_response.yaml} | 0 .../cases/docs/openapi/entrypoint.yaml | 8 +- .../openapi/paths/api@cases@{caseid}.yaml | 35 + .../paths/s@{spaceid}@api@cases@{caseid}.yaml | 36 + 8 files changed, 2001 insertions(+), 621 deletions(-) create mode 100644 x-pack/plugins/cases/docs/openapi/components/examples/get_case_response.yaml rename x-pack/plugins/cases/docs/openapi/components/examples/{get_status.yaml => get_status_response.yaml} (100%) create mode 100644 x-pack/plugins/cases/docs/openapi/paths/api@cases@{caseid}.yaml create mode 100644 x-pack/plugins/cases/docs/openapi/paths/s@{spaceid}@api@cases@{caseid}.yaml diff --git a/docs/api/cases/cases-api-get-case.asciidoc b/docs/api/cases/cases-api-get-case.asciidoc index 70cc7f5bab60c..d7bc316a7346d 100644 --- a/docs/api/cases/cases-api-get-case.asciidoc +++ b/docs/api/cases/cases-api-get-case.asciidoc @@ -4,7 +4,7 @@ Get case ++++ -Returns a specified case. +Returns information about a case. === {api-request-title} @@ -17,7 +17,7 @@ Returns a specified case. You must have `read` privileges for the *Cases* feature in the *Management*, *{observability}*, or *Security* section of the <>, depending on the -`owner` of the cases you're seeking. +`owner` of the case you're seeking. === {api-path-parms-title} @@ -42,11 +42,11 @@ default space is used. === {api-examples-title} -Returns case ID `a18b38a0-71b0-11ea-a0b2-c51ea50a58e2` without comments: +Returns case ID `31cdada0-02c1-11ed-85f2-4f7c222ca2fa`: [source,sh] -------------------------------------------------- -GET api/cases/a18b38a0-71b0-11ea-a0b2-c51ea50a58e2 +GET api/cases/31cdada0-02c1-11ed-85f2-4f7c222ca2fa -------------------------------------------------- // KIBANA @@ -55,49 +55,39 @@ The API returns a JSON object with the retrieved case. For example: [source,json] -------------------------------------------------- { - "id": "a18b38a0-71b0-11ea-a0b2-c51ea50a58e2", - "version": "Wzk4LDFd", - "comments": [], - "totalComment": 0, - "totalAlerts": 0, - "closed_at": null, - "closed_by": null, - "created_at": "2020-03-29T11:30:02.658Z", - "created_by": { - "email": "ahunley@imf.usa.gov", - "full_name": "Alan Hunley", - "username": "ahunley" - }, - "external_service": null, - "updated_at": "2020-03-29T12:01:50.244Z", - "updated_by": { - "full_name": "Classified", - "email": "classified@hms.oo.gov.uk", - "username": "M" - }, - "description": "James Bond clicked on a highly suspicious email banner advertising cheap holidays for underpaid civil servants. Operation bubblegum is active. Repeat - operation bubblegum is now active!", - "title": "This case will self-destruct in 5 seconds", - "status": "open", - "connector": { - "id": "131d4448-abe0-4789-939d-8ef60680b498", - "name": "My connector", - "type": ".jira", - "fields": { - "issueType": "10006", - "priority": "High", - } - }, - "settings": { - "syncAlerts": true - }, - "owner": "securitySolution", - "severity": "low", - "duration": null, <1> - "tags": [ - "phishing", - "social engineering", - "bubblegum" - ] + "id":"31cdada0-02c1-11ed-85f2-4f7c222ca2fa", + "version":"WzM2LDFd", + "comments":[{ + "id":"2134c1d0-02c2-11ed-85f2-4f7c222ca2fa", + "version":"WzM3LDFd", + "type":"user", + "owner":"cases", + "comment":"A new comment", + "created_at":"2022-07-13T15:40:32.335Z", + "created_by":{"email":null,"full_name":null,"username":"elastic"}, + "pushed_at":null, + "pushed_by":null, + "updated_at":null, + "updated_by":null + }], + "totalComment":1, + "totalAlerts":0, + "title":"Case title 1", + "tags":["tag 1"], + "settings":{"syncAlerts":true}, + "owner":"cases", + "description":"A case description", + "duration":null, <1> + "severity":"low", + "closed_at":null, + "closed_by":null, + "created_at":"2022-07-13T15:33:50.604Z", + "created_by":{"username":"elastic","email":null,"full_name":null}, + "status":"open", + "updated_at":"2022-07-13T15:40:32.335Z", + "updated_by":{"full_name":null,"email":null,"username":"elastic"}, + "connector":{"id":"none","name":"none","type":".none","fields":null}, + "external_service":null } -------------------------------------------------- <1> Duration represents the elapsed time from the creation of the case to its diff --git a/x-pack/plugins/cases/docs/openapi/bundled.json b/x-pack/plugins/cases/docs/openapi/bundled.json index ef89279600760..9482e4489d875 100644 --- a/x-pack/plugins/cases/docs/openapi/bundled.json +++ b/x-pack/plugins/cases/docs/openapi/bundled.json @@ -2699,44 +2699,30 @@ } ] }, - "/api/cases/{caseId}/comments": { - "post": { - "summary": "Adds a comment or alert to a case in the default space.", - "operationId": "addCaseCommentDefaultSpace", - "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're creating.\n", + "/api/cases/{caseId}": { + "get": { + "summary": "Retrieves information about a case in the default space.", + "operationId": "getCaseDefaultSpace", + "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're seeking.\n", "tags": [ "cases", "kibana" ], "parameters": [ { - "$ref": "#/components/parameters/kbn_xsrf" + "$ref": "#/components/parameters/case_id" }, { - "$ref": "#/components/parameters/case_id" - } - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "oneOf": [ - { - "$ref": "#/components/schemas/add_alert_comment_request_properties" - }, - { - "$ref": "#/components/schemas/add_user_comment_request_properties" - } - ] - }, - "examples": { - "createCaseCommentRequest": { - "$ref": "#/components/examples/add_comment_request" - } - } + "in": "query", + "name": "includeComments", + "description": "Determines whether case comments are returned.", + "deprecated": true, + "schema": { + "type": "boolean", + "default": true } } - }, + ], "responses": { "200": { "description": "Indicates a successful call.", @@ -3013,8 +2999,8 @@ } }, "examples": { - "createCaseCommentResponse": { - "$ref": "#/components/examples/add_comment_response" + "getCaseResponse": { + "$ref": "#/components/examples/get_case_response" } } } @@ -3027,37 +3013,17 @@ } ] }, - "delete": { - "summary": "Deletes all comments and alerts from a case in the default space.", - "operationId": "deleteCaseCommentsDefaultSpace", - "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're deleting.\n", - "tags": [ - "cases", - "kibana" - ], - "parameters": [ - { - "$ref": "#/components/parameters/kbn_xsrf" - }, - { - "$ref": "#/components/parameters/case_id" - } - ], - "responses": { - "204": { - "description": "Indicates a successful call." - } - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "patch": { - "summary": "Updates a comment or alert in a case in the default space.", - "operationId": "updateCaseCommentDefaultSpace", - "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're updating. NOTE: You cannot change the comment type or the owner of a comment.\n", + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "/api/cases/{caseId}/comments": { + "post": { + "summary": "Adds a comment or alert to a case in the default space.", + "operationId": "addCaseCommentDefaultSpace", + "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're creating.\n", "tags": [ "cases", "kibana" @@ -3076,16 +3042,16 @@ "schema": { "oneOf": [ { - "$ref": "#/components/schemas/update_alert_comment_request_properties" + "$ref": "#/components/schemas/add_alert_comment_request_properties" }, { - "$ref": "#/components/schemas/update_user_comment_request_properties" + "$ref": "#/components/schemas/add_user_comment_request_properties" } ] }, "examples": { - "updateCaseCommentRequest": { - "$ref": "#/components/examples/update_comment_request" + "createCaseCommentRequest": { + "$ref": "#/components/examples/add_comment_request" } } } @@ -3367,8 +3333,8 @@ } }, "examples": { - "updateCaseCommentResponse": { - "$ref": "#/components/examples/update_comment_response" + "createCaseCommentResponse": { + "$ref": "#/components/examples/add_comment_response" } } } @@ -3381,59 +3347,9 @@ } ] }, - "get": { - "summary": "Retrieves all the comments from a case in the default space.", - "operationId": "getAllCaseCommentsDefaultSpace", - "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases with the comments you're seeking.\n", - "tags": [ - "cases", - "kibana" - ], - "deprecated": true, - "parameters": [ - { - "$ref": "#/components/parameters/case_id" - } - ], - "responses": { - "200": { - "description": "Indicates a successful call.", - "content": { - "application/json; charset=utf-8": { - "schema": { - "type": "array", - "items": { - "anyOf": [ - { - "$ref": "#/components/schemas/alert_comment_response_properties" - }, - { - "$ref": "#/components/schemas/user_comment_response_properties" - } - ] - } - } - }, - "examples": {} - } - } - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "/api/cases/{caseId}/comments/{commentId}": { "delete": { - "summary": "Deletes a comment or alert from a case in the default space.", - "operationId": "deleteCaseCommentDefaultSpace", + "summary": "Deletes all comments and alerts from a case in the default space.", + "operationId": "deleteCaseCommentsDefaultSpace", "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're deleting.\n", "tags": [ "cases", @@ -3445,9 +3361,6 @@ }, { "$ref": "#/components/parameters/case_id" - }, - { - "$ref": "#/components/parameters/comment_id" } ], "responses": { @@ -3461,239 +3374,56 @@ } ] }, - "get": { - "summary": "Retrieves a comment from a case in the default space.", - "operationId": "getCaseCommentDefaultSpace", - "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases with the comments you're seeking.\n", + "patch": { + "summary": "Updates a comment or alert in a case in the default space.", + "operationId": "updateCaseCommentDefaultSpace", + "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're updating. NOTE: You cannot change the comment type or the owner of a comment.\n", "tags": [ "cases", "kibana" ], "parameters": [ { - "$ref": "#/components/parameters/case_id" + "$ref": "#/components/parameters/kbn_xsrf" }, { - "$ref": "#/components/parameters/comment_id" + "$ref": "#/components/parameters/case_id" } ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/update_alert_comment_request_properties" + }, + { + "$ref": "#/components/schemas/update_user_comment_request_properties" + } + ] + }, + "examples": { + "updateCaseCommentRequest": { + "$ref": "#/components/examples/update_comment_request" + } + } + } + } + }, "responses": { "200": { "description": "Indicates a successful call.", "content": { "application/json; charset=utf-8": { "schema": { - "oneOf": [ - { - "$ref": "#/components/schemas/alert_comment_response_properties" - }, - { - "$ref": "#/components/schemas/user_comment_response_properties" - } - ] - }, - "examples": { - "getCaseCommentResponse": { - "$ref": "#/components/examples/get_comment_response" - } - } - } - } - } - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "/s/{spaceId}/api/cases": { - "post": { - "summary": "Creates a case.", - "operationId": "createCase", - "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're creating.\n", - "tags": [ - "cases", - "kibana" - ], - "parameters": [ - { - "$ref": "#/components/parameters/kbn_xsrf" - }, - { - "$ref": "#/components/parameters/space_id" - } - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "object", - "properties": { - "connector": { - "description": "An object that contains the connector configuration.", - "type": "object", - "properties": { - "fields": { - "description": "An object containing the connector fields. To create a case without a connector, specify null. If you want to omit any individual field, specify null as its value.", - "nullable": true, - "type": "object", - "properties": { - "caseId": { - "description": "The case identifier for Swimlane connectors.", - "type": "string" - }, - "category": { - "description": "The category of the incident for ServiceNow ITSM and ServiceNow SecOps connectors.", - "type": "string" - }, - "destIp": { - "description": "A comma-separated list of destination IPs for ServiceNow SecOps connectors.", - "type": "string" - }, - "impact": { - "description": "The effect an incident had on business for ServiceNow ITSM connectors.", - "type": "string" - }, - "issueType": { - "description": "The type of issue for Jira connectors.", - "type": "string" - }, - "issueTypes": { - "description": "The type of incident for IBM Resilient connectors.", - "type": "array", - "items": { - "type": "number" - } - }, - "malwareHash": { - "description": "A comma-separated list of malware hashes for ServiceNow SecOps connectors.", - "type": "string" - }, - "malwareUrl": { - "description": "A comma-separated list of malware URLs for ServiceNow SecOps connectors.", - "type": "string" - }, - "parent": { - "description": "The key of the parent issue, when the issue type is sub-task for Jira connectors.", - "type": "string" - }, - "priority": { - "description": "The priority of the issue for Jira and ServiceNow SecOps connectors.", - "type": "string" - }, - "severity": { - "description": "The severity of the incident for ServiceNow ITSM connectors.", - "type": "string" - }, - "severityCode": { - "description": "The severity code of the incident for IBM Resilient connectors.", - "type": "number" - }, - "sourceIp": { - "description": "A comma-separated list of source IPs for ServiceNow SecOps connectors.", - "type": "string" - }, - "subcategory": { - "description": "The subcategory of the incident for ServiceNow ITSM connectors.", - "type": "string" - }, - "urgency": { - "description": "The extent to which the incident resolution can be delayed for ServiceNow ITSM connectors.", - "type": "string" - } - }, - "example": null - }, - "id": { - "description": "The identifier for the connector. To create a case without a connector, use `none`.", - "type": "string", - "example": "none" - }, - "name": { - "description": "The name of the connector. To create a case without a connector, use `none`.", - "type": "string", - "example": "none" - }, - "type": { - "$ref": "#/components/schemas/connector_types" - } - }, - "required": [ - "fields", - "id", - "name", - "type" - ] - }, - "description": { - "description": "The description for the case.", - "type": "string" - }, - "owner": { - "$ref": "#/components/schemas/owners" - }, - "settings": { - "description": "An object that contains the case settings.", - "type": "object", - "properties": { - "syncAlerts": { - "description": "Turns alert syncing on or off.", - "type": "boolean" - } - } - }, - "severity": { - "$ref": "#/components/schemas/severity_property" - }, - "tags": { - "description": "The words and phrases that help categorize cases. It can be an empty array.", - "type": "array", - "items": { - "type": "string" - } - }, - "title": { - "description": "A title for the case.", - "type": "string" - } - }, - "required": [ - "connector", - "description", - "owner", - "settings", - "tags", - "title" - ] - }, - "examples": { - "createCaseRequest": { - "$ref": "#/components/examples/create_case_request" - } - } - } - } - }, - "responses": { - "200": { - "description": "Indicates a successful call.", - "content": { - "application/json; charset=utf-8": { - "schema": { - "type": "object", - "properties": { - "closed_at": { - "type": "string", - "format": "date-time", - "nullable": true, - "example": null + "type": "object", + "properties": { + "closed_at": { + "type": "string", + "format": "date-time", + "nullable": true, + "example": null }, "closed_by": { "type": "object", @@ -3957,8 +3687,8 @@ } }, "examples": { - "createCaseResponse": { - "$ref": "#/components/examples/create_case_response" + "updateCaseCommentResponse": { + "$ref": "#/components/examples/update_comment_response" } } } @@ -3971,10 +3701,60 @@ } ] }, + "get": { + "summary": "Retrieves all the comments from a case in the default space.", + "operationId": "getAllCaseCommentsDefaultSpace", + "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases with the comments you're seeking.\n", + "tags": [ + "cases", + "kibana" + ], + "deprecated": true, + "parameters": [ + { + "$ref": "#/components/parameters/case_id" + } + ], + "responses": { + "200": { + "description": "Indicates a successful call.", + "content": { + "application/json; charset=utf-8": { + "schema": { + "type": "array", + "items": { + "anyOf": [ + { + "$ref": "#/components/schemas/alert_comment_response_properties" + }, + { + "$ref": "#/components/schemas/user_comment_response_properties" + } + ] + } + } + }, + "examples": {} + } + } + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "/api/cases/{caseId}/comments/{commentId}": { "delete": { - "summary": "Deletes one or more cases.", - "operationId": "deleteCase", - "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're deleting.\n", + "summary": "Deletes a comment or alert from a case in the default space.", + "operationId": "deleteCaseCommentDefaultSpace", + "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're deleting.\n", "tags": [ "cases", "kibana" @@ -3984,17 +3764,10 @@ "$ref": "#/components/parameters/kbn_xsrf" }, { - "$ref": "#/components/parameters/space_id" + "$ref": "#/components/parameters/case_id" }, { - "name": "ids", - "description": "The cases that you want to removed. All non-ASCII characters must be URL encoded.", - "in": "query", - "required": true, - "schema": { - "type": "string" - }, - "example": "d4e7abb0-b462-11ec-9a8d-698504725a43" + "$ref": "#/components/parameters/comment_id" } ], "responses": { @@ -4008,54 +3781,601 @@ } ] }, - "patch": { - "summary": "Updates one or more cases.", - "operationId": "updateCase", - "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're updating.\n", + "get": { + "summary": "Retrieves a comment from a case in the default space.", + "operationId": "getCaseCommentDefaultSpace", + "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases with the comments you're seeking.\n", "tags": [ "cases", "kibana" ], "parameters": [ { - "$ref": "#/components/parameters/kbn_xsrf" + "$ref": "#/components/parameters/case_id" }, { - "$ref": "#/components/parameters/space_id" + "$ref": "#/components/parameters/comment_id" } ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "type": "object", - "properties": { - "cases": { - "type": "array", - "items": { - "type": "object", - "properties": { - "connector": { - "description": "An object that contains the connector configuration.", - "type": "object", - "properties": { - "fields": { - "description": "An object containing the connector fields. To create a case without a connector, specify null. If you want to omit any individual field, specify null as its value.", - "nullable": true, - "type": "object", - "properties": { - "caseId": { - "description": "The case identifier for Swimlane connectors.", - "type": "string" - }, - "category": { - "description": "The category of the incident for ServiceNow ITSM and ServiceNow SecOps connectors.", - "type": "string" - }, - "destIp": { - "description": "A comma-separated list of destination IPs for ServiceNow SecOps connectors.", - "type": "string" - }, + "responses": { + "200": { + "description": "Indicates a successful call.", + "content": { + "application/json; charset=utf-8": { + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/alert_comment_response_properties" + }, + { + "$ref": "#/components/schemas/user_comment_response_properties" + } + ] + }, + "examples": { + "getCaseCommentResponse": { + "$ref": "#/components/examples/get_comment_response" + } + } + } + } + } + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "/s/{spaceId}/api/cases": { + "post": { + "summary": "Creates a case.", + "operationId": "createCase", + "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're creating.\n", + "tags": [ + "cases", + "kibana" + ], + "parameters": [ + { + "$ref": "#/components/parameters/kbn_xsrf" + }, + { + "$ref": "#/components/parameters/space_id" + } + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "connector": { + "description": "An object that contains the connector configuration.", + "type": "object", + "properties": { + "fields": { + "description": "An object containing the connector fields. To create a case without a connector, specify null. If you want to omit any individual field, specify null as its value.", + "nullable": true, + "type": "object", + "properties": { + "caseId": { + "description": "The case identifier for Swimlane connectors.", + "type": "string" + }, + "category": { + "description": "The category of the incident for ServiceNow ITSM and ServiceNow SecOps connectors.", + "type": "string" + }, + "destIp": { + "description": "A comma-separated list of destination IPs for ServiceNow SecOps connectors.", + "type": "string" + }, + "impact": { + "description": "The effect an incident had on business for ServiceNow ITSM connectors.", + "type": "string" + }, + "issueType": { + "description": "The type of issue for Jira connectors.", + "type": "string" + }, + "issueTypes": { + "description": "The type of incident for IBM Resilient connectors.", + "type": "array", + "items": { + "type": "number" + } + }, + "malwareHash": { + "description": "A comma-separated list of malware hashes for ServiceNow SecOps connectors.", + "type": "string" + }, + "malwareUrl": { + "description": "A comma-separated list of malware URLs for ServiceNow SecOps connectors.", + "type": "string" + }, + "parent": { + "description": "The key of the parent issue, when the issue type is sub-task for Jira connectors.", + "type": "string" + }, + "priority": { + "description": "The priority of the issue for Jira and ServiceNow SecOps connectors.", + "type": "string" + }, + "severity": { + "description": "The severity of the incident for ServiceNow ITSM connectors.", + "type": "string" + }, + "severityCode": { + "description": "The severity code of the incident for IBM Resilient connectors.", + "type": "number" + }, + "sourceIp": { + "description": "A comma-separated list of source IPs for ServiceNow SecOps connectors.", + "type": "string" + }, + "subcategory": { + "description": "The subcategory of the incident for ServiceNow ITSM connectors.", + "type": "string" + }, + "urgency": { + "description": "The extent to which the incident resolution can be delayed for ServiceNow ITSM connectors.", + "type": "string" + } + }, + "example": null + }, + "id": { + "description": "The identifier for the connector. To create a case without a connector, use `none`.", + "type": "string", + "example": "none" + }, + "name": { + "description": "The name of the connector. To create a case without a connector, use `none`.", + "type": "string", + "example": "none" + }, + "type": { + "$ref": "#/components/schemas/connector_types" + } + }, + "required": [ + "fields", + "id", + "name", + "type" + ] + }, + "description": { + "description": "The description for the case.", + "type": "string" + }, + "owner": { + "$ref": "#/components/schemas/owners" + }, + "settings": { + "description": "An object that contains the case settings.", + "type": "object", + "properties": { + "syncAlerts": { + "description": "Turns alert syncing on or off.", + "type": "boolean" + } + } + }, + "severity": { + "$ref": "#/components/schemas/severity_property" + }, + "tags": { + "description": "The words and phrases that help categorize cases. It can be an empty array.", + "type": "array", + "items": { + "type": "string" + } + }, + "title": { + "description": "A title for the case.", + "type": "string" + } + }, + "required": [ + "connector", + "description", + "owner", + "settings", + "tags", + "title" + ] + }, + "examples": { + "createCaseRequest": { + "$ref": "#/components/examples/create_case_request" + } + } + } + } + }, + "responses": { + "200": { + "description": "Indicates a successful call.", + "content": { + "application/json; charset=utf-8": { + "schema": { + "type": "object", + "properties": { + "closed_at": { + "type": "string", + "format": "date-time", + "nullable": true, + "example": null + }, + "closed_by": { + "type": "object", + "properties": { + "email": { + "type": "string" + }, + "full_name": { + "type": "string" + }, + "username": { + "type": "string" + } + }, + "nullable": true, + "example": null + }, + "comments": { + "type": "array", + "items": { + "oneOf": [ + { + "$ref": "#/components/schemas/alert_comment_response_properties" + }, + { + "$ref": "#/components/schemas/user_comment_response_properties" + } + ] + }, + "example": [] + }, + "connector": { + "type": "object", + "properties": { + "fields": { + "description": "An object containing the connector fields. To create a case without a connector, specify null. If you want to omit any individual field, specify null as its value.", + "nullable": true, + "type": "object", + "properties": { + "caseId": { + "description": "The case identifier for Swimlane connectors.", + "type": "string" + }, + "category": { + "description": "The category of the incident for ServiceNow ITSM and ServiceNow SecOps connectors.", + "type": "string" + }, + "destIp": { + "description": "A comma-separated list of destination IPs for ServiceNow SecOps connectors.", + "type": "string" + }, + "impact": { + "description": "The effect an incident had on business for ServiceNow ITSM connectors.", + "type": "string" + }, + "issueType": { + "description": "The type of issue for Jira connectors.", + "type": "string" + }, + "issueTypes": { + "description": "The type of incident for IBM Resilient connectors.", + "type": "array", + "items": { + "type": "number" + } + }, + "malwareHash": { + "description": "A comma-separated list of malware hashes for ServiceNow SecOps connectors.", + "type": "string" + }, + "malwareUrl": { + "description": "A comma-separated list of malware URLs for ServiceNow SecOps connectors.", + "type": "string" + }, + "parent": { + "description": "The key of the parent issue, when the issue type is sub-task for Jira connectors.", + "type": "string" + }, + "priority": { + "description": "The priority of the issue for Jira and ServiceNow SecOps connectors.", + "type": "string" + }, + "severity": { + "description": "The severity of the incident for ServiceNow ITSM connectors.", + "type": "string" + }, + "severityCode": { + "description": "The severity code of the incident for IBM Resilient connectors.", + "type": "number" + }, + "sourceIp": { + "description": "A comma-separated list of source IPs for ServiceNow SecOps connectors.", + "type": "string" + }, + "subcategory": { + "description": "The subcategory of the incident for ServiceNow ITSM connectors.", + "type": "string" + }, + "urgency": { + "description": "The extent to which the incident resolution can be delayed for ServiceNow ITSM connectors.", + "type": "string" + } + }, + "example": null + }, + "id": { + "description": "The identifier for the connector. To create a case without a connector, use `none`.", + "type": "string", + "example": "none" + }, + "name": { + "description": "The name of the connector. To create a case without a connector, use `none`.", + "type": "string", + "example": "none" + }, + "type": { + "$ref": "#/components/schemas/connector_types" + } + } + }, + "created_at": { + "type": "string", + "format": "date-time", + "example": "2022-05-13T09:16:17.416Z" + }, + "created_by": { + "type": "object", + "properties": { + "email": { + "type": "string", + "example": null + }, + "full_name": { + "type": "string", + "example": null + }, + "username": { + "type": "string", + "example": "elastic" + } + } + }, + "description": { + "type": "string", + "example": "A case description." + }, + "duration": { + "type": "integer", + "description": "The elapsed time from the creation of the case to its closure (in seconds). If the case has not been closed, the duration is set to null. If the case was closed after less than half a second, the duration is rounded down to zero.\n", + "example": 120 + }, + "external_service": { + "type": "object", + "properties": { + "connector_id": { + "type": "string" + }, + "connector_name": { + "type": "string" + }, + "external_id": { + "type": "string" + }, + "external_title": { + "type": "string" + }, + "external_url": { + "type": "string" + }, + "pushed_at": { + "type": "string", + "format": "date-time" + }, + "pushed_by": { + "type": "object", + "properties": { + "email": { + "type": "string" + }, + "full_name": { + "type": "string" + }, + "username": { + "type": "string" + } + }, + "nullable": true, + "example": null + } + } + }, + "id": { + "type": "string", + "example": "66b9aa00-94fa-11ea-9f74-e7e108796192" + }, + "owner": { + "$ref": "#/components/schemas/owners" + }, + "settings": { + "type": "object", + "properties": { + "syncAlerts": { + "type": "boolean", + "example": true + } + } + }, + "severity": { + "$ref": "#/components/schemas/severity_property" + }, + "status": { + "$ref": "#/components/schemas/status" + }, + "tags": { + "type": "array", + "items": { + "type": "string" + }, + "example": [ + "tag-1" + ] + }, + "title": { + "type": "string", + "example": "Case title 1" + }, + "totalAlerts": { + "type": "integer", + "example": 0 + }, + "totalComment": { + "type": "integer", + "example": 0 + }, + "updated_at": { + "type": "string", + "format": "date-time", + "nullable": true, + "example": null + }, + "updated_by": { + "type": "object", + "properties": { + "email": { + "type": "string" + }, + "full_name": { + "type": "string" + }, + "username": { + "type": "string" + } + }, + "nullable": true, + "example": null + }, + "version": { + "type": "string", + "example": "WzUzMiwxXQ==" + } + } + }, + "examples": { + "createCaseResponse": { + "$ref": "#/components/examples/create_case_response" + } + } + } + } + } + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "delete": { + "summary": "Deletes one or more cases.", + "operationId": "deleteCase", + "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're deleting.\n", + "tags": [ + "cases", + "kibana" + ], + "parameters": [ + { + "$ref": "#/components/parameters/kbn_xsrf" + }, + { + "$ref": "#/components/parameters/space_id" + }, + { + "name": "ids", + "description": "The cases that you want to removed. All non-ASCII characters must be URL encoded.", + "in": "query", + "required": true, + "schema": { + "type": "string" + }, + "example": "d4e7abb0-b462-11ec-9a8d-698504725a43" + } + ], + "responses": { + "204": { + "description": "Indicates a successful call." + } + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "patch": { + "summary": "Updates one or more cases.", + "operationId": "updateCase", + "description": "You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're updating.\n", + "tags": [ + "cases", + "kibana" + ], + "parameters": [ + { + "$ref": "#/components/parameters/kbn_xsrf" + }, + { + "$ref": "#/components/parameters/space_id" + } + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "cases": { + "type": "array", + "items": { + "type": "object", + "properties": { + "connector": { + "description": "An object that contains the connector configuration.", + "type": "object", + "properties": { + "fields": { + "description": "An object containing the connector fields. To create a case without a connector, specify null. If you want to omit any individual field, specify null as its value.", + "nullable": true, + "type": "object", + "properties": { + "caseId": { + "description": "The case identifier for Swimlane connectors.", + "type": "string" + }, + "category": { + "description": "The category of the incident for ServiceNow ITSM and ServiceNow SecOps connectors.", + "type": "string" + }, + "destIp": { + "description": "A comma-separated list of destination IPs for ServiceNow SecOps connectors.", + "type": "string" + }, "impact": { "description": "The effect an incident had on business for ServiceNow ITSM connectors.", "type": "string" @@ -5979,47 +6299,228 @@ "schema": { "type": "array", "items": { - "type": "object", - "properties": { - "actionTypeId": { - "$ref": "#/components/schemas/connector_types" - }, - "config": { - "type": "object", - "properties": { - "apiUrl": { - "type": "string" - }, - "projectKey": { - "type": "string" - } - }, - "additionalProperties": true - }, - "id": { - "type": "string" - }, - "isDeprecated": { - "type": "boolean" - }, - "isMissingSecrets": { - "type": "boolean" - }, - "isPreconfigured": { - "type": "boolean" - }, - "name": { - "type": "string" - }, - "referencedByCount": { - "type": "integer" - } - } + "type": "object", + "properties": { + "actionTypeId": { + "$ref": "#/components/schemas/connector_types" + }, + "config": { + "type": "object", + "properties": { + "apiUrl": { + "type": "string" + }, + "projectKey": { + "type": "string" + } + }, + "additionalProperties": true + }, + "id": { + "type": "string" + }, + "isDeprecated": { + "type": "boolean" + }, + "isMissingSecrets": { + "type": "boolean" + }, + "isPreconfigured": { + "type": "boolean" + }, + "name": { + "type": "string" + }, + "referencedByCount": { + "type": "integer" + } + } + } + }, + "examples": { + "findConnectorResponse": { + "$ref": "#/components/examples/find_connector_response" + } + } + } + } + } + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "/s/{spaceId}/api/cases/reporters": { + "get": { + "summary": "Returns information about the users who opened cases.", + "operationId": "getCaseReporters", + "description": "You must have read privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases. The API returns information about the users as they existed at the time of the case creation, including their name, full name, and email address. If any of those details change thereafter or if a user is deleted, the information returned by this API is unchanged.\n", + "tags": [ + "cases", + "kibana" + ], + "parameters": [ + { + "$ref": "#/components/parameters/space_id" + }, + { + "$ref": "#/components/parameters/owner" + } + ], + "responses": { + "200": { + "description": "Indicates a successful call.", + "content": { + "application/json; charset=utf-8": { + "schema": { + "type": "array", + "items": { + "type": "object", + "properties": { + "email": { + "type": "string" + }, + "full_name": { + "type": "string" + }, + "username": { + "type": "string" + } + } + } + }, + "examples": { + "getReportersResponse": { + "$ref": "#/components/examples/get_reporters_response" + } + } + } + } + } + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "/s/{spaceId}/api/cases/status": { + "get": { + "summary": "Returns the number of cases that are open, closed, and in progress.", + "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're seeking.\n", + "deprecated": true, + "tags": [ + "cases", + "kibana" + ], + "parameters": [ + { + "$ref": "#/components/parameters/space_id" + }, + { + "$ref": "#/components/parameters/owner" + } + ], + "responses": { + "200": { + "description": "Indicates a successful call.", + "content": { + "application/json; charset=utf-8": { + "schema": { + "type": "object", + "properties": { + "count_closed_cases": { + "type": "integer" + }, + "count_in_progress_cases": { + "type": "integer" + }, + "count_open_cases": { + "type": "integer" + } + } + }, + "examples": { + "getStatusResponse": { + "$ref": "#/components/examples/get_status_response" + } + } + } + } + } + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "servers": [ + { + "url": "https://localhost:5601" + } + ] + }, + "/s/{spaceId}/api/cases/tags": { + "get": { + "summary": "Aggregates and returns a list of case tags.", + "operationId": "getCaseTags", + "description": "You must have read privileges for the **Cases*** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're seeking.\n", + "tags": [ + "cases", + "kibana" + ], + "parameters": [ + { + "$ref": "#/components/parameters/space_id" + }, + { + "in": "query", + "name": "owner", + "description": "A filter to limit the retrieved case statistics to a specific set of applications. If this parameter is omitted, the response contains tags from all cases that the user has access to read.", + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/owners" + }, + { + "type": "array", + "items": { + "$ref": "#/components/schemas/owners" + } + } + ] + } + } + ], + "responses": { + "200": { + "description": "Indicates a successful call.", + "content": { + "application/json; charset=utf-8": { + "schema": { + "type": "array", + "items": { + "type": "string" } }, "examples": { - "findConnectorResponse": { - "$ref": "#/components/examples/find_connector_response" + "getTagsResponse": { + "$ref": "#/components/examples/get_tags_response" } } } @@ -6038,21 +6539,31 @@ } ] }, - "/s/{spaceId}/api/cases/reporters": { + "/s/{spaceId}/api/cases/{caseId}": { "get": { - "summary": "Returns information about the users who opened cases.", - "operationId": "getCaseReporters", - "description": "You must have read privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases. The API returns information about the users as they existed at the time of the case creation, including their name, full name, and email address. If any of those details change thereafter or if a user is deleted, the information returned by this API is unchanged.\n", + "summary": "Retrieves information about a case.", + "operationId": "getCase", + "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're seeking.\n", "tags": [ "cases", "kibana" ], "parameters": [ + { + "$ref": "#/components/parameters/case_id" + }, { "$ref": "#/components/parameters/space_id" }, { - "$ref": "#/components/parameters/owner" + "in": "query", + "name": "includeComments", + "description": "Determines whether case comments are returned.", + "deprecated": true, + "schema": { + "type": "boolean", + "default": true + } } ], "responses": { @@ -6061,146 +6572,278 @@ "content": { "application/json; charset=utf-8": { "schema": { - "type": "array", - "items": { - "type": "object", - "properties": { - "email": { - "type": "string" + "type": "object", + "properties": { + "closed_at": { + "type": "string", + "format": "date-time", + "nullable": true, + "example": null + }, + "closed_by": { + "type": "object", + "properties": { + "email": { + "type": "string" + }, + "full_name": { + "type": "string" + }, + "username": { + "type": "string" + } }, - "full_name": { + "nullable": true, + "example": null + }, + "comments": { + "type": "array", + "items": { + "oneOf": [ + { + "$ref": "#/components/schemas/alert_comment_response_properties" + }, + { + "$ref": "#/components/schemas/user_comment_response_properties" + } + ] + }, + "example": [] + }, + "connector": { + "type": "object", + "properties": { + "fields": { + "description": "An object containing the connector fields. To create a case without a connector, specify null. If you want to omit any individual field, specify null as its value.", + "nullable": true, + "type": "object", + "properties": { + "caseId": { + "description": "The case identifier for Swimlane connectors.", + "type": "string" + }, + "category": { + "description": "The category of the incident for ServiceNow ITSM and ServiceNow SecOps connectors.", + "type": "string" + }, + "destIp": { + "description": "A comma-separated list of destination IPs for ServiceNow SecOps connectors.", + "type": "string" + }, + "impact": { + "description": "The effect an incident had on business for ServiceNow ITSM connectors.", + "type": "string" + }, + "issueType": { + "description": "The type of issue for Jira connectors.", + "type": "string" + }, + "issueTypes": { + "description": "The type of incident for IBM Resilient connectors.", + "type": "array", + "items": { + "type": "number" + } + }, + "malwareHash": { + "description": "A comma-separated list of malware hashes for ServiceNow SecOps connectors.", + "type": "string" + }, + "malwareUrl": { + "description": "A comma-separated list of malware URLs for ServiceNow SecOps connectors.", + "type": "string" + }, + "parent": { + "description": "The key of the parent issue, when the issue type is sub-task for Jira connectors.", + "type": "string" + }, + "priority": { + "description": "The priority of the issue for Jira and ServiceNow SecOps connectors.", + "type": "string" + }, + "severity": { + "description": "The severity of the incident for ServiceNow ITSM connectors.", + "type": "string" + }, + "severityCode": { + "description": "The severity code of the incident for IBM Resilient connectors.", + "type": "number" + }, + "sourceIp": { + "description": "A comma-separated list of source IPs for ServiceNow SecOps connectors.", + "type": "string" + }, + "subcategory": { + "description": "The subcategory of the incident for ServiceNow ITSM connectors.", + "type": "string" + }, + "urgency": { + "description": "The extent to which the incident resolution can be delayed for ServiceNow ITSM connectors.", + "type": "string" + } + }, + "example": null + }, + "id": { + "description": "The identifier for the connector. To create a case without a connector, use `none`.", + "type": "string", + "example": "none" + }, + "name": { + "description": "The name of the connector. To create a case without a connector, use `none`.", + "type": "string", + "example": "none" + }, + "type": { + "$ref": "#/components/schemas/connector_types" + } + } + }, + "created_at": { + "type": "string", + "format": "date-time", + "example": "2022-05-13T09:16:17.416Z" + }, + "created_by": { + "type": "object", + "properties": { + "email": { + "type": "string", + "example": null + }, + "full_name": { + "type": "string", + "example": null + }, + "username": { + "type": "string", + "example": "elastic" + } + } + }, + "description": { + "type": "string", + "example": "A case description." + }, + "duration": { + "type": "integer", + "description": "The elapsed time from the creation of the case to its closure (in seconds). If the case has not been closed, the duration is set to null. If the case was closed after less than half a second, the duration is rounded down to zero.\n", + "example": 120 + }, + "external_service": { + "type": "object", + "properties": { + "connector_id": { + "type": "string" + }, + "connector_name": { + "type": "string" + }, + "external_id": { + "type": "string" + }, + "external_title": { + "type": "string" + }, + "external_url": { + "type": "string" + }, + "pushed_at": { + "type": "string", + "format": "date-time" + }, + "pushed_by": { + "type": "object", + "properties": { + "email": { + "type": "string" + }, + "full_name": { + "type": "string" + }, + "username": { + "type": "string" + } + }, + "nullable": true, + "example": null + } + } + }, + "id": { + "type": "string", + "example": "66b9aa00-94fa-11ea-9f74-e7e108796192" + }, + "owner": { + "$ref": "#/components/schemas/owners" + }, + "settings": { + "type": "object", + "properties": { + "syncAlerts": { + "type": "boolean", + "example": true + } + } + }, + "severity": { + "$ref": "#/components/schemas/severity_property" + }, + "status": { + "$ref": "#/components/schemas/status" + }, + "tags": { + "type": "array", + "items": { "type": "string" }, - "username": { - "type": "string" - } - } - } - }, - "examples": { - "getReportersResponse": { - "$ref": "#/components/examples/get_reporters_response" - } - } - } - } - } - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "/s/{spaceId}/api/cases/status": { - "get": { - "summary": "Returns the number of cases that are open, closed, and in progress.", - "description": "You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're seeking.\n", - "deprecated": true, - "tags": [ - "cases", - "kibana" - ], - "parameters": [ - { - "$ref": "#/components/parameters/space_id" - }, - { - "$ref": "#/components/parameters/owner" - } - ], - "responses": { - "200": { - "description": "Indicates a successful call.", - "content": { - "application/json; charset=utf-8": { - "schema": { - "type": "object", - "properties": { - "count_closed_cases": { - "type": "integer" + "example": [ + "tag-1" + ] }, - "count_in_progress_cases": { - "type": "integer" + "title": { + "type": "string", + "example": "Case title 1" }, - "count_open_cases": { - "type": "integer" + "totalAlerts": { + "type": "integer", + "example": 0 + }, + "totalComment": { + "type": "integer", + "example": 0 + }, + "updated_at": { + "type": "string", + "format": "date-time", + "nullable": true, + "example": null + }, + "updated_by": { + "type": "object", + "properties": { + "email": { + "type": "string" + }, + "full_name": { + "type": "string" + }, + "username": { + "type": "string" + } + }, + "nullable": true, + "example": null + }, + "version": { + "type": "string", + "example": "WzUzMiwxXQ==" } } }, "examples": { - "getStatusResponse": { - "$ref": "#/components/examples/get_status_response" - } - } - } - } - } - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "servers": [ - { - "url": "https://localhost:5601" - } - ] - }, - "/s/{spaceId}/api/cases/tags": { - "get": { - "summary": "Aggregates and returns a list of case tags.", - "operationId": "getCaseTags", - "description": "You must have read privileges for the **Cases*** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're seeking.\n", - "tags": [ - "cases", - "kibana" - ], - "parameters": [ - { - "$ref": "#/components/parameters/space_id" - }, - { - "in": "query", - "name": "owner", - "description": "A filter to limit the retrieved case statistics to a specific set of applications. If this parameter is omitted, the response contains tags from all cases that the user has access to read.", - "schema": { - "oneOf": [ - { - "$ref": "#/components/schemas/owners" - }, - { - "type": "array", - "items": { - "$ref": "#/components/schemas/owners" - } - } - ] - } - } - ], - "responses": { - "200": { - "description": "Indicates a successful call.", - "content": { - "application/json; charset=utf-8": { - "schema": { - "type": "array", - "items": { - "type": "string" - } - }, - "examples": { - "getTagsResponse": { - "$ref": "#/components/examples/get_tags_response" + "getCaseResponse": { + "$ref": "#/components/examples/get_case_response" } } } @@ -7857,6 +8500,67 @@ "tag 2" ] }, + "get_case_response": { + "summary": "Retrieves information about a case including its comments.", + "value": { + "id": "31cdada0-02c1-11ed-85f2-4f7c222ca2fa", + "version": "WzM2LDFd", + "comments": [ + { + "id": "2134c1d0-02c2-11ed-85f2-4f7c222ca2fa", + "version": "WzM3LDFd", + "type": "user", + "owner": "cases", + "comment": "A new comment", + "created_at": "2022-07-13T15:40:32.335Z", + "created_by": { + "email": null, + "full_name": null, + "username": "elastic" + }, + "pushed_at": null, + "pushed_by": null, + "updated_at": null, + "updated_by": null + } + ], + "totalComment": 1, + "totalAlerts": 0, + "title": "Case title 1", + "tags": [ + "tag 1" + ], + "settings": { + "syncAlerts": true + }, + "owner": "cases", + "description": "A case description", + "duration": null, + "severity": "low", + "closed_at": null, + "closed_by": null, + "created_at": "2022-07-13T15:33:50.604Z", + "created_by": { + "username": "elastic", + "email": null, + "full_name": null + }, + "status": "open", + "updated_at": "2022-07-13T15:40:32.335Z", + "updated_by": { + "full_name": null, + "email": null, + "username": "elastic" + }, + "connector": { + "id": "none", + "name": "none", + "type": ".none", + "fields": null + }, + "external_service": null + } + }, "add_comment_request": { "summary": "Adds a comment to a case.", "value": { diff --git a/x-pack/plugins/cases/docs/openapi/bundled.yaml b/x-pack/plugins/cases/docs/openapi/bundled.yaml index 57b3c4647887c..57b01b3f05365 100644 --- a/x-pack/plugins/cases/docs/openapi/bundled.yaml +++ b/x-pack/plugins/cases/docs/openapi/bundled.yaml @@ -2259,6 +2259,266 @@ paths: - url: https://localhost:5601 servers: - url: https://localhost:5601 + /api/cases/{caseId}: + get: + summary: Retrieves information about a case in the default space. + operationId: getCaseDefaultSpace + description: > + You must have `read` privileges for the **Cases** feature in the + **Management**, **Observability**, or **Security** section of the Kibana + feature privileges, depending on the owner of the case you're seeking. + tags: + - cases + - kibana + parameters: + - $ref: '#/components/parameters/case_id' + - in: query + name: includeComments + description: Determines whether case comments are returned. + deprecated: true + schema: + type: boolean + default: true + responses: + '200': + description: Indicates a successful call. + content: + application/json; charset=utf-8: + schema: + type: object + properties: + closed_at: + type: string + format: date-time + nullable: true + example: null + closed_by: + type: object + properties: + email: + type: string + full_name: + type: string + username: + type: string + nullable: true + example: null + comments: + type: array + items: + oneOf: + - $ref: >- + #/components/schemas/alert_comment_response_properties + - $ref: >- + #/components/schemas/user_comment_response_properties + example: [] + connector: + type: object + properties: + fields: + description: >- + An object containing the connector fields. To create a + case without a connector, specify null. If you want to + omit any individual field, specify null as its value. + nullable: true + type: object + properties: + caseId: + description: The case identifier for Swimlane connectors. + type: string + category: + description: >- + The category of the incident for ServiceNow ITSM + and ServiceNow SecOps connectors. + type: string + destIp: + description: >- + A comma-separated list of destination IPs for + ServiceNow SecOps connectors. + type: string + impact: + description: >- + The effect an incident had on business for + ServiceNow ITSM connectors. + type: string + issueType: + description: The type of issue for Jira connectors. + type: string + issueTypes: + description: The type of incident for IBM Resilient connectors. + type: array + items: + type: number + malwareHash: + description: >- + A comma-separated list of malware hashes for + ServiceNow SecOps connectors. + type: string + malwareUrl: + description: >- + A comma-separated list of malware URLs for + ServiceNow SecOps connectors. + type: string + parent: + description: >- + The key of the parent issue, when the issue type + is sub-task for Jira connectors. + type: string + priority: + description: >- + The priority of the issue for Jira and ServiceNow + SecOps connectors. + type: string + severity: + description: >- + The severity of the incident for ServiceNow ITSM + connectors. + type: string + severityCode: + description: >- + The severity code of the incident for IBM + Resilient connectors. + type: number + sourceIp: + description: >- + A comma-separated list of source IPs for + ServiceNow SecOps connectors. + type: string + subcategory: + description: >- + The subcategory of the incident for ServiceNow + ITSM connectors. + type: string + urgency: + description: >- + The extent to which the incident resolution can be + delayed for ServiceNow ITSM connectors. + type: string + example: null + id: + description: >- + The identifier for the connector. To create a case + without a connector, use `none`. + type: string + example: none + name: + description: >- + The name of the connector. To create a case without a + connector, use `none`. + type: string + example: none + type: + $ref: '#/components/schemas/connector_types' + created_at: + type: string + format: date-time + example: '2022-05-13T09:16:17.416Z' + created_by: + type: object + properties: + email: + type: string + example: null + full_name: + type: string + example: null + username: + type: string + example: elastic + description: + type: string + example: A case description. + duration: + type: integer + description: > + The elapsed time from the creation of the case to its + closure (in seconds). If the case has not been closed, the + duration is set to null. If the case was closed after less + than half a second, the duration is rounded down to zero. + example: 120 + external_service: + type: object + properties: + connector_id: + type: string + connector_name: + type: string + external_id: + type: string + external_title: + type: string + external_url: + type: string + pushed_at: + type: string + format: date-time + pushed_by: + type: object + properties: + email: + type: string + full_name: + type: string + username: + type: string + nullable: true + example: null + id: + type: string + example: 66b9aa00-94fa-11ea-9f74-e7e108796192 + owner: + $ref: '#/components/schemas/owners' + settings: + type: object + properties: + syncAlerts: + type: boolean + example: true + severity: + $ref: '#/components/schemas/severity_property' + status: + $ref: '#/components/schemas/status' + tags: + type: array + items: + type: string + example: + - tag-1 + title: + type: string + example: Case title 1 + totalAlerts: + type: integer + example: 0 + totalComment: + type: integer + example: 0 + updated_at: + type: string + format: date-time + nullable: true + example: null + updated_by: + type: object + properties: + email: + type: string + full_name: + type: string + username: + type: string + nullable: true + example: null + version: + type: string + example: WzUzMiwxXQ== + examples: + getCaseResponse: + $ref: '#/components/examples/get_case_response' + servers: + - url: https://localhost:5601 + servers: + - url: https://localhost:5601 /api/cases/{caseId}/comments: post: summary: Adds a comment or alert to a case in the default space. @@ -5139,12 +5399,273 @@ paths: - url: https://localhost:5601 servers: - url: https://localhost:5601 - /s/{spaceId}/api/cases/{caseId}/comments: - post: - summary: Adds a comment or alert to a case. - operationId: addCaseComment + /s/{spaceId}/api/cases/{caseId}: + get: + summary: Retrieves information about a case. + operationId: getCase description: > - You must have `all` privileges for the **Cases** feature in the + You must have `read` privileges for the **Cases** feature in the + **Management**, **Observability**, or **Security** section of the Kibana + feature privileges, depending on the owner of the case you're seeking. + tags: + - cases + - kibana + parameters: + - $ref: '#/components/parameters/case_id' + - $ref: '#/components/parameters/space_id' + - in: query + name: includeComments + description: Determines whether case comments are returned. + deprecated: true + schema: + type: boolean + default: true + responses: + '200': + description: Indicates a successful call. + content: + application/json; charset=utf-8: + schema: + type: object + properties: + closed_at: + type: string + format: date-time + nullable: true + example: null + closed_by: + type: object + properties: + email: + type: string + full_name: + type: string + username: + type: string + nullable: true + example: null + comments: + type: array + items: + oneOf: + - $ref: >- + #/components/schemas/alert_comment_response_properties + - $ref: >- + #/components/schemas/user_comment_response_properties + example: [] + connector: + type: object + properties: + fields: + description: >- + An object containing the connector fields. To create a + case without a connector, specify null. If you want to + omit any individual field, specify null as its value. + nullable: true + type: object + properties: + caseId: + description: The case identifier for Swimlane connectors. + type: string + category: + description: >- + The category of the incident for ServiceNow ITSM + and ServiceNow SecOps connectors. + type: string + destIp: + description: >- + A comma-separated list of destination IPs for + ServiceNow SecOps connectors. + type: string + impact: + description: >- + The effect an incident had on business for + ServiceNow ITSM connectors. + type: string + issueType: + description: The type of issue for Jira connectors. + type: string + issueTypes: + description: The type of incident for IBM Resilient connectors. + type: array + items: + type: number + malwareHash: + description: >- + A comma-separated list of malware hashes for + ServiceNow SecOps connectors. + type: string + malwareUrl: + description: >- + A comma-separated list of malware URLs for + ServiceNow SecOps connectors. + type: string + parent: + description: >- + The key of the parent issue, when the issue type + is sub-task for Jira connectors. + type: string + priority: + description: >- + The priority of the issue for Jira and ServiceNow + SecOps connectors. + type: string + severity: + description: >- + The severity of the incident for ServiceNow ITSM + connectors. + type: string + severityCode: + description: >- + The severity code of the incident for IBM + Resilient connectors. + type: number + sourceIp: + description: >- + A comma-separated list of source IPs for + ServiceNow SecOps connectors. + type: string + subcategory: + description: >- + The subcategory of the incident for ServiceNow + ITSM connectors. + type: string + urgency: + description: >- + The extent to which the incident resolution can be + delayed for ServiceNow ITSM connectors. + type: string + example: null + id: + description: >- + The identifier for the connector. To create a case + without a connector, use `none`. + type: string + example: none + name: + description: >- + The name of the connector. To create a case without a + connector, use `none`. + type: string + example: none + type: + $ref: '#/components/schemas/connector_types' + created_at: + type: string + format: date-time + example: '2022-05-13T09:16:17.416Z' + created_by: + type: object + properties: + email: + type: string + example: null + full_name: + type: string + example: null + username: + type: string + example: elastic + description: + type: string + example: A case description. + duration: + type: integer + description: > + The elapsed time from the creation of the case to its + closure (in seconds). If the case has not been closed, the + duration is set to null. If the case was closed after less + than half a second, the duration is rounded down to zero. + example: 120 + external_service: + type: object + properties: + connector_id: + type: string + connector_name: + type: string + external_id: + type: string + external_title: + type: string + external_url: + type: string + pushed_at: + type: string + format: date-time + pushed_by: + type: object + properties: + email: + type: string + full_name: + type: string + username: + type: string + nullable: true + example: null + id: + type: string + example: 66b9aa00-94fa-11ea-9f74-e7e108796192 + owner: + $ref: '#/components/schemas/owners' + settings: + type: object + properties: + syncAlerts: + type: boolean + example: true + severity: + $ref: '#/components/schemas/severity_property' + status: + $ref: '#/components/schemas/status' + tags: + type: array + items: + type: string + example: + - tag-1 + title: + type: string + example: Case title 1 + totalAlerts: + type: integer + example: 0 + totalComment: + type: integer + example: 0 + updated_at: + type: string + format: date-time + nullable: true + example: null + updated_by: + type: object + properties: + email: + type: string + full_name: + type: string + username: + type: string + nullable: true + example: null + version: + type: string + example: WzUzMiwxXQ== + examples: + getCaseResponse: + $ref: '#/components/examples/get_case_response' + servers: + - url: https://localhost:5601 + servers: + - url: https://localhost:5601 + /s/{spaceId}/api/cases/{caseId}/comments: + post: + summary: Adds a comment or alert to a case. + operationId: addCaseComment + description: > + You must have `all` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're creating. tags: @@ -6432,6 +6953,56 @@ components: - security - tag 1 - tag 2 + get_case_response: + summary: Retrieves information about a case including its comments. + value: + id: 31cdada0-02c1-11ed-85f2-4f7c222ca2fa + version: WzM2LDFd + comments: + - id: 2134c1d0-02c2-11ed-85f2-4f7c222ca2fa + version: WzM3LDFd + type: user + owner: cases + comment: A new comment + created_at: '2022-07-13T15:40:32.335Z' + created_by: + email: null + full_name: null + username: elastic + pushed_at: null + pushed_by: null + updated_at: null + updated_by: null + totalComment: 1 + totalAlerts: 0 + title: Case title 1 + tags: + - tag 1 + settings: + syncAlerts: true + owner: cases + description: A case description + duration: null + severity: low + closed_at: null + closed_by: null + created_at: '2022-07-13T15:33:50.604Z' + created_by: + username: elastic + email: null + full_name: null + status: open + updated_at: '2022-07-13T15:40:32.335Z' + updated_by: + full_name: null + email: null + username: elastic + connector: + id: none + name: none + type: .none + fields: null + external_service: null add_comment_request: summary: Adds a comment to a case. value: diff --git a/x-pack/plugins/cases/docs/openapi/components/examples/get_case_response.yaml b/x-pack/plugins/cases/docs/openapi/components/examples/get_case_response.yaml new file mode 100644 index 0000000000000..936a21a5cfc70 --- /dev/null +++ b/x-pack/plugins/cases/docs/openapi/components/examples/get_case_response.yaml @@ -0,0 +1,44 @@ +summary: Retrieves information about a case including its comments. +value: + { + "id":"31cdada0-02c1-11ed-85f2-4f7c222ca2fa", + "version":"WzM2LDFd", + "comments":[{ + "id":"2134c1d0-02c2-11ed-85f2-4f7c222ca2fa", + "version":"WzM3LDFd", + "type":"user", + "owner":"cases", + "comment":"A new comment", + "created_at":"2022-07-13T15:40:32.335Z", + "created_by":{ + "email":null, + "full_name":null, + "username":"elastic" + }, + "pushed_at":null, + "pushed_by":null, + "updated_at":null, + "updated_by":null + }], + "totalComment":1, + "totalAlerts":0, + "title":"Case title 1", + "tags":["tag 1"], + "settings":{"syncAlerts":true}, + "owner":"cases", + "description":"A case description", + "duration":null, + "severity":"low", + "closed_at":null, + "closed_by":null, + "created_at":"2022-07-13T15:33:50.604Z", + "created_by":{"username":"elastic","email":null,"full_name":null},"status":"open", + "updated_at":"2022-07-13T15:40:32.335Z", + "updated_by":{"full_name":null,"email":null,"username":"elastic"},"connector":{ + "id":"none", + "name":"none", + "type":".none", + "fields":null + }, + "external_service":null + } \ No newline at end of file diff --git a/x-pack/plugins/cases/docs/openapi/components/examples/get_status.yaml b/x-pack/plugins/cases/docs/openapi/components/examples/get_status_response.yaml similarity index 100% rename from x-pack/plugins/cases/docs/openapi/components/examples/get_status.yaml rename to x-pack/plugins/cases/docs/openapi/components/examples/get_status_response.yaml diff --git a/x-pack/plugins/cases/docs/openapi/entrypoint.yaml b/x-pack/plugins/cases/docs/openapi/entrypoint.yaml index c32112eacbda0..7e05b510d5375 100644 --- a/x-pack/plugins/cases/docs/openapi/entrypoint.yaml +++ b/x-pack/plugins/cases/docs/openapi/entrypoint.yaml @@ -35,8 +35,8 @@ paths: $ref: 'paths/api@cases@status.yaml' '/api/cases/tags': $ref: 'paths/api@cases@tags.yaml' -# '/api/cases/{caseId}': -# $ref: 'paths/api@cases@{caseid}.yaml' + '/api/cases/{caseId}': + $ref: 'paths/api@cases@{caseid}.yaml' # '/api/cases/{caseId}/alerts': # $ref: 'paths/api@cases@{caseid}@alerts.yaml' '/api/cases/{caseId}/comments': @@ -66,8 +66,8 @@ paths: $ref: 'paths/s@{spaceid}@api@cases@status.yaml' '/s/{spaceId}/api/cases/tags': $ref: 'paths/s@{spaceid}@api@cases@tags.yaml' - # '/s/{spaceId}/api/cases/{caseId}': - # $ref: 'paths/s@{spaceid}@api@cases@{caseid}.yaml' + '/s/{spaceId}/api/cases/{caseId}': + $ref: 'paths/s@{spaceid}@api@cases@{caseid}.yaml' # '/s/{spaceId}/api/cases/{caseId}/alerts': # $ref: 'paths/s@{spaceid}@api@cases@{caseid}@alerts.yaml' '/s/{spaceId}/api/cases/{caseId}/comments': diff --git a/x-pack/plugins/cases/docs/openapi/paths/api@cases@{caseid}.yaml b/x-pack/plugins/cases/docs/openapi/paths/api@cases@{caseid}.yaml new file mode 100644 index 0000000000000..7290e5f5fdfba --- /dev/null +++ b/x-pack/plugins/cases/docs/openapi/paths/api@cases@{caseid}.yaml @@ -0,0 +1,35 @@ +get: + summary: Retrieves information about a case in the default space. + operationId: getCaseDefaultSpace + description: > + You must have `read` privileges for the **Cases** feature in the + **Management**, **Observability**, or **Security** section of the Kibana + feature privileges, depending on the owner of the case you're seeking. + tags: + - cases + - kibana + parameters: + - $ref: ../components/parameters/case_id.yaml + - in: query + name: includeComments + description: Determines whether case comments are returned. + deprecated: true + schema: + type: boolean + default: true + responses: + '200': + description: Indicates a successful call. + content: + application/json; charset=utf-8: + schema: + type: object + properties: + $ref: '../components/schemas/case_response_properties.yaml' + examples: + getCaseResponse: + $ref: '../components/examples/get_case_response.yaml' + servers: + - url: https://localhost:5601 +servers: + - url: https://localhost:5601 diff --git a/x-pack/plugins/cases/docs/openapi/paths/s@{spaceid}@api@cases@{caseid}.yaml b/x-pack/plugins/cases/docs/openapi/paths/s@{spaceid}@api@cases@{caseid}.yaml new file mode 100644 index 0000000000000..30c33a27a37f6 --- /dev/null +++ b/x-pack/plugins/cases/docs/openapi/paths/s@{spaceid}@api@cases@{caseid}.yaml @@ -0,0 +1,36 @@ +get: + summary: Retrieves information about a case. + operationId: getCase + description: > + You must have `read` privileges for the **Cases** feature in the + **Management**, **Observability**, or **Security** section of the Kibana + feature privileges, depending on the owner of the case you're seeking. + tags: + - cases + - kibana + parameters: + - $ref: ../components/parameters/case_id.yaml + - $ref: '../components/parameters/space_id.yaml' + - in: query + name: includeComments + description: Determines whether case comments are returned. + deprecated: true + schema: + type: boolean + default: true + responses: + '200': + description: Indicates a successful call. + content: + application/json; charset=utf-8: + schema: + type: object + properties: + $ref: '../components/schemas/case_response_properties.yaml' + examples: + getCaseResponse: + $ref: '../components/examples/get_case_response.yaml' + servers: + - url: https://localhost:5601 +servers: + - url: https://localhost:5601 From d351c92b1a70f195eae73fd29da7c53773354247 Mon Sep 17 00:00:00 2001 From: Nathan Reese Date: Thu, 14 Jul 2022 12:57:58 -0600 Subject: [PATCH 042/111] [Maps] change EMS tile layer display name to 'Basemap' (#136393) * [Maps] change EMS basemap display name to 'Basemap' * add tooltip content * revert getLayerTypeIconName deletion * change i18n tag * rename * eslint * fix functional tests * Update x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/ems_vector_tile_layer.tsx Co-authored-by: gchaps <33642766+gchaps@users.noreply.github.com> Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> Co-authored-by: gchaps <33642766+gchaps@users.noreply.github.com> --- ...ile_layer.ts => ems_vector_tile_layer.tsx} | 13 +++++++++++- .../sources/ems_tms_source/ems_tms_source.tsx | 12 +++++++++-- .../apps/maps/group1/sample_data.js | 6 +++--- .../test/functional/page_objects/gis_page.ts | 5 +++++ .../upgrade/apps/maps/maps_smoke_tests.ts | 6 +++--- .../upgrade/services/maps_upgrade_services.ts | 21 ------------------- 6 files changed, 33 insertions(+), 30 deletions(-) rename x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/{ems_vector_tile_layer.ts => ems_vector_tile_layer.tsx} (97%) diff --git a/x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/ems_vector_tile_layer.ts b/x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/ems_vector_tile_layer.tsx similarity index 97% rename from x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/ems_vector_tile_layer.ts rename to x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/ems_vector_tile_layer.tsx index 05009abc7793b..bedf997566ec2 100644 --- a/x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/ems_vector_tile_layer.ts +++ b/x-pack/plugins/maps/public/classes/layers/ems_vector_tile_layer/ems_vector_tile_layer.tsx @@ -5,13 +5,15 @@ * 2.0. */ +import React from 'react'; import type { Map as MbMap, LayerSpecification, StyleSpecification } from '@kbn/mapbox-gl'; import { type blendMode, type EmsSpriteSheet, TMSService } from '@elastic/ems-client'; import { i18n } from '@kbn/i18n'; import _ from 'lodash'; +import { EuiIcon } from '@elastic/eui'; // @ts-expect-error import { RGBAImage } from './image_utils'; -import { AbstractLayer } from '../layer'; +import { AbstractLayer, type LayerIcon } from '../layer'; import { AUTOSELECT_EMS_LOCALE, NO_EMS_LOCALE, @@ -486,6 +488,15 @@ export class EmsVectorTileLayer extends AbstractLayer { return 'grid'; } + getLayerIcon(): LayerIcon { + return { + icon: , + tooltipContent: i18n.translate('xpack.maps.emsVectorTileLayer.layerDescription', { + defaultMessage: `Reference map provided by Elastic Maps Service (EMS).`, + }), + }; + } + isBasemap(order: number) { return order === 0; } diff --git a/x-pack/plugins/maps/public/classes/sources/ems_tms_source/ems_tms_source.tsx b/x-pack/plugins/maps/public/classes/sources/ems_tms_source/ems_tms_source.tsx index 6874820d561f7..cc094bc6caeef 100644 --- a/x-pack/plugins/maps/public/classes/sources/ems_tms_source/ems_tms_source.tsx +++ b/x-pack/plugins/maps/public/classes/sources/ems_tms_source/ems_tms_source.tsx @@ -66,7 +66,7 @@ export class EMSTMSSource extends AbstractSource implements ITMSSource { } async getImmutableProperties() { - const displayName = await this.getDisplayName(); + const tileServiceName = await this._getTileServiceName(); const autoSelectMsg = i18n.translate('xpack.maps.source.emsTile.isAutoSelectLabel', { defaultMessage: 'autoselect based on Kibana theme', }); @@ -80,7 +80,9 @@ export class EMSTMSSource extends AbstractSource implements ITMSSource { label: i18n.translate('xpack.maps.source.emsTile.serviceId', { defaultMessage: `Tile service`, }), - value: this._descriptor.isAutoSelect ? `${displayName} - ${autoSelectMsg}` : displayName, + value: this._descriptor.isAutoSelect + ? `${tileServiceName} - ${autoSelectMsg}` + : tileServiceName, }, ]; @@ -114,6 +116,12 @@ export class EMSTMSSource extends AbstractSource implements ITMSSource { } async getDisplayName() { + return i18n.translate('xpack.maps.source.emsTile.basemapLabel', { + defaultMessage: 'Basemap', + }); + } + + async _getTileServiceName() { try { const emsTMSService = await this._getEMSTMSService(); return emsTMSService.getDisplayName(); diff --git a/x-pack/test/functional/apps/maps/group1/sample_data.js b/x-pack/test/functional/apps/maps/group1/sample_data.js index a8ebc8ec6ba85..d9ef08ef712f1 100644 --- a/x-pack/test/functional/apps/maps/group1/sample_data.js +++ b/x-pack/test/functional/apps/maps/group1/sample_data.js @@ -68,7 +68,7 @@ export default function ({ getPageObjects, getService, updateBaselines }) { describe('ecommerce', () => { before(async () => { await PageObjects.maps.loadSavedMap('[eCommerce] Orders by Country'); - await PageObjects.maps.toggleLayerVisibility('Road map - desaturated'); + await PageObjects.maps.toggleEmsBasemapLayerVisibility(); await PageObjects.maps.toggleLayerVisibility('United Kingdom'); await PageObjects.maps.toggleLayerVisibility('France'); await PageObjects.maps.toggleLayerVisibility('United States'); @@ -96,7 +96,7 @@ export default function ({ getPageObjects, getService, updateBaselines }) { describe('flights', () => { before(async () => { await PageObjects.maps.loadSavedMap('[Flights] Origin Time Delayed'); - await PageObjects.maps.toggleLayerVisibility('Road map - desaturated'); + await PageObjects.maps.toggleEmsBasemapLayerVisibility(); await PageObjects.timePicker.setCommonlyUsedTime('sample_data range'); await PageObjects.maps.enterFullScreen(); await PageObjects.maps.closeLegend(); @@ -121,7 +121,7 @@ export default function ({ getPageObjects, getService, updateBaselines }) { before(async () => { await PageObjects.maps.loadSavedMap('[Logs] Total Requests and Bytes'); await PageObjects.maps.toggleLayerVisibility('Total Requests by Destination'); - await PageObjects.maps.toggleLayerVisibility('Road map - desaturated'); + await PageObjects.maps.toggleEmsBasemapLayerVisibility(); await PageObjects.timePicker.setCommonlyUsedTime('sample_data range'); await PageObjects.maps.enterFullScreen(); await PageObjects.maps.closeLegend(); diff --git a/x-pack/test/functional/page_objects/gis_page.ts b/x-pack/test/functional/page_objects/gis_page.ts index e1b55d5eefe05..8e5e78a6154e7 100644 --- a/x-pack/test/functional/page_objects/gis_page.ts +++ b/x-pack/test/functional/page_objects/gis_page.ts @@ -302,6 +302,11 @@ export class GisPageObject extends FtrService { await this.testSubjects.click('layerVisibilityToggleButton'); } + // In 8.4, EMS basemap layers no longer use EMS tile service name, instead using "Basemap" + async toggleEmsBasemapLayerVisibility() { + await this.toggleLayerVisibility('Basemap'); + } + async openLegend() { const isOpen = await this.testSubjects.exists('mapLayerTOC'); if (isOpen === false) { diff --git a/x-pack/test/upgrade/apps/maps/maps_smoke_tests.ts b/x-pack/test/upgrade/apps/maps/maps_smoke_tests.ts index 334b4ce965905..db8e624ac4356 100644 --- a/x-pack/test/upgrade/apps/maps/maps_smoke_tests.ts +++ b/x-pack/test/upgrade/apps/maps/maps_smoke_tests.ts @@ -110,7 +110,7 @@ export default function ({ await PageObjects.home.launchSampleMap('ecommerce'); await PageObjects.header.waitUntilLoadingHasFinished(); await PageObjects.maps.waitForLayersToLoad(); - await mapsHelper.toggleLayerVisibilityRoadMap(); + await PageObjects.maps.toggleEmsBasemapLayerVisibility(); await PageObjects.maps.toggleLayerVisibility('United Kingdom'); await PageObjects.maps.toggleLayerVisibility('France'); await PageObjects.maps.toggleLayerVisibility('United States'); @@ -138,7 +138,7 @@ export default function ({ await PageObjects.home.launchSampleMap('flights'); await PageObjects.header.waitUntilLoadingHasFinished(); await PageObjects.maps.waitForLayersToLoad(); - await mapsHelper.toggleLayerVisibilityRoadMap(); + await PageObjects.maps.toggleEmsBasemapLayerVisibility(); await PageObjects.timePicker.setCommonlyUsedTime('sample_data range'); await PageObjects.maps.enterFullScreen(); await PageObjects.maps.closeLegend(); @@ -162,7 +162,7 @@ export default function ({ await PageObjects.home.launchSampleMap('logs'); await PageObjects.header.waitUntilLoadingHasFinished(); await PageObjects.maps.waitForLayersToLoad(); - await mapsHelper.toggleLayerVisibilityRoadMap(); + await PageObjects.maps.toggleEmsBasemapLayerVisibility(); await mapsHelper.toggleLayerVisibilityTotalRequests(); await PageObjects.timePicker.setCommonlyUsedTime('sample_data range'); await PageObjects.maps.enterFullScreen(); diff --git a/x-pack/test/upgrade/services/maps_upgrade_services.ts b/x-pack/test/upgrade/services/maps_upgrade_services.ts index 28eafafc8663a..97adb3ca9ea8a 100644 --- a/x-pack/test/upgrade/services/maps_upgrade_services.ts +++ b/x-pack/test/upgrade/services/maps_upgrade_services.ts @@ -25,27 +25,6 @@ export function MapsHelper({ getPageObjects, getService }: FtrProviderContext) { } }, - // In v8.0, the default base map switched from bright to desaturated. - // https://github.com/elastic/kibana/pull/116179 - // Maps created before this change will have a base map called "Road map" - // Maps created after this change will have a base map called "Road map - desaturated" - // toggleLayerVisibilityRoadMap will toggle layer visibility for either value - async toggleLayerVisibilityRoadMap() { - const isRoadMapDesaturated = await testSubjects.exists( - 'layerTocActionsPanelToggleButtonRoad_map_-_desaturated' - ); - const isRoadMap = await testSubjects.exists('layerTocActionsPanelToggleButtonRoad_map'); - if (!isRoadMapDesaturated && !isRoadMap) { - throw new Error('Layer road map not found'); - } - if (isRoadMapDesaturated) { - await this.toggleLayerVisibility('Road map - desaturated'); - } - if (isRoadMap) { - await this.toggleLayerVisibility('Road map'); - } - }, - // In v7.16, e-commerce sample data was re-worked so that geo.src field to match country code of geo.coordinates // https://github.com/elastic/kibana/pull/110885 // Maps created before this change will have a layer called "Total Requests by Country" From 86a16274eb73ce6cede7cebd98745e8a8de90535 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Istv=C3=A1n=20Zolt=C3=A1n=20Szab=C3=B3?= Date: Thu, 14 Jul 2022 20:59:22 +0200 Subject: [PATCH 043/111] [ML] Changes Learn more link URL on start deployment modal (#136381) --- packages/kbn-doc-links/src/get_doc_links.ts | 2 +- .../trained_models/models_management/models_list.tsx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/kbn-doc-links/src/get_doc_links.ts b/packages/kbn-doc-links/src/get_doc_links.ts index ee2fb5143e92b..67bfabcbd0984 100644 --- a/packages/kbn-doc-links/src/get_doc_links.ts +++ b/packages/kbn-doc-links/src/get_doc_links.ts @@ -396,7 +396,7 @@ export const getDocLinks = ({ kibanaBranch }: GetDocLinkOptions): DocLinks => { classificationAucRoc: `${ELASTIC_WEBSITE_URL}guide/en/machine-learning/${DOC_LINK_VERSION}/ml-dfa-classification.html#ml-dfanalytics-class-aucroc`, setUpgradeMode: `${ELASTICSEARCH_DOCS}ml-set-upgrade-mode.html`, trainedModels: `${ELASTIC_WEBSITE_URL}guide/en/machine-learning/${DOC_LINK_VERSION}/ml-trained-models.html`, - startTrainedModelsDeploymentQueryParams: `${ELASTIC_WEBSITE_URL}guide/en/elasticsearch/reference/${DOC_LINK_VERSION}/start-trained-model-deployment.html#start-trained-model-deployment-query-params`, + startTrainedModelsDeployment: `${ELASTIC_WEBSITE_URL}guide/en/machine-learning/${DOC_LINK_VERSION}/ml-nlp-deploy-models.html#ml-nlp-deploy-model`, }, transforms: { guide: `${ELASTICSEARCH_DOCS}transforms.html`, diff --git a/x-pack/plugins/ml/public/application/trained_models/models_management/models_list.tsx b/x-pack/plugins/ml/public/application/trained_models/models_management/models_list.tsx index c8143a5c283e4..0c8f1aec7d97d 100644 --- a/x-pack/plugins/ml/public/application/trained_models/models_management/models_list.tsx +++ b/x-pack/plugins/ml/public/application/trained_models/models_management/models_list.tsx @@ -94,7 +94,7 @@ export const ModelsList: FC = ({ } = useMlKibana(); const urlLocator = useMlLocator()!; - const startModelDeploymentDocUrl = docLinks.links.ml.startTrainedModelsDeploymentQueryParams; + const startModelDeploymentDocUrl = docLinks.links.ml.startTrainedModelsDeployment; useTimefilter({ timeRangeSelector: false, autoRefreshSelector: true }); From 26ce11cb2c5b85c95225eceb2539a8921d06145d Mon Sep 17 00:00:00 2001 From: Rickyanto Ang Date: Thu, 14 Jul 2022 12:04:53 -0700 Subject: [PATCH 044/111] [8.4][Kubernetes Security]Kubernetes widget Container Images Session (#134972) * base commit for container name session widget * Cleaned up + implemented suggestions from Jack and Paulo * Used Datagrid instead of table for this widget, TODO: Fix TS error ,styling fixes, Unit test * some clean up * [CI] Auto-commit changed files from 'node scripts/precommit_hook.js --ref HEAD~1..HEAD --fix' * some CSS updates * [CI] Auto-commit changed files from 'node scripts/precommit_hook.js --ref HEAD~1..HEAD --fix' * WIP, need to add infinite scroll * [CI] Auto-commit changed files from 'node scripts/eslint --no-cache --fix' * added infinite scroll, TODO: cleanup + Unit test * [CI] Auto-commit changed files from 'node scripts/eslint --no-cache --fix' * added Unit test * updated aggregate.ts * moved rendering filter button logic to another another component to prevent rerendering entire table * fixing CI failures * attempt to fix CI failures * more fixes for Check Types failure * undefined error fix? * more Check Types failure fixes * updated type in percent widget * addressed PR comments + added unit test for helper component * moved helper unit test to its own file, added loading progress bar * [CI] Auto-commit changed files from 'node scripts/eslint --no-cache --fix' * addressing PR comments * fetched latest main and added paulo's fix to aggregate route test * [CI] Auto-commit changed files from 'node scripts/precommit_hook.js --ref HEAD~1..HEAD --fix' * more pr comments * removed unused variable, updated aggregate route to match paulo branch * addressing PR comments * PR comments * Fix widgets spacing * correcting typo * Update widgets group min widths Co-authored-by: kibanamachine <42973632+kibanamachine@users.noreply.github.com> Co-authored-by: Jack --- .../kubernetes_security/common/constants.ts | 1 + .../common/translations.ts | 21 ++ .../common/types/aggregate/index.ts | 16 +- .../container_name_row.test.tsx | 43 ++++ .../container_name_row.tsx | 46 ++++ .../components/container_name_widget/hooks.ts | 56 +++++ .../container_name_widget/index.test.tsx | 135 +++++++++++ .../container_name_widget/index.tsx | 226 ++++++++++++++++++ .../container_name_widget/styles.ts | 62 +++++ .../public/components/count_widget/styles.ts | 1 + .../kubernetes_security_routes/index.test.tsx | 4 + .../kubernetes_security_routes/index.tsx | 37 +-- .../kubernetes_security_routes/styles.ts | 35 ++- .../public/components/percent_widget/hooks.ts | 34 +-- .../components/percent_widget/index.tsx | 2 +- .../kubernetes_security/public/hooks/index.ts | 1 + .../public/hooks/use_scroll.ts | 51 ++++ .../server/routes/aggregate.ts | 34 ++- .../basic/tests/aggregate.ts | 21 +- 19 files changed, 759 insertions(+), 67 deletions(-) create mode 100644 x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.test.tsx create mode 100644 x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.tsx create mode 100644 x-pack/plugins/kubernetes_security/public/components/container_name_widget/hooks.ts create mode 100644 x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.test.tsx create mode 100644 x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.tsx create mode 100644 x-pack/plugins/kubernetes_security/public/components/container_name_widget/styles.ts create mode 100644 x-pack/plugins/kubernetes_security/public/hooks/use_scroll.ts diff --git a/x-pack/plugins/kubernetes_security/common/constants.ts b/x-pack/plugins/kubernetes_security/common/constants.ts index 625946b99a123..ce9497285f0c6 100644 --- a/x-pack/plugins/kubernetes_security/common/constants.ts +++ b/x-pack/plugins/kubernetes_security/common/constants.ts @@ -20,6 +20,7 @@ export const AGGREGATE_MAX_BUCKETS = 2000; // react-query caching keys export const QUERY_KEY_PERCENT_WIDGET = 'kubernetesSecurityPercentWidget'; export const QUERY_KEY_COUNT_WIDGET = 'kubernetesSecurityCountWidget'; +export const QUERY_KEY_CONTAINER_NAME_WIDGET = 'kubernetesSecurityContainerNameWidget'; export const DEFAULT_QUERY = '{"bool":{"must":[],"filter":[],"should":[],"must_not":[]}}'; diff --git a/x-pack/plugins/kubernetes_security/common/translations.ts b/x-pack/plugins/kubernetes_security/common/translations.ts index 0264be3e55bd5..7c139e88a0759 100644 --- a/x-pack/plugins/kubernetes_security/common/translations.ts +++ b/x-pack/plugins/kubernetes_security/common/translations.ts @@ -58,3 +58,24 @@ export const COUNT_WIDGET_CONTAINER_IMAGES = i18n.translate( defaultMessage: 'Container Images', } ); + +export const CONTAINER_NAME_SESSION = i18n.translate( + 'xpack.kubernetesSecurity.containerNameWidget.containerImage', + { + defaultMessage: 'Container Images Session', + } +); + +export const CONTAINER_NAME_SESSION_COUNT_COLUMN = i18n.translate( + 'xpack.kubernetesSecurity.containerNameWidget.containerImageCountColumn', + { + defaultMessage: 'Count', + } +); + +export const CONTAINER_NAME_SESSION_ARIA_LABEL = i18n.translate( + 'xpack.kubernetesSecurity.containerNameWidget.containerImageAriaLabel', + { + defaultMessage: 'Container Name Session Widget', + } +); diff --git a/x-pack/plugins/kubernetes_security/common/types/aggregate/index.ts b/x-pack/plugins/kubernetes_security/common/types/aggregate/index.ts index 70747aa8e878d..57a1df44292e9 100644 --- a/x-pack/plugins/kubernetes_security/common/types/aggregate/index.ts +++ b/x-pack/plugins/kubernetes_security/common/types/aggregate/index.ts @@ -5,11 +5,23 @@ * 2.0. */ -export interface AggregateResult { +interface Aggregate { key: string | number; - key_as_string?: string; doc_count: number; +} + +interface Buckets extends Aggregate { + key_as_string?: string; count_by_aggs: { value: number; }; } +export interface AggregateResult { + buckets: Buckets[]; + hasNextPage: boolean; +} + +export interface AggregateBucketPaginationResult { + buckets: Aggregate[]; + hasNextPage: boolean; +} diff --git a/x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.test.tsx b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.test.tsx new file mode 100644 index 0000000000000..8691288bd7c7a --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.test.tsx @@ -0,0 +1,43 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { AppContextTestRender, createAppRootMockRenderer } from '../../test'; +import { ContainerNameRow } from './container_name_row'; +import { fireEvent } from '@testing-library/react'; + +const TEST_NAME = 'TEST ROW'; +const TEST_BUTTON_FILTER =

    Filter In
    ; +const TEST_BUTTON_FILTER_OUT =
    Filter Out
    ; + +describe('ContainerNameRow component with valid row', () => { + let renderResult: ReturnType; + const mockedContext = createAppRootMockRenderer(); + const render: () => ReturnType = () => + (renderResult = mockedContext.render( + + )); + + it('should show the row element as well as the pop up filter button when mouse hovers above it', async () => { + render(); + expect(renderResult.getByText(TEST_NAME)).toBeVisible(); + fireEvent.mouseOver(renderResult.queryByText(TEST_NAME)!); + expect(renderResult.getByText('Filter In')).toBeVisible(); + expect(renderResult.getByText('Filter Out')).toBeVisible(); + }); + + it('should show the row element but not the pop up filter button outside mouse hover', async () => { + render(); + expect(renderResult.getByText(TEST_NAME)).toBeVisible(); + expect(renderResult.queryByText('Filter In')).toBeFalsy(); + expect(renderResult.queryByText('Filter Out')).toBeFalsy(); + }); +}); diff --git a/x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.tsx b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.tsx new file mode 100644 index 0000000000000..50bb4504f5d6d --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/container_name_row.tsx @@ -0,0 +1,46 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React, { ReactNode, useState } from 'react'; +import { EuiFlexItem, EuiText } from '@elastic/eui'; +import { useStyles } from './styles'; + +export interface ContainerNameRowDeps { + name: string; + filterButtonIn?: ReactNode; + filterButtonOut?: ReactNode; +} + +export const ROW_TEST_ID = 'kubernetesSecurity:containerNameSessionRow'; + +export const ContainerNameRow = ({ + name, + filterButtonIn, + filterButtonOut, +}: ContainerNameRowDeps) => { + const [isHover, setIsHover] = useState(false); + + const styles = useStyles(); + + return ( + setIsHover(true)} + onMouseLeave={() => setIsHover(false)} + data-test-subj={ROW_TEST_ID} + > + + {name} + {isHover && ( +
    + {filterButtonIn} + {filterButtonOut} +
    + )} +
    +
    + ); +}; diff --git a/x-pack/plugins/kubernetes_security/public/components/container_name_widget/hooks.ts b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/hooks.ts new file mode 100644 index 0000000000000..66dcbc5b50265 --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/hooks.ts @@ -0,0 +1,56 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useInfiniteQuery } from 'react-query'; +import { CoreStart } from '@kbn/core/public'; +import { useKibana } from '@kbn/kibana-react-plugin/public'; +import { QUERY_KEY_CONTAINER_NAME_WIDGET, AGGREGATE_ROUTE } from '../../../common/constants'; +import { AggregateResult } from '../../../common/types/aggregate'; + +export const useFetchContainerNameData = ( + filterQuery: string, + widgetKey: string, + groupBy: string, + countBy?: string, + index?: string, + sortByCount?: string, + pageNumber?: number +) => { + const { http } = useKibana().services; + const cachingKeys = [ + QUERY_KEY_CONTAINER_NAME_WIDGET, + widgetKey, + filterQuery, + groupBy, + countBy, + sortByCount, + pageNumber, + ]; + const query = useInfiniteQuery( + cachingKeys, + async ({ pageParam = 0 }) => { + const res = await http.get(AGGREGATE_ROUTE, { + query: { + query: filterQuery, + groupBy, + countBy, + page: pageParam, + index, + sortByCount, + }, + }); + return res; + }, + { + refetchOnWindowFocus: false, + refetchOnMount: false, + refetchOnReconnect: false, + getNextPageParam: (lastPage, pages) => (lastPage.hasNextPage ? pages.length : undefined), + } + ); + return query; +}; diff --git a/x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.test.tsx b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.test.tsx new file mode 100644 index 0000000000000..bdafb47a8b246 --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.test.tsx @@ -0,0 +1,135 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { ENTRY_LEADER_ENTITY_ID, CONTAINER_IMAGE_NAME } from '../../../common/constants'; +import { AppContextTestRender, createAppRootMockRenderer } from '../../test'; +import { GlobalFilter } from '../../types'; +import { + ContainerNameWidget, + LOADING_TEST_ID, + NAME_COLUMN_TEST_ID, + COUNT_COLUMN_TEST_ID, + CONTAINER_NAME_TABLE_TEST_ID, +} from '.'; +import { useFetchContainerNameData } from './hooks'; +import { ROW_TEST_ID } from './container_name_row'; + +const TABLE_SORT_BUTTON_ID = 'tableHeaderSortButton'; + +const TITLE = 'Container Images Session'; +const GLOBAL_FILTER: GlobalFilter = { + endDate: '2022-06-15T14:15:25.777Z', + filterQuery: '{"bool":{"must":[],"filter":[],"should":[],"must_not":[]}}', + startDate: '2022-05-15T14:15:25.777Z', +}; +const MOCK_DATA = { + pages: [ + { + buckets: [ + { key: 'Container A', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container B', doc_count: 295, count_by_aggs: { value: 3 } }, + { key: 'Container C', doc_count: 295, count_by_aggs: { value: 2 } }, + { key: 'Container D', doc_count: 295, count_by_aggs: { value: 4 } }, + { key: 'Container E', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container F', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container G', doc_count: 295, count_by_aggs: { value: 0 } }, + { key: 'Container H', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container J', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container K', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container L', doc_count: 295, count_by_aggs: { value: 5 } }, + ], + hasNextPage: true, + }, + { + buckets: [ + { key: 'Container A2', doc_count: 295, count_by_aggs: { value: 2 } }, + { key: 'Container B2', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container C2', doc_count: 295, count_by_aggs: { value: 6 } }, + { key: 'Container D2', doc_count: 295, count_by_aggs: { value: 1 } }, + { key: 'Container E2', doc_count: 295, count_by_aggs: { value: 3 } }, + { key: 'Container F2', doc_count: 295, count_by_aggs: { value: 1 } }, + ], + hasNextPage: false, + }, + ], + pageParams: [undefined], +}; + +jest.mock('../../hooks/use_filter', () => ({ + useSetFilter: () => ({ + getFilterForValueButton: jest.fn(), + getFilterOutValueButton: jest.fn(), + filterManager: {}, + }), +})); + +jest.mock('./hooks'); +const mockUseFetchData = useFetchContainerNameData as jest.Mock; + +describe('ContainerNameWidget component', () => { + let renderResult: ReturnType; + const mockedContext = createAppRootMockRenderer(); + const render: () => ReturnType = () => + (renderResult = mockedContext.render( + + )); + + describe('When ContainerNameWidget is mounted', () => { + describe('with data', () => { + beforeEach(() => { + mockUseFetchData.mockImplementation(() => ({ + data: MOCK_DATA, + isFetchingNextPage: true, + })); + }); + + it('should show the table, table title, table columns, sort button', async () => { + render(); + expect(renderResult.queryByTestId(CONTAINER_NAME_TABLE_TEST_ID)).toBeVisible(); + expect(renderResult.queryAllByTestId(TABLE_SORT_BUTTON_ID)).toHaveLength(1); + expect(renderResult.queryAllByTestId(NAME_COLUMN_TEST_ID)).toHaveLength(17); + expect(renderResult.queryAllByTestId(COUNT_COLUMN_TEST_ID)).toHaveLength(17); + }); + + it('should show data value names and value', async () => { + render(); + expect(renderResult.queryAllByTestId(ROW_TEST_ID)).toHaveLength(17); + }); + }); + + describe('without data ', () => { + it('should show no items found text', async () => { + mockUseFetchData.mockImplementation(() => ({ + data: undefined, + isFetchingNextPage: false, + })); + render(); + expect(renderResult.getByText(TITLE)).toBeVisible(); + expect(renderResult.getByText('No items found')).toBeVisible(); + expect(renderResult.getByTestId(CONTAINER_NAME_TABLE_TEST_ID)).toBeVisible(); + }); + }); + + describe('when loading data', () => { + it('should show progress bar', async () => { + mockUseFetchData.mockImplementation(() => ({ + data: MOCK_DATA, + isFetchingNextPage: false, + isLoading: true, + })); + render(); + expect(renderResult.getByTestId(LOADING_TEST_ID)).toBeVisible(); + }); + }); + }); +}); diff --git a/x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.tsx b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.tsx new file mode 100644 index 0000000000000..15f3727efa660 --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/index.tsx @@ -0,0 +1,226 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React, { ReactNode, useMemo, useState, useRef, useCallback } from 'react'; +import { EuiBasicTable, EuiTableSortingType, EuiProgress, EuiBasicTableColumn } from '@elastic/eui'; +import { useStyles } from './styles'; +import { ContainerNameRow } from './container_name_row'; +import type { IndexPattern, GlobalFilter } from '../../types'; +import { useSetFilter, useScroll } from '../../hooks'; +import { addTimerangeToQuery } from '../../utils/add_timerange_to_query'; +import { useFetchContainerNameData } from './hooks'; +import { CONTAINER_IMAGE_NAME } from '../../../common/constants'; +import { + CONTAINER_NAME_SESSION, + CONTAINER_NAME_SESSION_COUNT_COLUMN, + CONTAINER_NAME_SESSION_ARIA_LABEL, +} from '../../../common/translations'; + +export const LOADING_TEST_ID = 'kubernetesSecurity:containerNameWidgetLoading'; +export const NAME_COLUMN_TEST_ID = 'kubernetesSecurity:containerImageNameSessionNameColumn'; +export const COUNT_COLUMN_TEST_ID = 'kubernetesSecurity:containerImageNameSessionCountColumn'; +export const CONTAINER_NAME_TABLE_TEST_ID = 'kubernetesSecurity:containerNameSessionTable'; + +export interface ContainerNameWidgetDataValueMap { + key: string; + doc_count: number; + count_by_aggs: { + value: number; + }; +} + +export interface ContainerNameArrayDataValue { + name: string; + count: number; +} + +export interface ContainerNameWidgetDeps { + widgetKey: string; + indexPattern?: IndexPattern; + globalFilter: GlobalFilter; + groupedBy: string; + countBy?: string; +} + +interface FilterButtons { + filterForButtons: ReactNode[]; + filterOutButtons: ReactNode[]; +} + +export const ContainerNameWidget = ({ + widgetKey, + indexPattern, + globalFilter, + groupedBy, + countBy, +}: ContainerNameWidgetDeps) => { + const [sortField, setSortField] = useState('count'); + const [sortDirection, setSortDirection] = useState('desc'); + const styles = useStyles(); + + const filterQueryWithTimeRange = useMemo(() => { + return addTimerangeToQuery( + globalFilter.filterQuery, + globalFilter.startDate, + globalFilter.endDate + ); + }, [globalFilter.filterQuery, globalFilter.startDate, globalFilter.endDate]); + + const { data, fetchNextPage, isFetchingNextPage, isLoading } = useFetchContainerNameData( + filterQueryWithTimeRange, + widgetKey, + groupedBy, + countBy, + indexPattern?.title, + sortDirection + ); + + const onTableChange = useCallback(({ sort = {} }) => { + // @ts-ignore + const { field: sortingField, direction: sortingDirection } = sort; + + setSortField(sortingField); + setSortDirection(sortingDirection); + }, []); + + const sorting: EuiTableSortingType = { + sort: { + field: sortField as keyof ContainerNameArrayDataValue, + direction: sortDirection as 'desc' | 'asc', + }, + enableAllColumns: true, + }; + + const { getFilterForValueButton, getFilterOutValueButton, filterManager } = useSetFilter(); + const filterButtons = useMemo((): FilterButtons => { + const result: FilterButtons = { + filterForButtons: + data?.pages + ?.map((aggsData) => { + return aggsData?.buckets.map((aggData) => { + return getFilterForValueButton({ + field: CONTAINER_IMAGE_NAME, + filterManager, + size: 'xs', + onClick: () => {}, + onFilterAdded: () => {}, + ownFocus: false, + showTooltip: true, + value: aggData.key as string, + }); + }); + }) + .flat() || [], + + filterOutButtons: + data?.pages + ?.map((aggsData) => { + return aggsData?.buckets.map((aggData) => { + return getFilterOutValueButton({ + field: CONTAINER_IMAGE_NAME, + filterManager, + size: 'xs', + onClick: () => {}, + onFilterAdded: () => {}, + ownFocus: false, + showTooltip: true, + value: aggData.key as string, + }); + }); + }) + .flat() || [], + }; + return result; + }, [data, getFilterForValueButton, getFilterOutValueButton, filterManager]); + + const containerNameArray = useMemo((): ContainerNameArrayDataValue[] => { + return data + ? data?.pages + ?.map((aggsData) => { + return aggsData?.buckets.map((aggData) => { + return { + name: aggData.key as string, + count: aggData.count_by_aggs.value, + }; + }); + }) + .flat() + : []; + }, [data]); + + const columns = useMemo((): Array> => { + return [ + { + field: 'name', + name: CONTAINER_NAME_SESSION, + 'data-test-subj': NAME_COLUMN_TEST_ID, + render: (name: string) => { + const indexHelper = containerNameArray.findIndex((obj) => { + return obj.name === name; + }); + + return ( + + ); + }, + align: 'left', + width: '74%', + sortable: false, + }, + { + field: 'count', + name: CONTAINER_NAME_SESSION_COUNT_COLUMN, + width: '26%', + 'data-test-subj': COUNT_COLUMN_TEST_ID, + render: (count: number) => { + return {count}; + }, + sortable: true, + align: 'right', + }, + ]; + }, [filterButtons.filterForButtons, filterButtons.filterOutButtons, containerNameArray, styles]); + + const scrollerRef = useRef(null); + useScroll({ + div: scrollerRef.current, + handler: (pos: number, endReached: boolean) => { + if (!isFetchingNextPage && endReached) { + fetchNextPage(); + } + }, + }); + + return ( +
    + {isLoading && ( + + )} + +
    + ); +}; diff --git a/x-pack/plugins/kubernetes_security/public/components/container_name_widget/styles.ts b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/styles.ts new file mode 100644 index 0000000000000..7e676b3e03445 --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/components/container_name_widget/styles.ts @@ -0,0 +1,62 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useMemo } from 'react'; +import { CSSObject } from '@emotion/react'; +import { transparentize } from '@elastic/eui'; +import { useEuiTheme } from '../../hooks'; + +export const useStyles = () => { + const { euiTheme } = useEuiTheme(); + + const cached = useMemo(() => { + const { size, font, colors } = euiTheme; + + const container: CSSObject = { + padding: size.base, + border: euiTheme.border.thin, + borderRadius: euiTheme.border.radius.medium, + overflow: 'auto', + height: '100%', + minHeight: '250px', + position: 'relative', + marginBottom: size.l, + }; + + const dataInfo: CSSObject = { + marginBottom: size.xs, + display: 'flex', + alignItems: 'center', + height: size.l, + position: 'relative', + }; + + const filters: CSSObject = { + marginLeft: size.s, + position: 'absolute', + left: '50%', + backgroundColor: colors.emptyShade, + borderRadius: euiTheme.border.radius.small, + border: euiTheme.border.thin, + bottom: '-25px', + boxShadow: `0 ${size.xs} ${size.xs} ${transparentize(euiTheme.colors.shadow, 0.04)}`, + }; + + const countValue: CSSObject = { + fontWeight: font.weight.semiBold, + }; + + return { + container, + dataInfo, + filters, + countValue, + }; + }, [euiTheme]); + + return cached; +}; diff --git a/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts b/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts index b02f30fa952fa..adea8ee704c97 100644 --- a/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts +++ b/x-pack/plugins/kubernetes_security/public/components/count_widget/styles.ts @@ -21,6 +21,7 @@ export const useStyles = () => { borderRadius: border.radius.medium, overflow: 'auto', position: 'relative', + height: '100%', }; const title: CSSObject = { diff --git a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.test.tsx b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.test.tsx index 5399975091420..ea9b8b11da891 100644 --- a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.test.tsx +++ b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.test.tsx @@ -25,6 +25,10 @@ jest.mock('../count_widget', () => ({ CountWidget: () =>
    {'Mock count widget'}
    , })); +jest.mock('../container_name_widget', () => ({ + ContainerNameWidget: () =>
    {'Mock Container Name widget'}
    , +})); + const renderWithRouter = ( initialEntries: MemoryRouterProps['initialEntries'] = ['/kubernetes'] ) => { diff --git a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx index 7be342a782d98..6387c7e961f9c 100644 --- a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx +++ b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/index.tsx @@ -44,6 +44,7 @@ import { COUNT_WIDGET_PODS, COUNT_WIDGET_CONTAINER_IMAGES, } from '../../../common/translations'; +import { ContainerNameWidget } from '../container_name_widget'; const KubernetesSecurityRoutesComponent = ({ filter, @@ -59,8 +60,8 @@ const KubernetesSecurityRoutesComponent = ({ const lastUpdated = useLastUpdated(globalFilter); const onReduceInteractiveAggs = useCallback( - (result: AggregateResult[]): Record => - result.reduce((groupedByKeyValue, aggregate) => { + (result: AggregateResult): Record => + result.buckets.reduce((groupedByKeyValue, aggregate) => { groupedByKeyValue[aggregate.key_as_string || (aggregate.key.toString() as string)] = aggregate.count_by_aggs.value; return groupedByKeyValue; @@ -69,9 +70,9 @@ const KubernetesSecurityRoutesComponent = ({ ); const onReduceRootAggs = useCallback( - (result: AggregateResult[]): Record => - result.reduce((groupedByKeyValue, aggregate) => { - if (aggregate.key === '0') { + (result: AggregateResult): Record => + result.buckets.reduce((groupedByKeyValue, aggregate) => { + if (aggregate.key.toString() === '0') { groupedByKeyValue[aggregate.key] = aggregate.count_by_aggs.value; } else { groupedByKeyValue.nonRoot = @@ -106,9 +107,9 @@ const KubernetesSecurityRoutesComponent = ({ {!shouldHideCharts && ( <> - - - + + + - - + + @@ -208,7 +209,7 @@ const KubernetesSecurityRoutesComponent = ({ onReduce={onReduceInteractiveAggs} /> - + @@ -257,12 +258,14 @@ const KubernetesSecurityRoutesComponent = ({ - - - -
    PlaceHolder for Container Name Widget
    -
    -
    + +
    diff --git a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts index 49e41b4cbca38..aa35cd8a22a4f 100644 --- a/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts +++ b/x-pack/plugins/kubernetes_security/public/components/kubernetes_security_routes/styles.ts @@ -48,8 +48,26 @@ export const useStyles = () => { height: '500px', }; - const percentageWidgets: CSSObject = { - marginBottom: size.l, + const widgetsBottomSpacing: CSSObject = { + marginBottom: size.m, + }; + + const noBottomSpacing: CSSObject = { + marginBottom: 0, + }; + + const countWidgetsGroup: CSSObject = { + ...widgetsBottomSpacing, + flexWrap: 'wrap', + }; + + const leftWidgetsGroup: CSSObject = { + ...noBottomSpacing, + minWidth: `calc(70% - ${size.xxxl})`, + }; + + const rightWidgetsGroup: CSSObject = { + minWidth: '30%', }; const percentageChartTitle: CSSObject = { @@ -58,16 +76,10 @@ export const useStyles = () => { fontWeight: font.weight.bold, }; - const countWidgets: CSSObject = { - marginBottom: size.l, - }; - const widgetHolder: CSSObject = { position: 'relative', width: '332px', height: '235px', - padding: size.base, - border: border.thin, borderRadius: border.radius.medium, fontWeight: font.weight.bold, fontSize: size.m, @@ -80,9 +92,12 @@ export const useStyles = () => { updatedAt, widgetBadge, treeViewContainer, - percentageWidgets, + countWidgetsGroup, + leftWidgetsGroup, + rightWidgetsGroup, + widgetsBottomSpacing, percentageChartTitle, - countWidgets, + noBottomSpacing, widgetHolder, }; }, [euiTheme]); diff --git a/x-pack/plugins/kubernetes_security/public/components/percent_widget/hooks.ts b/x-pack/plugins/kubernetes_security/public/components/percent_widget/hooks.ts index decdb0c6e27a9..f13cdfa0ac7a4 100644 --- a/x-pack/plugins/kubernetes_security/public/components/percent_widget/hooks.ts +++ b/x-pack/plugins/kubernetes_security/public/components/percent_widget/hooks.ts @@ -11,7 +11,7 @@ import { QUERY_KEY_PERCENT_WIDGET, AGGREGATE_ROUTE } from '../../../common/const import { AggregateResult } from '../../../common/types/aggregate'; export const useFetchPercentWidgetData = ( - onReduce: (result: AggregateResult[]) => Record, + onReduce: (result: AggregateResult) => Record, filterQuery: string, widgetKey: string, groupBy: string, @@ -20,27 +20,19 @@ export const useFetchPercentWidgetData = ( ) => { const { http } = useKibana().services; const cachingKeys = [QUERY_KEY_PERCENT_WIDGET, widgetKey, filterQuery, groupBy, countBy, index]; - const query = useQuery( - cachingKeys, - async (): Promise> => { - const res = await http.get(AGGREGATE_ROUTE, { - query: { - query: filterQuery, - groupBy, - countBy, - page: 0, - index, - }, - }); + const query = useQuery(cachingKeys, async (): Promise> => { + const res = await http.get(AGGREGATE_ROUTE, { + query: { + query: filterQuery, + groupBy, + countBy, + page: 0, + index, + }, + }); - return onReduce(res); - }, - { - refetchOnWindowFocus: false, - refetchOnMount: false, - refetchOnReconnect: false, - } - ); + return onReduce(res); + }); return query; }; diff --git a/x-pack/plugins/kubernetes_security/public/components/percent_widget/index.tsx b/x-pack/plugins/kubernetes_security/public/components/percent_widget/index.tsx index 0c3cb3da9c5a8..21c068978a345 100644 --- a/x-pack/plugins/kubernetes_security/public/components/percent_widget/index.tsx +++ b/x-pack/plugins/kubernetes_security/public/components/percent_widget/index.tsx @@ -32,7 +32,7 @@ export interface PercentWidgetDeps { globalFilter: GlobalFilter; groupedBy: string; countBy?: string; - onReduce: (result: AggregateResult[]) => Record; + onReduce: (result: AggregateResult) => Record; } interface FilterButtons { diff --git a/x-pack/plugins/kubernetes_security/public/hooks/index.ts b/x-pack/plugins/kubernetes_security/public/hooks/index.ts index 14d956be9b629..2e330dfb1b159 100644 --- a/x-pack/plugins/kubernetes_security/public/hooks/index.ts +++ b/x-pack/plugins/kubernetes_security/public/hooks/index.ts @@ -8,3 +8,4 @@ export { useEuiTheme } from './use_eui_theme'; export { useSetFilter } from './use_filter'; export { useLastUpdated } from './use_last_updated'; +export { useScroll } from './use_scroll'; diff --git a/x-pack/plugins/kubernetes_security/public/hooks/use_scroll.ts b/x-pack/plugins/kubernetes_security/public/hooks/use_scroll.ts new file mode 100644 index 0000000000000..716e35dbb0987 --- /dev/null +++ b/x-pack/plugins/kubernetes_security/public/hooks/use_scroll.ts @@ -0,0 +1,51 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useEffect } from 'react'; +import _ from 'lodash'; + +const SCROLL_END_BUFFER_HEIGHT = 20; +const DEBOUNCE_TIMEOUT = 500; + +function getScrollPosition(div: HTMLElement) { + if (div) { + return div.scrollTop; + } else { + return document.documentElement.scrollTop || document.body.scrollTop; + } +} + +interface IUseScrollDeps { + div: HTMLElement | null; + handler(pos: number, endReached: boolean): void; +} + +/** + * listens to scroll events on given div, if scroll reaches bottom, calls a callback + * @param {ref} ref to listen to scroll events on + * @param {function} handler function receives params (scrollTop, endReached) + */ +export function useScroll({ div, handler }: IUseScrollDeps) { + useEffect(() => { + if (div) { + const debounced = _.debounce(() => { + const pos = getScrollPosition(div); + const endReached = pos + div.offsetHeight > div.scrollHeight - SCROLL_END_BUFFER_HEIGHT; + + handler(pos, endReached); + }, DEBOUNCE_TIMEOUT); + + div.onscroll = debounced; + + return () => { + debounced.cancel(); + + div.onscroll = null; + }; + } + }, [div, handler]); +} diff --git a/x-pack/plugins/kubernetes_security/server/routes/aggregate.ts b/x-pack/plugins/kubernetes_security/server/routes/aggregate.ts index 252b20a458a78..e56a17d89845f 100644 --- a/x-pack/plugins/kubernetes_security/server/routes/aggregate.ts +++ b/x-pack/plugins/kubernetes_security/server/routes/aggregate.ts @@ -14,6 +14,7 @@ import { AGGREGATE_PAGE_SIZE, AGGREGATE_MAX_BUCKETS, } from '../../common/constants'; +import { AggregateBucketPaginationResult } from '../../common/types/aggregate'; // sort by values const ASC = 'asc'; @@ -29,6 +30,7 @@ export const registerAggregateRoute = (router: IRouter) => { countBy: schema.maybe(schema.string()), groupBy: schema.string(), page: schema.number(), + perPage: schema.maybe(schema.number()), index: schema.maybe(schema.string()), sortByCount: schema.maybe(schema.string()), }), @@ -36,10 +38,19 @@ export const registerAggregateRoute = (router: IRouter) => { }, async (context, request, response) => { const client = (await context.core).elasticsearch.client.asCurrentUser; - const { query, countBy, sortByCount, groupBy, page, index } = request.query; + const { query, countBy, sortByCount, groupBy, page, perPage, index } = request.query; try { - const body = await doSearch(client, query, groupBy, page, index, countBy, sortByCount); + const body = await doSearch( + client, + query, + groupBy, + page, + perPage, + index, + countBy, + sortByCount + ); return response.ok({ body }); } catch (err) { @@ -54,10 +65,11 @@ export const doSearch = async ( query: string, groupBy: string, page: number, // zero based + perPage = AGGREGATE_PAGE_SIZE, index?: string, countBy?: string, sortByCount?: string -) => { +): Promise => { const queryDSL = JSON.parse(query); const countByAggs = countBy @@ -91,8 +103,8 @@ export const doSearch = async ( bucket_sort: { bucket_sort: { sort: [sort], // defaulting to alphabetic sort - size: AGGREGATE_PAGE_SIZE, - from: AGGREGATE_PAGE_SIZE * page, + size: perPage + 1, // check if there's a "next page" + from: perPage * page, }, }, }, @@ -102,6 +114,16 @@ export const doSearch = async ( }); const agg: any = search.aggregations?.custom_agg; + const buckets = agg?.buckets || []; - return agg?.buckets || []; + const hasNextPage = buckets.length > perPage; + + if (hasNextPage) { + buckets.pop(); + } + + return { + buckets, + hasNextPage, + }; }; diff --git a/x-pack/test/kubernetes_security/basic/tests/aggregate.ts b/x-pack/test/kubernetes_security/basic/tests/aggregate.ts index c1501c97e77e5..92d6da4655cf4 100644 --- a/x-pack/test/kubernetes_security/basic/tests/aggregate.ts +++ b/x-pack/test/kubernetes_security/basic/tests/aggregate.ts @@ -42,12 +42,13 @@ export default function aggregateTests({ getService }: FtrProviderContext) { groupBy: ORCHESTRATOR_NAMESPACE_PROPERTY, page: 0, index: MOCK_INDEX, + perPage: 10, }); expect(response.status).to.be(200); - expect(response.body.length).to.be(10); + expect(response.body.buckets.length).to.be(10); namespaces.forEach((namespace, i) => { - expect(response.body[i].key).to.be(namespace); + expect(response.body.buckets[i].key).to.be(namespace); }); }); @@ -62,8 +63,8 @@ export default function aggregateTests({ getService }: FtrProviderContext) { index: MOCK_INDEX, }); expect(response.status).to.be(200); - expect(response.body.length).to.be(1); - expect(response.body[0].key).to.be('namespace11'); + expect(response.body.buckets.length).to.be(1); + expect(response.body.buckets[0].key).to.be('namespace11'); }); it(`${AGGREGATE_ROUTE} return countBy value for each aggregation`, async () => { @@ -78,10 +79,10 @@ export default function aggregateTests({ getService }: FtrProviderContext) { index: MOCK_INDEX, }); expect(response.status).to.be(200); - expect(response.body.length).to.be(10); + expect(response.body.buckets.length).to.be(10); // when groupBy and countBy use the same field, count_by_aggs.value will always be 1 - response.body.forEach((agg: any) => { + response.body.buckets.forEach((agg: any) => { expect(agg.count_by_aggs.value).to.be(1); }); }); @@ -99,9 +100,9 @@ export default function aggregateTests({ getService }: FtrProviderContext) { sortByCount: 'desc', }); expect(response.status).to.be(200); - expect(response.body.length).to.be(10); - expect(response.body[0].count_by_aggs.value).to.be(2); - expect(response.body[1].count_by_aggs.value).to.be(1); + expect(response.body.buckets.length).to.be(10); + expect(response.body.buckets[0].count_by_aggs.value).to.be(2); + expect(response.body.buckets[1].count_by_aggs.value).to.be(1); }); it(`${AGGREGATE_ROUTE} allows a range query`, async () => { @@ -122,7 +123,7 @@ export default function aggregateTests({ getService }: FtrProviderContext) { index: MOCK_INDEX, }); expect(response.status).to.be(200); - expect(response.body.length).to.be(3); + expect(response.body.buckets.length).to.be(3); }); it(`${AGGREGATE_ROUTE} handles a bad request`, async () => { From 33b743c84e9d27e6a0234ebea85964ce0ddefb24 Mon Sep 17 00:00:00 2001 From: Jonathan Budzenski Date: Thu, 14 Jul 2022 14:53:12 -0500 Subject: [PATCH 045/111] Revert "Remove percy based visual regression tests (#136359)" (#136437) * Revert "Remove percy based visual regression tests (#136359)" This reverts commit a91aeb42ffef8d34f1fa0c8af81877e9dfa7f66a. * update codeowners --- .buildkite/ftr_configs.yml | 2 + .eslintrc.js | 1 + .github/CODEOWNERS | 3 + package.json | 1 + packages/kbn-pm/dist/index.js | 88 ++-- test/visual_regression/config.ts | 30 ++ .../visual_regression/ftr_provider_context.ts | 15 + test/visual_regression/services/index.ts | 15 + .../services/visual_testing/index.ts | 9 + .../visual_testing/take_percy_snapshot.js | 102 +++++ .../services/visual_testing/visual_testing.ts | 114 +++++ test/visual_regression/tests/console_app.ts | 71 +++ .../tests/discover/chart_visualization.ts | 117 +++++ .../visual_regression/tests/discover/index.ts | 25 ++ test/visual_regression/tests/vega/index.ts | 25 ++ .../tests/vega/vega_map_visualization.ts | 39 ++ x-pack/test/visual_regression/config.ts | 31 ++ .../ftr_provider_context.d.ts | 13 + x-pack/test/visual_regression/page_objects.ts | 10 + x-pack/test/visual_regression/services.ts | 14 + .../tests/canvas/fullscreen.js | 25 ++ .../visual_regression/tests/canvas/index.js | 30 ++ .../visual_regression/tests/infra/index.js | 19 + .../tests/infra/saved_views.js | 87 ++++ .../tests/infra/waffle_map.js | 27 ++ .../visual_regression/tests/login_page.ts | 58 +++ .../visual_regression/tests/maps/index.js | 61 +++ .../tests/maps/vector_styling.js | 49 +++ yarn.lock | 415 +++++++++++++++++- 29 files changed, 1430 insertions(+), 66 deletions(-) create mode 100644 test/visual_regression/config.ts create mode 100644 test/visual_regression/ftr_provider_context.ts create mode 100644 test/visual_regression/services/index.ts create mode 100644 test/visual_regression/services/visual_testing/index.ts create mode 100644 test/visual_regression/services/visual_testing/take_percy_snapshot.js create mode 100644 test/visual_regression/services/visual_testing/visual_testing.ts create mode 100644 test/visual_regression/tests/console_app.ts create mode 100644 test/visual_regression/tests/discover/chart_visualization.ts create mode 100644 test/visual_regression/tests/discover/index.ts create mode 100644 test/visual_regression/tests/vega/index.ts create mode 100644 test/visual_regression/tests/vega/vega_map_visualization.ts create mode 100644 x-pack/test/visual_regression/config.ts create mode 100644 x-pack/test/visual_regression/ftr_provider_context.d.ts create mode 100644 x-pack/test/visual_regression/page_objects.ts create mode 100644 x-pack/test/visual_regression/services.ts create mode 100644 x-pack/test/visual_regression/tests/canvas/fullscreen.js create mode 100644 x-pack/test/visual_regression/tests/canvas/index.js create mode 100644 x-pack/test/visual_regression/tests/infra/index.js create mode 100644 x-pack/test/visual_regression/tests/infra/saved_views.js create mode 100644 x-pack/test/visual_regression/tests/infra/waffle_map.js create mode 100644 x-pack/test/visual_regression/tests/login_page.ts create mode 100644 x-pack/test/visual_regression/tests/maps/index.js create mode 100644 x-pack/test/visual_regression/tests/maps/vector_styling.js diff --git a/.buildkite/ftr_configs.yml b/.buildkite/ftr_configs.yml index ef21725869c3e..39a8b8b9f0a66 100644 --- a/.buildkite/ftr_configs.yml +++ b/.buildkite/ftr_configs.yml @@ -44,6 +44,8 @@ disabled: - x-pack/plugins/observability/e2e/synthetics_run.ts # Configs that exist but weren't running in CI when this file was introduced + - test/visual_regression/config.ts + - x-pack/test/visual_regression/config.ts - x-pack/test/alerting_api_integration/security_and_spaces/group2/tests/actions/config.ts - x-pack/test/alerting_api_integration/security_and_spaces/group2/tests/telemetry/config.ts - x-pack/test/alerting_api_integration/spaces_only_legacy/config.ts diff --git a/.eslintrc.js b/.eslintrc.js index 9ed08807b8e23..385d241e52fff 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -702,6 +702,7 @@ module.exports = { 'test/*/config_open.ts', 'test/*/*.config.ts', 'test/*/{tests,test_suites,apis,apps}/**/*', + 'test/visual_regression/tests/**/*', 'x-pack/test/*/{tests,test_suites,apis,apps}/**/*', 'x-pack/test/*/*config.*ts', 'x-pack/test/saved_object_api_integration/*/apis/**/*', diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 8b0af587e0032..3fb8a5f2d1b8e 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -210,6 +210,7 @@ /x-pack/test/api_integration/apis/maps/ @elastic/kibana-gis /x-pack/test/functional/apps/maps/ @elastic/kibana-gis /x-pack/test/functional/es_archives/maps/ @elastic/kibana-gis +/x-pack/test/visual_regression/tests/maps/index.js @elastic/kibana-gis /x-pack/plugins/stack_alerts/server/alert_types/geo_containment @elastic/kibana-gis /x-pack/plugins/stack_alerts/public/alert_types/geo_containment @elastic/kibana-gis #CC# /x-pack/plugins/file_upload @elastic/kibana-gis @@ -265,6 +266,8 @@ /test/functional/services/common @elastic/kibana-qa /test/functional/services/lib @elastic/kibana-qa /test/functional/services/remote @elastic/kibana-qa +/test/visual_regression @elastic/kibana-qa +/x-pack/test/visual_regression @elastic/kibana-qa # Core /examples/hello_world/ @elastic/kibana-core diff --git a/package.json b/package.json index 42da0114078f0..9294089cb355a 100644 --- a/package.json +++ b/package.json @@ -616,6 +616,7 @@ "@mapbox/vector-tile": "1.3.1", "@octokit/rest": "^16.35.0", "@openpgp/web-stream-tools": "^0.0.10", + "@percy/agent": "^0.28.6", "@storybook/addon-a11y": "^6.4.22", "@storybook/addon-actions": "^6.4.22", "@storybook/addon-controls": "^6.4.22", diff --git a/packages/kbn-pm/dist/index.js b/packages/kbn-pm/dist/index.js index e9e0fd88618fe..647e8a8d4bbbe 100644 --- a/packages/kbn-pm/dist/index.js +++ b/packages/kbn-pm/dist/index.js @@ -23844,7 +23844,7 @@ module.exports.sync = (patterns, {force, dryRun, cwd = process.cwd(), ...options "use strict"; -const indentString = __webpack_require__("../../node_modules/indent-string/index.js"); +const indentString = __webpack_require__("../../node_modules/del/node_modules/indent-string/index.js"); const cleanStack = __webpack_require__("../../node_modules/clean-stack/index.js"); const cleanInternalStack = stack => stack.replace(/\s+at .*aggregate-error\/index.js:\d+:\d+\)?/g, ''); @@ -24257,6 +24257,49 @@ module.exports = { }; +/***/ }), + +/***/ "../../node_modules/del/node_modules/indent-string/index.js": +/***/ (function(module, exports, __webpack_require__) { + +"use strict"; + + +module.exports = (string, count = 1, options) => { + options = { + indent: ' ', + includeEmptyLines: false, + ...options + }; + + if (typeof string !== 'string') { + throw new TypeError( + `Expected \`input\` to be a \`string\`, got \`${typeof string}\`` + ); + } + + if (typeof count !== 'number') { + throw new TypeError( + `Expected \`count\` to be a \`number\`, got \`${typeof count}\`` + ); + } + + if (typeof options.indent !== 'string') { + throw new TypeError( + `Expected \`options.indent\` to be a \`string\`, got \`${typeof options.indent}\`` + ); + } + + if (count === 0) { + return string; + } + + const regex = options.includeEmptyLines ? /^/gm : /^(?!\s*$)/gm; + + return string.replace(regex, options.indent.repeat(count)); +}; + + /***/ }), /***/ "../../node_modules/del/node_modules/p-map/index.js": @@ -34306,49 +34349,6 @@ if ( }()); -/***/ }), - -/***/ "../../node_modules/indent-string/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = (string, count = 1, options) => { - options = { - indent: ' ', - includeEmptyLines: false, - ...options - }; - - if (typeof string !== 'string') { - throw new TypeError( - `Expected \`input\` to be a \`string\`, got \`${typeof string}\`` - ); - } - - if (typeof count !== 'number') { - throw new TypeError( - `Expected \`count\` to be a \`number\`, got \`${typeof count}\`` - ); - } - - if (typeof options.indent !== 'string') { - throw new TypeError( - `Expected \`options.indent\` to be a \`string\`, got \`${typeof options.indent}\`` - ); - } - - if (count === 0) { - return string; - } - - const regex = options.includeEmptyLines ? /^/gm : /^(?!\s*$)/gm; - - return string.replace(regex, options.indent.repeat(count)); -}; - - /***/ }), /***/ "../../node_modules/inflight/inflight.js": diff --git a/test/visual_regression/config.ts b/test/visual_regression/config.ts new file mode 100644 index 0000000000000..294848246e7c8 --- /dev/null +++ b/test/visual_regression/config.ts @@ -0,0 +1,30 @@ +/* + * 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 { FtrConfigProviderContext } from '@kbn/test'; +import { services } from './services'; + +export default async function ({ readConfigFile }: FtrConfigProviderContext) { + const functionalConfig = await readConfigFile(require.resolve('../functional/config.base.js')); + + return { + ...functionalConfig.getAll(), + + testFiles: [ + require.resolve('./tests/console_app'), + require.resolve('./tests/discover'), + require.resolve('./tests/vega'), + ], + + services, + + junit: { + reportName: 'Kibana Visual Regression Tests', + }, + }; +} diff --git a/test/visual_regression/ftr_provider_context.ts b/test/visual_regression/ftr_provider_context.ts new file mode 100644 index 0000000000000..28bedd1ca6bc3 --- /dev/null +++ b/test/visual_regression/ftr_provider_context.ts @@ -0,0 +1,15 @@ +/* + * 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 { GenericFtrProviderContext, GenericFtrService } from '@kbn/test'; + +import { pageObjects } from '../functional/page_objects'; +import { services } from './services'; + +export type FtrProviderContext = GenericFtrProviderContext; +export class FtrService extends GenericFtrService {} diff --git a/test/visual_regression/services/index.ts b/test/visual_regression/services/index.ts new file mode 100644 index 0000000000000..9aefe1f8de780 --- /dev/null +++ b/test/visual_regression/services/index.ts @@ -0,0 +1,15 @@ +/* + * 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 { services as functionalServices } from '../../functional/services'; +import { VisualTestingService } from './visual_testing'; + +export const services = { + ...functionalServices, + visualTesting: VisualTestingService, +}; diff --git a/test/visual_regression/services/visual_testing/index.ts b/test/visual_regression/services/visual_testing/index.ts new file mode 100644 index 0000000000000..156e3814d8a1d --- /dev/null +++ b/test/visual_regression/services/visual_testing/index.ts @@ -0,0 +1,9 @@ +/* + * 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. + */ + +export * from './visual_testing'; diff --git a/test/visual_regression/services/visual_testing/take_percy_snapshot.js b/test/visual_regression/services/visual_testing/take_percy_snapshot.js new file mode 100644 index 0000000000000..5325765c8d06b --- /dev/null +++ b/test/visual_regression/services/visual_testing/take_percy_snapshot.js @@ -0,0 +1,102 @@ +/* + * 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 { readFileSync } from 'fs'; +import { agentJsFilename } from '@percy/agent/dist/utils/sdk-utils'; + +export function takePercySnapshot(show, hide) { + if (!window.PercyAgent) { + return false; + } + + // add percy styles to hide/show specific elements + const styleElement = document.createElement('style'); + styleElement.appendChild( + document.createTextNode(` + .hideInPercy { + visibility: hidden; + + .showInPercy { + visibility: visible; + } + } + + .showInPercy { + visibility: visible; + + .hideInPercy { + visibility: hidden; + } + } + `) + ); + document.head.appendChild(styleElement); + + const add = (selectors, className) => { + for (const selector of selectors) { + for (const element of document.querySelectorAll(selector)) { + element.classList.add(className); + } + } + }; + + const remove = (selectors, className) => { + for (const selector of selectors) { + for (const element of document.querySelectorAll(selector)) { + element.classList.remove(className); + } + } + }; + + // set Percy visibility on elements + add(hide, 'hideInPercy'); + if (show.length > 0) { + // hide the body by default + add(['body'], 'hideInPercy'); + add(show, 'showInPercy'); + } + + // convert canvas elements into static images + const replacements = []; + for (const canvas of document.querySelectorAll('canvas')) { + const image = document.createElement('img'); + image.classList.value = canvas.classList.value; + image.src = canvas.toDataURL(); + image.style.cssText = window.getComputedStyle(canvas).cssText; + canvas.parentElement.replaceChild(image, canvas); + replacements.push({ canvas, image }); + } + + try { + const agent = new window.PercyAgent({ + handleAgentCommunication: false, + }); + + // cache the dom snapshot containing the images + return agent.snapshot(document, { + widths: [document.documentElement.clientWidth], + }); + } finally { + // restore replaced canvases + for (const { image, canvas } of replacements) { + image.parentElement.replaceChild(canvas, image); + } + + // restore element visibility + document.head.removeChild(styleElement); + remove(['body'], 'hideInPercy'); + remove(show, 'showInPercy'); + remove(hide, 'hideInPercy'); + } +} + +export const takePercySnapshotWithAgent = ` + ${readFileSync(agentJsFilename(), 'utf8')} + + return (${takePercySnapshot.toString()}).apply(null, arguments); +`; diff --git a/test/visual_regression/services/visual_testing/visual_testing.ts b/test/visual_regression/services/visual_testing/visual_testing.ts new file mode 100644 index 0000000000000..59c601e6a2b6e --- /dev/null +++ b/test/visual_regression/services/visual_testing/visual_testing.ts @@ -0,0 +1,114 @@ +/* + * 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 { postSnapshot } from '@percy/agent/dist/utils/sdk-utils'; +import testSubjSelector from '@kbn/test-subj-selector'; +import { Test } from '@kbn/test'; +import { kibanaPackageJson as pkg } from '@kbn/utils'; +import { FtrService, FtrProviderContext } from '../../ftr_provider_context'; + +// @ts-ignore internal js that is passed to the browser as is +import { takePercySnapshot, takePercySnapshotWithAgent } from './take_percy_snapshot'; + +export const DEFAULT_OPTIONS = { + widths: [1200], +}; + +export interface SnapshotOptions { + /** + * name to append to visual test name + */ + name?: string; + /** + * test subject selectiors to __show__ in screenshot + */ + show?: string[]; + /** + * test subject selectiors to __hide__ in screenshot + */ + hide?: string[]; +} + +const statsCache = new WeakMap(); + +function getStats(test: Test) { + if (!statsCache.has(test)) { + statsCache.set(test, { + snapshotCount: 0, + }); + } + + return statsCache.get(test)!; +} + +export class VisualTestingService extends FtrService { + private readonly browser = this.ctx.getService('browser'); + private readonly log = this.ctx.getService('log'); + + private currentTest: Test | undefined; + + constructor(ctx: FtrProviderContext) { + super(ctx); + + this.ctx.getService('lifecycle').beforeEachTest.add((test) => { + this.currentTest = test; + }); + } + + public async snapshot(options: SnapshotOptions = {}) { + if (process.env.DISABLE_VISUAL_TESTING) { + this.log.warning( + 'Capturing of percy snapshots disabled, would normally capture a snapshot here!' + ); + return; + } + + this.log.debug('Capturing percy snapshot'); + + if (!this.currentTest) { + throw new Error('unable to determine current test'); + } + + const [domSnapshot, url] = await Promise.all([ + this.getSnapshot(options.show, options.hide), + this.browser.getCurrentUrl(), + ]); + const stats = getStats(this.currentTest); + stats.snapshotCount += 1; + + const { name } = options; + const success = await postSnapshot({ + name: `${this.currentTest.fullTitle()} [${name ? name : stats.snapshotCount}]`, + url, + domSnapshot, + clientInfo: `kibana-ftr:${pkg.version}`, + ...DEFAULT_OPTIONS, + }); + + if (!success) { + throw new Error('Percy snapshot failed'); + } + } + + private async getSnapshot(show: string[] = [], hide: string[] = []) { + const showSelectors = show.map(testSubjSelector); + const hideSelectors = hide.map(testSubjSelector); + const snapshot = await this.browser.execute<[string[], string[]], string | false>( + takePercySnapshot, + showSelectors, + hideSelectors + ); + return snapshot !== false + ? snapshot + : await this.browser.execute<[string[], string[]], string>( + takePercySnapshotWithAgent, + showSelectors, + hideSelectors + ); + } +} diff --git a/test/visual_regression/tests/console_app.ts b/test/visual_regression/tests/console_app.ts new file mode 100644 index 0000000000000..2c2351b76ad4f --- /dev/null +++ b/test/visual_regression/tests/console_app.ts @@ -0,0 +1,71 @@ +/* + * 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 expect from '@kbn/expect'; +import { FtrProviderContext } from '../ftr_provider_context'; + +const DEFAULT_REQUEST = ` + +GET _search +{ + "query": { + "match_all": {} + } +} + +`.trim(); + +export default function ({ getService, getPageObjects }: FtrProviderContext) { + const retry = getService('retry'); + const log = getService('log'); + const visualTesting = getService('visualTesting'); + const PageObjects = getPageObjects(['common', 'console']); + + describe.skip('console app', function describeIndexTests() { + before(async () => { + log.debug('navigateTo console'); + await PageObjects.common.navigateToApp('console'); + }); + + it('should show the default request', async () => { + // collapse the help pane because we only get the VISIBLE TEXT, not the part that is scrolled + await PageObjects.console.collapseHelp(); + await retry.try(async () => { + const actualRequest = await PageObjects.console.getRequest(); + log.debug(actualRequest); + expect(actualRequest.trim()).to.eql(DEFAULT_REQUEST); + }); + + await visualTesting.snapshot(); + }); + + it('default request response should include `"timed_out" : false`', async () => { + const expectedResponseContains = '"timed_out" : false,'; + await PageObjects.console.clickPlay(); + await retry.try(async () => { + const actualResponse = await PageObjects.console.getResponse(); + log.debug(actualResponse); + expect(actualResponse).to.contain(expectedResponseContains); + }); + }); + + it('settings should allow changing the text size', async () => { + await PageObjects.console.setFontSizeSetting(20); + await retry.try(async () => { + // the settings are not applied synchronously, so we retry for a time + expect(await PageObjects.console.getRequestFontSize()).to.be('20px'); + }); + + await PageObjects.console.setFontSizeSetting(24); + await retry.try(async () => { + // the settings are not applied synchronously, so we retry for a time + expect(await PageObjects.console.getRequestFontSize()).to.be('24px'); + }); + }); + }); +} diff --git a/test/visual_regression/tests/discover/chart_visualization.ts b/test/visual_regression/tests/discover/chart_visualization.ts new file mode 100644 index 0000000000000..f8390064732b9 --- /dev/null +++ b/test/visual_regression/tests/discover/chart_visualization.ts @@ -0,0 +1,117 @@ +/* + * 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 expect from '@kbn/expect'; + +import { FtrProviderContext } from '../../ftr_provider_context'; + +export default function ({ getService, getPageObjects }: FtrProviderContext) { + const retry = getService('retry'); + const esArchiver = getService('esArchiver'); + const browser = getService('browser'); + const kibanaServer = getService('kibanaServer'); + const PageObjects = getPageObjects(['common', 'discover', 'header', 'timePicker']); + const visualTesting = getService('visualTesting'); + const defaultSettings = { + defaultIndex: 'logstash-*', + 'discover:sampleSize': 1, + }; + + describe('discover', function describeIndexTests() { + before(async function () { + await kibanaServer.savedObjects.cleanStandardList(); + await kibanaServer.importExport.load( + 'test/functional/fixtures/kbn_archiver/discover/visual_regression' + ); + + // and load a set of makelogs data + await esArchiver.loadIfNeeded('test/functional/fixtures/es_archiver/logstash_functional'); + await kibanaServer.uiSettings.replace(defaultSettings); + await PageObjects.common.navigateToApp('discover'); + await PageObjects.timePicker.setDefaultAbsoluteRange(); + }); + + after(async function unloadMakelogs() { + await esArchiver.unload('test/functional/fixtures/es_archiver/logstash_functional'); + await kibanaServer.savedObjects.cleanStandardList(); + }); + + async function refreshDiscover() { + await browser.refresh(); + await PageObjects.header.awaitKibanaChrome(); + await PageObjects.header.awaitGlobalLoadingIndicatorHidden(); + await PageObjects.discover.waitUntilSearchingHasFinished(); + await PageObjects.discover.waitForChartLoadingComplete(1); + } + + async function takeSnapshot() { + await refreshDiscover(); + await visualTesting.snapshot({ + show: ['discoverChart'], + }); + } + + describe('query', function () { + this.tags(['skipFirefox']); + + it('should show bars in the correct time zone', async function () { + await PageObjects.header.awaitGlobalLoadingIndicatorHidden(); + await PageObjects.discover.waitUntilSearchingHasFinished(); + await takeSnapshot(); + }); + + it('should show correct data for chart interval Hour', async function () { + await PageObjects.discover.setChartInterval('Hour'); + await takeSnapshot(); + }); + + it('should show correct data for chart interval Day', async function () { + await PageObjects.discover.setChartInterval('Day'); + await takeSnapshot(); + }); + + it('should show correct data for chart interval Week', async function () { + await PageObjects.discover.setChartInterval('Week'); + await takeSnapshot(); + }); + + it('browser back button should show previous interval Day', async function () { + await browser.goBack(); + await retry.try(async function tryingForTime() { + const actualInterval = await PageObjects.discover.getChartInterval(); + expect(actualInterval).to.be('Day'); + }); + await takeSnapshot(); + }); + + it('should show correct data for chart interval Month', async function () { + await PageObjects.discover.setChartInterval('Month'); + await takeSnapshot(); + }); + + it('should show correct data for chart interval Year', async function () { + await PageObjects.discover.setChartInterval('Year'); + await takeSnapshot(); + }); + + it('should show correct data for chart interval Auto', async function () { + await PageObjects.discover.setChartInterval('Auto'); + await takeSnapshot(); + }); + }); + + describe('time zone switch', () => { + it('should show bars in the correct time zone after switching', async function () { + await kibanaServer.uiSettings.replace({ 'dateFormat:tz': 'America/Phoenix' }); + await refreshDiscover(); + await PageObjects.timePicker.setDefaultAbsoluteRange(); + await takeSnapshot(); + }); + }); + }); +} diff --git a/test/visual_regression/tests/discover/index.ts b/test/visual_regression/tests/discover/index.ts new file mode 100644 index 0000000000000..9142a430f963b --- /dev/null +++ b/test/visual_regression/tests/discover/index.ts @@ -0,0 +1,25 @@ +/* + * 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 { DEFAULT_OPTIONS } from '../../services/visual_testing/visual_testing'; +import { FtrProviderContext } from '../../ftr_provider_context'; + +// Width must be the same as visual_testing or canvas image widths will get skewed +const [SCREEN_WIDTH] = DEFAULT_OPTIONS.widths || []; + +export default function ({ getService, loadTestFile }: FtrProviderContext) { + const browser = getService('browser'); + + describe('discover app', function () { + before(function () { + return browser.setWindowSize(SCREEN_WIDTH, 1000); + }); + + loadTestFile(require.resolve('./chart_visualization')); + }); +} diff --git a/test/visual_regression/tests/vega/index.ts b/test/visual_regression/tests/vega/index.ts new file mode 100644 index 0000000000000..9ab4e199439a4 --- /dev/null +++ b/test/visual_regression/tests/vega/index.ts @@ -0,0 +1,25 @@ +/* + * 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 { DEFAULT_OPTIONS } from '../../services/visual_testing/visual_testing'; +import { FtrProviderContext } from '../../ftr_provider_context'; + +// Width must be the same as visual_testing or canvas image widths will get skewed +const [SCREEN_WIDTH] = DEFAULT_OPTIONS.widths || []; + +export default function ({ getService, loadTestFile }: FtrProviderContext) { + const browser = getService('browser'); + + describe('vega app', function () { + before(function () { + return browser.setWindowSize(SCREEN_WIDTH, 1000); + }); + + loadTestFile(require.resolve('./vega_map_visualization')); + }); +} diff --git a/test/visual_regression/tests/vega/vega_map_visualization.ts b/test/visual_regression/tests/vega/vega_map_visualization.ts new file mode 100644 index 0000000000000..d891e7f2bab6b --- /dev/null +++ b/test/visual_regression/tests/vega/vega_map_visualization.ts @@ -0,0 +1,39 @@ +/* + * 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 { FtrProviderContext } from '../../ftr_provider_context'; + +export default function ({ getService, getPageObjects }: FtrProviderContext) { + const esArchiver = getService('esArchiver'); + const kibanaServer = getService('kibanaServer'); + const PageObjects = getPageObjects(['common', 'visualize', 'visChart', 'visEditor', 'vegaChart']); + const visualTesting = getService('visualTesting'); + + describe('vega chart in visualize app', () => { + before(async () => { + await esArchiver.loadIfNeeded( + 'test/functional/fixtures/es_archiver/kibana_sample_data_flights' + ); + await kibanaServer.importExport.load('test/functional/fixtures/kbn_archiver/visualize.json'); + }); + + after(async () => { + await esArchiver.unload('test/functional/fixtures/es_archiver/kibana_sample_data_flights'); + await kibanaServer.importExport.unload( + 'test/functional/fixtures/kbn_archiver/visualize.json' + ); + }); + + it('should show map with vega layer', async function () { + await PageObjects.visualize.gotoVisualizationLandingPage(); + await PageObjects.visualize.openSavedVisualization('VegaMap'); + await PageObjects.visChart.waitForVisualizationRenderingStabilized(); + await visualTesting.snapshot(); + }); + }); +} diff --git a/x-pack/test/visual_regression/config.ts b/x-pack/test/visual_regression/config.ts new file mode 100644 index 0000000000000..c7f0d8203833e --- /dev/null +++ b/x-pack/test/visual_regression/config.ts @@ -0,0 +1,31 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { FtrConfigProviderContext } from '@kbn/test'; + +import { services } from './services'; + +export default async function ({ readConfigFile }: FtrConfigProviderContext) { + const functionalConfig = await readConfigFile(require.resolve('../functional/config.base.js')); + + return { + ...functionalConfig.getAll(), + + testFiles: [ + require.resolve('./tests/canvas'), + require.resolve('./tests/login_page'), + require.resolve('./tests/maps'), + require.resolve('./tests/infra'), + ], + + services, + + junit: { + reportName: 'X-Pack Visual Regression Tests', + }, + }; +} diff --git a/x-pack/test/visual_regression/ftr_provider_context.d.ts b/x-pack/test/visual_regression/ftr_provider_context.d.ts new file mode 100644 index 0000000000000..24f5087ef7fe2 --- /dev/null +++ b/x-pack/test/visual_regression/ftr_provider_context.d.ts @@ -0,0 +1,13 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { GenericFtrProviderContext } from '@kbn/test'; + +import { pageObjects } from './page_objects'; +import { services } from './services'; + +export type FtrProviderContext = GenericFtrProviderContext; diff --git a/x-pack/test/visual_regression/page_objects.ts b/x-pack/test/visual_regression/page_objects.ts new file mode 100644 index 0000000000000..c8b0c9050dbb9 --- /dev/null +++ b/x-pack/test/visual_regression/page_objects.ts @@ -0,0 +1,10 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { pageObjects } from '../functional/page_objects'; + +export { pageObjects }; diff --git a/x-pack/test/visual_regression/services.ts b/x-pack/test/visual_regression/services.ts new file mode 100644 index 0000000000000..7d58bd3f35b32 --- /dev/null +++ b/x-pack/test/visual_regression/services.ts @@ -0,0 +1,14 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { services as ossVisualRegressionServices } from '../../../test/visual_regression/services'; +import { services as functionalServices } from '../functional/services'; + +export const services = { + ...functionalServices, + visualTesting: ossVisualRegressionServices.visualTesting, +}; diff --git a/x-pack/test/visual_regression/tests/canvas/fullscreen.js b/x-pack/test/visual_regression/tests/canvas/fullscreen.js new file mode 100644 index 0000000000000..6a20db5bccdec --- /dev/null +++ b/x-pack/test/visual_regression/tests/canvas/fullscreen.js @@ -0,0 +1,25 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +export default function ({ getPageObjects, getService }) { + const PageObjects = getPageObjects(['common', 'canvas']); + const visualTesting = getService('visualTesting'); + + describe('fullscreen', () => { + it('workpad should display properly in fullscreen mode', async () => { + await PageObjects.common.navigateToApp('canvas', { + hash: '/workpad/workpad-1705f884-6224-47de-ba49-ca224fe6ec31/page/1', + }); + + await PageObjects.canvas.enterFullscreen(); + + await PageObjects.canvas.waitForWorkpadElements(); + + await visualTesting.snapshot(); + }); + }); +} diff --git a/x-pack/test/visual_regression/tests/canvas/index.js b/x-pack/test/visual_regression/tests/canvas/index.js new file mode 100644 index 0000000000000..20a262fef10fe --- /dev/null +++ b/x-pack/test/visual_regression/tests/canvas/index.js @@ -0,0 +1,30 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { DEFAULT_OPTIONS } from '../../../../../test/visual_regression/services/visual_testing/visual_testing'; + +const [SCREEN_WIDTH] = DEFAULT_OPTIONS.widths || []; + +export default function ({ loadTestFile, getService }) { + const esArchiver = getService('esArchiver'); + const browser = getService('browser'); + + describe('canvas app visual regression', function () { + before(async () => { + await esArchiver.loadIfNeeded('x-pack/test/functional/es_archives/logstash_functional'); + await esArchiver.load('x-pack/test/functional/es_archives/canvas/default'); + + await browser.setWindowSize(SCREEN_WIDTH, 1000); + }); + + after(async () => { + await esArchiver.unload('x-pack/test/functional/es_archives/canvas/default'); + }); + + loadTestFile(require.resolve('./fullscreen')); + }); +} diff --git a/x-pack/test/visual_regression/tests/infra/index.js b/x-pack/test/visual_regression/tests/infra/index.js new file mode 100644 index 0000000000000..13669c50953f9 --- /dev/null +++ b/x-pack/test/visual_regression/tests/infra/index.js @@ -0,0 +1,19 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +export default function ({ loadTestFile, getService }) { + const browser = getService('browser'); + + describe.skip('InfraUI Visual Regression', function () { + before(async () => { + await browser.setWindowSize(1600, 1000); + }); + + loadTestFile(require.resolve('./waffle_map')); + loadTestFile(require.resolve('./saved_views')); + }); +} diff --git a/x-pack/test/visual_regression/tests/infra/saved_views.js b/x-pack/test/visual_regression/tests/infra/saved_views.js new file mode 100644 index 0000000000000..a2fb3fda206da --- /dev/null +++ b/x-pack/test/visual_regression/tests/infra/saved_views.js @@ -0,0 +1,87 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { DATES } from '../../../functional/apps/infra/constants'; +const DATE_WITH_DATA = DATES.metricsAndLogs.hosts.withData; + +export default function ({ getPageObjects, getService }) { + const PageObjects = getPageObjects(['common', 'infraHome', 'infraMetricsExplorer']); + const visualTesting = getService('visualTesting'); + const esArchiver = getService('esArchiver'); + + describe('saved views', () => { + before(() => esArchiver.load('x-pack/test/functional/es_archives/infra/metrics_and_logs')); + after(() => esArchiver.unload('x-pack/test/functional/es_archives/infra/metrics_and_logs')); + describe('Inverntory Test save functionality', () => { + it('should have save and load controls', async () => { + await PageObjects.common.navigateToApp('infraOps'); + await PageObjects.infraHome.goToTime(DATE_WITH_DATA); + await PageObjects.infraHome.getSaveViewButton(); + await PageObjects.infraHome.getLoadViewsButton(); + await visualTesting.snapshot(); + }); + + it('should open flyout list', async () => { + await PageObjects.infraHome.openSaveViewsFlyout(); + await visualTesting.snapshot(); + await PageObjects.infraHome.closeSavedViewFlyout(); + }); + + it('should open saved view modal', async () => { + await PageObjects.infraHome.openCreateSaveViewModal(); + await visualTesting.snapshot(); + }); + + it('should be able to enter a view name', async () => { + await PageObjects.infraHome.openEnterViewNameAndSave(); + await visualTesting.snapshot(); + }); + + it('should see a saved view in list', async () => { + await PageObjects.infraHome.openSaveViewsFlyout(); + await visualTesting.snapshot(); + }); + }); + + describe('Metric Explorer Test Saved Views', () => { + before(() => esArchiver.load('x-pack/test/functional/es_archives/infra/metrics_and_logs')); + after(() => esArchiver.unload('x-pack/test/functional/es_archives/infra/metrics_and_logs')); + describe('save functionality', () => { + it('should have saved views component', async () => { + await PageObjects.common.navigateToApp('infraOps'); + await PageObjects.infraHome.goToMetricExplorer(); + await PageObjects.infraSavedViews.getSavedViewsButton(); + await PageObjects.infraSavedViews.ensureViewIsLoaded('Default view'); + await visualTesting.snapshot(); + }); + + it('should open popover', async () => { + await PageObjects.infraSavedViews.clickSavedViewsButton(); + await visualTesting.snapshot(); + await PageObjects.infraSavedViews.closeSavedViewsPopover(); + }); + + it('should create new saved view and load it', async () => { + await PageObjects.infraSavedViews.clickSavedViewsButton(); + await PageObjects.infraSavedViews.clickSaveNewViewButton(); + await PageObjects.infraSavedViews.getCreateSavedViewModal(); + await PageObjects.infraSavedViews.createNewSavedView('view1'); + await PageObjects.infraSavedViews.ensureViewIsLoaded('view1'); + await visualTesting.snapshot(); + }); + + it('should new views should be listed in the load views list', async () => { + await PageObjects.infraSavedViews.clickSavedViewsButton(); + await PageObjects.infraSavedViews.clickLoadViewButton(); + await PageObjects.infraSavedViews.ensureViewIsLoadable('view1'); + await visualTesting.snapshot(); + await PageObjects.infraSavedViews.closeSavedViewsLoadModal(); + }); + }); + }); + }); +} diff --git a/x-pack/test/visual_regression/tests/infra/waffle_map.js b/x-pack/test/visual_regression/tests/infra/waffle_map.js new file mode 100644 index 0000000000000..70aaf89a059eb --- /dev/null +++ b/x-pack/test/visual_regression/tests/infra/waffle_map.js @@ -0,0 +1,27 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { DATES } from '../../../functional/apps/infra/constants'; +const DATE_WITH_DATA = DATES.metricsAndLogs.hosts.withData; + +export default function ({ getPageObjects, getService }) { + const PageObjects = getPageObjects(['common', 'infraHome']); + const visualTesting = getService('visualTesting'); + const esArchiver = getService('esArchiver'); + + describe('waffle map', () => { + before(() => esArchiver.load('x-pack/test/functional/es_archives/infra/metrics_and_logs')); + after(() => esArchiver.unload('x-pack/test/functional/es_archives/infra/metrics_and_logs')); + + it('should just work', async () => { + await PageObjects.common.navigateToApp('infraOps'); + await PageObjects.infraHome.goToTime(DATE_WITH_DATA); + await PageObjects.infraHome.getWaffleMap(); + await visualTesting.snapshot(); + }); + }); +} diff --git a/x-pack/test/visual_regression/tests/login_page.ts b/x-pack/test/visual_regression/tests/login_page.ts new file mode 100644 index 0000000000000..34e1132134744 --- /dev/null +++ b/x-pack/test/visual_regression/tests/login_page.ts @@ -0,0 +1,58 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { FtrProviderContext } from '../ftr_provider_context'; + +export default function ({ getService, getPageObjects }: FtrProviderContext) { + const esArchiver = getService('esArchiver'); + const visualTesting = getService('visualTesting'); + const testSubjects = getService('testSubjects'); + const retry = getService('retry'); + const PageObjects = getPageObjects(['common', 'security']); + + describe.skip('Security', () => { + describe('Login Page', () => { + before(async () => { + await esArchiver.load('x-pack/test/functional/es_archives/empty_kibana'); + await PageObjects.security.forceLogout(); + }); + + after(async () => { + await esArchiver.unload('x-pack/test/functional/es_archives/empty_kibana'); + }); + + afterEach(async () => { + // NOTE: Logout needs to happen before anything else to avoid flaky behavior + await PageObjects.security.forceLogout(); + }); + + it('renders login page', async () => { + await PageObjects.common.navigateToApp('login'); + + await retry.waitFor( + 'login page visible', + async () => await testSubjects.exists('loginSubmit') + ); + + await visualTesting.snapshot(); + }); + + it('renders failed login', async () => { + await PageObjects.security.loginPage.login('wrong-user', 'wrong-password', { + expectSuccess: false, + }); + + await retry.waitFor( + 'login error visible', + async () => await testSubjects.exists('loginErrorMessage') + ); + + await visualTesting.snapshot(); + }); + }); + }); +} diff --git a/x-pack/test/visual_regression/tests/maps/index.js b/x-pack/test/visual_regression/tests/maps/index.js new file mode 100644 index 0000000000000..9d53d70ad2abc --- /dev/null +++ b/x-pack/test/visual_regression/tests/maps/index.js @@ -0,0 +1,61 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +export default function ({ loadTestFile, getService }) { + const kibanaServer = getService('kibanaServer'); + const esArchiver = getService('esArchiver'); + const browser = getService('browser'); + const log = getService('log'); + const supertest = getService('supertest'); + + describe('maps app visual regression', function () { + before(async () => { + await esArchiver.loadIfNeeded('x-pack/test/functional/es_archives/logstash_functional'); + await kibanaServer.importExport.load( + 'x-pack/test/functional/fixtures/kbn_archiver/maps.json' + ); + // Functional tests verify behavior when referenced index pattern saved objects can not be found. + // However, saved object import fails when reference saved objects can not be found. + // To prevent import errors, index pattern saved object references exist during import + // but are then deleted afterwards to enable testing of missing reference index pattern saved objects. + + log.info('Delete index pattern'); + log.debug('id: ' + 'idThatDoesNotExitForESGeoGridSource'); + log.debug('id: ' + 'idThatDoesNotExitForESSearchSource'); + log.debug('id: ' + 'idThatDoesNotExitForESJoinSource'); + await supertest + .delete('/api/index_patterns/index_pattern/' + 'idThatDoesNotExitForESGeoGridSource') + .set('kbn-xsrf', 'true') + .expect(200); + + await supertest + .delete('/api/index_patterns/index_pattern/' + 'idThatDoesNotExitForESSearchSource') + .set('kbn-xsrf', 'true') + .expect(200); + + await supertest + .delete('/api/index_patterns/index_pattern/' + 'idThatDoesNotExitForESJoinSource') + .set('kbn-xsrf', 'true') + .expect(200); + + await esArchiver.load('x-pack/test/functional/es_archives/maps/data'); + await kibanaServer.uiSettings.replace({ + defaultIndex: 'c698b940-e149-11e8-a35a-370a8516603a', + }); + await browser.setWindowSize(1600, 1000); + }); + + after(async () => { + await esArchiver.unload('x-pack/test/functional/es_archives/maps/data'); + await kibanaServer.importExport.unload( + 'x-pack/test/functional/fixtures/kbn_archiver/maps.json' + ); + }); + + loadTestFile(require.resolve('./vector_styling')); + }); +} diff --git a/x-pack/test/visual_regression/tests/maps/vector_styling.js b/x-pack/test/visual_regression/tests/maps/vector_styling.js new file mode 100644 index 0000000000000..092ae603117d9 --- /dev/null +++ b/x-pack/test/visual_regression/tests/maps/vector_styling.js @@ -0,0 +1,49 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +export default function ({ getPageObjects, getService }) { + const PageObjects = getPageObjects(['maps']); + const visualTesting = getService('visualTesting'); + + describe('vector styling', () => { + describe('symbolize as icon', () => { + before(async () => { + await PageObjects.maps.loadSavedMap('vector styling icon demo'); + await PageObjects.maps.enterFullScreen(); + await PageObjects.maps.closeLegend(); + }); + + it('should symbolize points as icons with expected color, size, and orientation', async () => { + await visualTesting.snapshot(); + }); + }); + + describe('dynamic coloring', () => { + before(async () => { + await PageObjects.maps.loadSavedMap('join and dynamic coloring demo'); + await PageObjects.maps.enterFullScreen(); + await PageObjects.maps.closeLegend(); + }); + + it('should symbolize fill color with custom steps from join value and border color with dynamic color ramp from prop value', async () => { + await visualTesting.snapshot(); + }); + }); + + describe('dynamic line coloring', () => { + before(async () => { + await PageObjects.maps.loadSavedMap('pew pew demo'); + await PageObjects.maps.enterFullScreen(); + await PageObjects.maps.closeLegend(); + }); + + it('should symbolize pew pew lines', async () => { + await visualTesting.snapshot(); + }); + }); + }); +} diff --git a/yarn.lock b/yarn.lock index a7f74c0b215b0..f8f09a1dab087 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4087,6 +4087,90 @@ dependencies: mkdirp "^1.0.4" +"@oclif/color@^0.0.0": + version "0.0.0" + resolved "https://registry.yarnpkg.com/@oclif/color/-/color-0.0.0.tgz#54939bbd16d1387511bf1a48ccda1a417248e6a9" + integrity sha512-KKd3W7eNwfNF061tr663oUNdt8EMnfuyf5Xv55SGWA1a0rjhWqS/32P7OeB7CbXcJUBdfVrPyR//1afaW12AWw== + dependencies: + ansi-styles "^3.2.1" + supports-color "^5.4.0" + tslib "^1" + +"@oclif/command@1.5.19", "@oclif/command@^1.5.13", "@oclif/command@^1.5.3": + version "1.5.19" + resolved "https://registry.yarnpkg.com/@oclif/command/-/command-1.5.19.tgz#13f472450eb83bd6c6871a164c03eadb5e1a07ed" + integrity sha512-6+iaCMh/JXJaB2QWikqvGE9//wLEVYYwZd5sud8aLoLKog1Q75naZh2vlGVtg5Mq/NqpqGQvdIjJb3Bm+64AUQ== + dependencies: + "@oclif/config" "^1" + "@oclif/errors" "^1.2.2" + "@oclif/parser" "^3.8.3" + "@oclif/plugin-help" "^2" + debug "^4.1.1" + semver "^5.6.0" + +"@oclif/config@^1": + version "1.13.0" + resolved "https://registry.yarnpkg.com/@oclif/config/-/config-1.13.0.tgz#fc2bd82a9cb30a73faf7d2aa5ae937c719492bd1" + integrity sha512-ttb4l85q7SBx+WlUJY4A9eXLgv4i7hGDNGaXnY9fDKrYD7PBMwNOQ3Ssn2YT2yARAjyOxVE/5LfcwhQGq4kzqg== + dependencies: + debug "^4.1.1" + tslib "^1.9.3" + +"@oclif/errors@^1.2.2": + version "1.2.2" + resolved "https://registry.yarnpkg.com/@oclif/errors/-/errors-1.2.2.tgz#9d8f269b15f13d70aa93316fed7bebc24688edc2" + integrity sha512-Eq8BFuJUQcbAPVofDxwdE0bL14inIiwt5EaKRVY9ZDIG11jwdXZqiQEECJx0VfnLyUZdYfRd/znDI/MytdJoKg== + dependencies: + clean-stack "^1.3.0" + fs-extra "^7.0.0" + indent-string "^3.2.0" + strip-ansi "^5.0.0" + wrap-ansi "^4.0.0" + +"@oclif/linewrap@^1.0.0": + version "1.0.0" + resolved "https://registry.yarnpkg.com/@oclif/linewrap/-/linewrap-1.0.0.tgz#aedcb64b479d4db7be24196384897b5000901d91" + integrity sha512-Ups2dShK52xXa8w6iBWLgcjPJWjais6KPJQq3gQ/88AY6BXoTX+MIGFPrWQO1KLMiQfoTpcLnUwloN4brrVUHw== + +"@oclif/parser@^3.8.3": + version "3.8.4" + resolved "https://registry.yarnpkg.com/@oclif/parser/-/parser-3.8.4.tgz#1a90fc770a42792e574fb896325618aebbe8c9e4" + integrity sha512-cyP1at3l42kQHZtqDS3KfTeyMvxITGwXwH1qk9ktBYvqgMp5h4vHT+cOD74ld3RqJUOZY/+Zi9lb4Tbza3BtuA== + dependencies: + "@oclif/linewrap" "^1.0.0" + chalk "^2.4.2" + tslib "^1.9.3" + +"@oclif/plugin-help@^2": + version "2.2.0" + resolved "https://registry.yarnpkg.com/@oclif/plugin-help/-/plugin-help-2.2.0.tgz#8dfc1c80deae47a205fbc70b018747ba93f31cc3" + integrity sha512-56iIgE7NQfwy/ZrWrvrEfJGb5rrMUt409yoQGw4feiU101UudA1btN1pbUbcKBr7vY9KFeqZZcftXEGxOp7zBg== + dependencies: + "@oclif/command" "^1.5.13" + chalk "^2.4.1" + indent-string "^3.2.0" + lodash.template "^4.4.0" + string-width "^3.0.0" + strip-ansi "^5.0.0" + widest-line "^2.0.1" + wrap-ansi "^4.0.0" + +"@oclif/plugin-not-found@^1.2": + version "1.2.2" + resolved "https://registry.yarnpkg.com/@oclif/plugin-not-found/-/plugin-not-found-1.2.2.tgz#3e601f6e4264d7a0268cd03c152d90aa9c0cec6d" + integrity sha512-SPlmiJFmTFltQT/owdzQwKgq6eq5AEKVwVK31JqbzK48bRWvEL1Ye60cgztXyZ4bpPn2Fl+KeL3FWFQX41qJuA== + dependencies: + "@oclif/color" "^0.0.0" + "@oclif/command" "^1.5.3" + cli-ux "^4.9.0" + fast-levenshtein "^2.0.6" + lodash "^4.17.11" + +"@oclif/screen@^1.0.3": + version "1.0.4" + resolved "https://registry.yarnpkg.com/@oclif/screen/-/screen-1.0.4.tgz#b740f68609dfae8aa71c3a6cab15d816407ba493" + integrity sha512-60CHpq+eqnTxLZQ4PGHYNwUX572hgpMHGPtTWMjdTMsAvlm69lZV/4ly6O3sAYkomo4NggGcomrDpBe34rxUqw== + "@octokit/app@^2.2.2": version "2.2.2" resolved "https://registry.yarnpkg.com/@octokit/app/-/app-2.2.2.tgz#a1b8248f64159eeccbe4000d888fdae4163c4ad8" @@ -4445,6 +4529,34 @@ resolved "https://registry.yarnpkg.com/@opentelemetry/semantic-conventions/-/semantic-conventions-1.4.0.tgz#facf2c67d6063b9918d5a5e3fdf25f3a30d547b6" integrity sha512-Hzl8soGpmyzja9w3kiFFcYJ7n5HNETpplY6cb67KR4QPlxp4FTTresO06qXHgHDhyIInmbLJXuwARjjpsKYGuQ== +"@percy/agent@^0.28.6": + version "0.28.6" + resolved "https://registry.yarnpkg.com/@percy/agent/-/agent-0.28.6.tgz#b220fab6ddcf63ae4e6c343108ba6955a772ce1c" + integrity sha512-SDAyBiUmfQMVTayjvEjQ0IJIA7Y3AoeyWn0jmUxNOMRRIJWo4lQJghfhFCgzCkhXDCm67NMN2nAQAsvXrlIdkQ== + dependencies: + "@oclif/command" "1.5.19" + "@oclif/config" "^1" + "@oclif/plugin-help" "^2" + "@oclif/plugin-not-found" "^1.2" + axios "^0.21.1" + body-parser "^1.18.3" + colors "^1.3.2" + cors "^2.8.4" + cosmiconfig "^5.2.1" + cross-spawn "^7.0.2" + deepmerge "^4.0.0" + express "^4.16.3" + follow-redirects "1.12.1" + generic-pool "^3.7.1" + globby "^10.0.1" + image-size "^0.8.2" + js-yaml "^3.13.1" + percy-client "^3.2.0" + puppeteer "^5.3.1" + retry-axios "^1.0.1" + which "^2.0.1" + winston "^3.0.0" + "@pmmmwh/react-refresh-webpack-plugin@^0.5.1": version "0.5.5" resolved "https://registry.yarnpkg.com/@pmmmwh/react-refresh-webpack-plugin/-/react-refresh-webpack-plugin-0.5.5.tgz#e77aac783bd079f548daa0a7f080ab5b5a9741ca" @@ -8678,6 +8790,11 @@ agent-base@4: dependencies: es6-promisify "^5.0.0" +agent-base@5: + version "5.1.1" + resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-5.1.1.tgz#e8fb3f242959db44d63be665db7a8e739537a32c" + integrity sha512-TMeqbNl2fMW0nMjTEPOwe3J/PRFP4vqeoNuQMG0HlMrtm5QxKqdvAkZ1pRBQ/ulIyDD5Yq0nJ7YbdD8ey0TO3g== + agent-base@6, agent-base@^6.0.2: version "6.0.2" resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" @@ -8848,7 +8965,7 @@ ansi-colors@^3.0.0: resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-3.2.4.tgz#e3a3da4bfbae6c86a9c285625de124a234026fbf" integrity sha512-hHUXGagefjN2iRrID63xckIvotOXOojhQKWIPUZ4mNUZ9nLZW+7FMNoE1lOkEhNWYsx/7ysGIuJYCiMAA9FnrA== -ansi-escapes@^3.0.0: +ansi-escapes@^3.0.0, ansi-escapes@^3.1.0: version "3.2.0" resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-3.2.0.tgz#8780b98ff9dbf5638152d1f1fe5c1d7b4442976b" integrity sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ== @@ -8948,6 +9065,11 @@ ansi-wrap@0.1.0, ansi-wrap@^0.1.0: resolved "https://registry.yarnpkg.com/ansi-wrap/-/ansi-wrap-0.1.0.tgz#a82250ddb0015e9a27ca82e82ea603bbfa45efaf" integrity sha1-qCJQ3bABXponyoLoLqYDu/pF768= +ansicolors@~0.3.2: + version "0.3.2" + resolved "https://registry.yarnpkg.com/ansicolors/-/ansicolors-0.3.2.tgz#665597de86a9ffe3aa9bfbe6cae5c6ea426b4979" + integrity sha1-ZlWX3oap/+Oqm/vmyuXG6kJrSXk= + antlr4ts-cli@^0.5.0-alpha.3: version "0.5.0-alpha.3" resolved "https://registry.yarnpkg.com/antlr4ts-cli/-/antlr4ts-cli-0.5.0-alpha.3.tgz#1f581b2a3c840d3921a2f3b1e739e48c7e7c18cd" @@ -10041,7 +10163,12 @@ blob-util@^2.0.2: resolved "https://registry.yarnpkg.com/blob-util/-/blob-util-2.0.2.tgz#3b4e3c281111bb7f11128518006cdc60b403a1eb" integrity sha512-T7JQa+zsXXEa6/8ZhHcQEW1UFfVM49Ts65uBkFL6fz2QmrElqmbajIDJvuA0tEhRe5eIjpV9ZF+0RfZR9voJFQ== -bluebird@3.7.2, bluebird@^3.3.5, bluebird@^3.5.5, bluebird@^3.7.1, bluebird@^3.7.2: +bluebird-retry@^0.11.0: + version "0.11.0" + resolved "https://registry.yarnpkg.com/bluebird-retry/-/bluebird-retry-0.11.0.tgz#1289ab22cbbc3a02587baad35595351dd0c1c047" + integrity sha1-EomrIsu8OgJYe6rTVZU1HdDBwEc= + +bluebird@3.7.2, bluebird@^3.3.5, bluebird@^3.5.0, bluebird@^3.5.1, bluebird@^3.5.5, bluebird@^3.7.1, bluebird@^3.7.2: version "3.7.2" resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-3.7.2.tgz#9f229c15be272454ffa973ace0dbee79a1b0c36f" integrity sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg== @@ -10056,7 +10183,7 @@ bn.js@^4.0.0, bn.js@^4.1.0, bn.js@^4.1.1, bn.js@^4.11.9: resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.11.9.tgz#26d556829458f9d1e81fc48952493d0ba3507828" integrity sha512-E6QoYqCKZfgatHTdHzs1RRKP7ip4vvm+EyRUeE2RF0NblwVvb0p6jSVeNTOFxPn26QXN2o6SMfNxKp6kU8zQaw== -body-parser@1.19.0: +body-parser@1.19.0, body-parser@^1.18.3: version "1.19.0" resolved "https://registry.yarnpkg.com/body-parser/-/body-parser-1.19.0.tgz#96b2709e57c9c4e09a6fd66a8fd979844f69f08a" integrity sha512-dhEPs72UPbDnAQJ9ZKMNTP6ptJaionhP5cBb541nXPlW60Jepo9RV/a4fX4XWW9CuFNK22krhrj1+rgzifNCsw== @@ -10771,6 +10898,14 @@ capture-exit@^2.0.0: dependencies: rsvp "^4.8.4" +cardinal@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/cardinal/-/cardinal-2.1.1.tgz#7cc1055d822d212954d07b085dea251cc7bc5505" + integrity sha1-fMEFXYItISlU0HsIXeolHMe8VQU= + dependencies: + ansicolors "~0.3.2" + redeyed "~2.1.0" + case-sensitive-paths-webpack-plugin@^2.3.0: version "2.3.0" resolved "https://registry.yarnpkg.com/case-sensitive-paths-webpack-plugin/-/case-sensitive-paths-webpack-plugin-2.3.0.tgz#23ac613cc9a856e4f88ff8bb73bbb5e989825cf7" @@ -11017,6 +11152,11 @@ clean-css@^4.2.3: dependencies: source-map "~0.6.0" +clean-stack@^1.3.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-1.3.0.tgz#9e821501ae979986c46b1d66d2d432db2fd4ae31" + integrity sha1-noIVAa6XmYbEax1m0tQy2y/UrjE= + clean-stack@^2.0.0: version "2.2.0" resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b" @@ -11079,6 +11219,33 @@ cli-truncate@^2.1.0: slice-ansi "^3.0.0" string-width "^4.2.0" +cli-ux@^4.9.0: + version "4.9.3" + resolved "https://registry.yarnpkg.com/cli-ux/-/cli-ux-4.9.3.tgz#4c3e070c1ea23eef010bbdb041192e0661be84ce" + integrity sha512-/1owvF0SZ5Gn54cgrikJ0QskgTzeg30HGjkmjFoaHDJzAqFpuX1DBpFR8aLvsE1J5s9MgeYRENQK4BFwOag5VA== + dependencies: + "@oclif/errors" "^1.2.2" + "@oclif/linewrap" "^1.0.0" + "@oclif/screen" "^1.0.3" + ansi-escapes "^3.1.0" + ansi-styles "^3.2.1" + cardinal "^2.1.1" + chalk "^2.4.1" + clean-stack "^2.0.0" + extract-stack "^1.0.0" + fs-extra "^7.0.0" + hyperlinker "^1.0.0" + indent-string "^3.2.0" + is-wsl "^1.1.0" + lodash "^4.17.11" + password-prompt "^1.0.7" + semver "^5.6.0" + strip-ansi "^5.0.0" + supports-color "^5.5.0" + supports-hyperlinks "^1.0.1" + treeify "^1.1.0" + tslib "^1.9.3" + cli-width@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/cli-width/-/cli-width-3.0.0.tgz#a2f48437a2caa9a22436e794bf071ec9e61cedf6" @@ -11317,7 +11484,7 @@ colorette@^1.2.0, colorette@^1.2.1, colorette@^1.2.2: resolved "https://registry.yarnpkg.com/colorette/-/colorette-1.2.2.tgz#cbcc79d5e99caea2dbf10eb3a26fd8b3e6acfa94" integrity sha512-MKGMzyfeuutC/ZJ1cba9NqcNpfeqMUcYmyF1ZFY6/Cn7CNSAKx6a+s48sqLqyAiZuaP2TcqMhoo+dlwFnVxT9w== -colors@1.4.0: +colors@1.4.0, colors@^1.3.2: version "1.4.0" resolved "https://registry.yarnpkg.com/colors/-/colors-1.4.0.tgz#c50491479d4c1bdaed2c9ced32cf7c7dc2360f78" integrity sha512-a+UqTh4kgZg/SlGvfbzDHpgRu7AAQOmmqRHJnxhRZICKFUT91brVhNNt58CMWU9PsBbv3PDCZUHbVxuDiH2mtA== @@ -11710,6 +11877,14 @@ core-util-is@1.0.2, core-util-is@^1.0.2, core-util-is@~1.0.0: resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.2.tgz#b5fd54220aa2bc5ab57aab7140c940754503c1a7" integrity sha1-tf1UIgqivFq1eqtxQMlAdUUDwac= +cors@^2.8.4: + version "2.8.5" + resolved "https://registry.yarnpkg.com/cors/-/cors-2.8.5.tgz#eac11da51592dd86b9f06f6e7ac293b3df875d29" + integrity sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g== + dependencies: + object-assign "^4" + vary "^1" + cosmiconfig@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/cosmiconfig/-/cosmiconfig-4.0.0.tgz#760391549580bbd2df1e562bc177b13c290972dc" @@ -11720,7 +11895,7 @@ cosmiconfig@^4.0.0: parse-json "^4.0.0" require-from-string "^2.0.1" -cosmiconfig@^5.0.0: +cosmiconfig@^5.0.0, cosmiconfig@^5.2.1: version "5.2.1" resolved "https://registry.yarnpkg.com/cosmiconfig/-/cosmiconfig-5.2.1.tgz#040f726809c591e77a17c0a3626ca45b4f168b1a" integrity sha512-H65gsXo1SKjf8zmrJ67eJk8aIRKV5ff2D4uKZIBZShbhGSpEmsQOPW/SKMKYhSTrqR7ufy6RP69rPogdaPh/kA== @@ -12944,7 +13119,7 @@ deep-object-diff@^1.1.0: resolved "https://registry.yarnpkg.com/deep-object-diff/-/deep-object-diff-1.1.0.tgz#d6fabf476c2ed1751fc94d5ca693d2ed8c18bc5a" integrity sha512-b+QLs5vHgS+IoSNcUE4n9HP2NwcHj7aqnJWsjPtuG75Rh5TOaGt0OjAYInh77d5T16V5cRDC+Pw/6ZZZiETBGw== -deepmerge@3.2.0, deepmerge@^2.1.1, deepmerge@^4.2.2: +deepmerge@3.2.0, deepmerge@^2.1.1, deepmerge@^4.0.0, deepmerge@^4.2.2: version "4.2.2" resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.2.2.tgz#44d2ea3679b8f4d4ffba33f03d865fc1e7bf4955" integrity sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg== @@ -13225,6 +13400,11 @@ detective@^5.0.2, detective@^5.2.0: defined "^1.0.0" minimist "^1.1.1" +devtools-protocol@0.0.818844: + version "0.0.818844" + resolved "https://registry.yarnpkg.com/devtools-protocol/-/devtools-protocol-0.0.818844.tgz#d1947278ec85b53e4c8ca598f607a28fa785ba9e" + integrity sha512-AD1hi7iVJ8OD0aMLQU5VK0XH9LDlA1+BcPIgrAxPfaibx2DbWucuyOhc4oyQCbnvDDO68nN6/LcKfqTP343Jjg== + devtools-protocol@0.0.901419: version "0.0.901419" resolved "https://registry.yarnpkg.com/devtools-protocol/-/devtools-protocol-0.0.901419.tgz#79b5459c48fe7e1c5563c02bd72f8fec3e0cebcd" @@ -13460,7 +13640,7 @@ domhandler@^3.0.0: dependencies: domelementtype "^2.0.1" -domhandler@^4.0, domhandler@^4.0.0, domhandler@^4.2.0, domhandler@^4.2.2: +domhandler@^4.0.0, domhandler@^4.0, domhandler@^4.2.0, domhandler@^4.2.2: version "4.3.0" resolved "https://registry.yarnpkg.com/domhandler/-/domhandler-4.3.0.tgz#16c658c626cf966967e306f966b431f77d4a5626" integrity sha512-fC0aXNQXqKSFTr2wDNZDhsEYjCiYsDWl3D01kwt25hm1YIPyDGHvvi3rw+PLqHAl/m71MaiF7d5zvBr0p5UB2g== @@ -13524,7 +13704,7 @@ dotenv@^16.0.1: resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-16.0.1.tgz#8f8f9d94876c35dac989876a5d3a82a267fdce1d" integrity sha512-1K6hR6wtk2FviQ4kEiSjFiH5rpzEVi8WW0x96aztHVMhEspNpc4DVOUTEHtEva5VThQ8IaBX1Pe4gSzpVVUsKQ== -dotenv@^8.0.0: +dotenv@^8.0.0, dotenv@^8.1.0: version "8.2.0" resolved "https://registry.yarnpkg.com/dotenv/-/dotenv-8.2.0.tgz#97e619259ada750eea3e4ea3e26bceea5424b16a" integrity sha512-8sJ78ElpbDJBHNeBzUbUVLsqKdccaa/BXF1uPTw3GrvQTBgrQrtObr2mUrE38vzYd8cEv+m/JBfDLioYcfXoaw== @@ -14077,6 +14257,11 @@ es6-map@^0.1.5: es6-symbol "~3.1.1" event-emitter "~0.3.5" +es6-promise-pool@^2.5.0: + version "2.5.0" + resolved "https://registry.yarnpkg.com/es6-promise-pool/-/es6-promise-pool-2.5.0.tgz#147c612b36b47f105027f9d2bf54a598a99d9ccb" + integrity sha1-FHxhKza0fxBQJ/nSv1SlmKmdnMs= + es6-promise@^4.0.3, es6-promise@^4.2.8: version "4.2.8" resolved "https://registry.yarnpkg.com/es6-promise/-/es6-promise-4.2.8.tgz#4eb21594c972bc40553d276e510539143db53e0a" @@ -14487,7 +14672,7 @@ espree@^7.3.0, espree@^7.3.1: acorn-jsx "^5.3.1" eslint-visitor-keys "^1.3.0" -esprima@^4.0.0, esprima@^4.0.1: +esprima@^4.0.0, esprima@^4.0.1, esprima@~4.0.0: version "4.0.1" resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.1.tgz#13b04cdb3e6c5d19df91ab6987a8695619b0aa71" integrity sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A== @@ -14770,7 +14955,7 @@ expose-loader@^0.7.5: resolved "https://registry.yarnpkg.com/expose-loader/-/expose-loader-0.7.5.tgz#e29ea2d9aeeed3254a3faa1b35f502db9f9c3f6f" integrity sha512-iPowgKUZkTPX5PznYsmifVj9Bob0w2wTHVkt/eYNPSzyebkUgIedmskf/kcfEIWpiWjg3JRjnW+a17XypySMuw== -express@^4.17.1: +express@^4.16.3, express@^4.17.1: version "4.17.1" resolved "https://registry.yarnpkg.com/express/-/express-4.17.1.tgz#4491fc38605cf51f8629d39c2b5d026f98a4c134" integrity sha512-mHJ9O79RqluphRrcw2X/GTh3k9tVv8YcoyY4Kkh4WDMUYKRZUq0h1o0w2rrrxBqM7VoeUVqgb27xlEMXTnYt4g== @@ -14849,7 +15034,12 @@ extglob@^2.0.4: snapdragon "^0.8.1" to-regex "^3.0.1" -extract-zip@2.0.1, extract-zip@^2.0.1: +extract-stack@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/extract-stack/-/extract-stack-1.0.0.tgz#b97acaf9441eea2332529624b732fc5a1c8165fa" + integrity sha1-uXrK+UQe6iMyUpYktzL8WhyBZfo= + +extract-zip@2.0.1, extract-zip@^2.0.0, extract-zip@^2.0.1: version "2.0.1" resolved "https://registry.yarnpkg.com/extract-zip/-/extract-zip-2.0.1.tgz#663dca56fe46df890d5f131ef4a06d22bb8ba13a" integrity sha512-GDhU9ntwuKyGXdZBUgTIe+vXnWj0fppUEtMDL0+idd5Sta8TGpHssn/eusA9mrPr9qNDym6SxAYZjNvCn/9RBg== @@ -15348,6 +15538,11 @@ folktale@2.3.2: resolved "https://registry.yarnpkg.com/folktale/-/folktale-2.3.2.tgz#38231b039e5ef36989920cbf805bf6b227bf4fd4" integrity sha512-+8GbtQBwEqutP0v3uajDDoN64K2ehmHd0cjlghhxh0WpcfPzAIjPA03e1VvHlxL02FVGR0A6lwXsNQKn3H1RNQ== +follow-redirects@1.12.1: + version "1.12.1" + resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.12.1.tgz#de54a6205311b93d60398ebc01cf7015682312b6" + integrity sha512-tmRv0AVuR7ZyouUHLeNSiO6pqulF7dYa3s19c6t+wz9LD69/uSzdMxJ2S91nTI9U3rt/IldxpzMOFejp6f0hjg== + follow-redirects@^1.0.0, follow-redirects@^1.14.0, follow-redirects@^1.14.9: version "1.15.0" resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.0.tgz#06441868281c86d0dda4ad8bdaead2d02dca89d4" @@ -15382,6 +15577,11 @@ foreach@^2.0.5: resolved "https://registry.yarnpkg.com/foreach/-/foreach-2.0.5.tgz#0bee005018aeb260d0a3af3ae658dd0136ec1b99" integrity sha1-C+4AUBiusmDQo6865ljdATbsG5k= +foreachasync@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/foreachasync/-/foreachasync-3.0.0.tgz#5502987dc8714be3392097f32e0071c9dee07cf6" + integrity sha1-VQKYfchxS+M5IJfzLgBxyd7gfPY= + foreground-child@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/foreground-child/-/foreground-child-2.0.0.tgz#71b32800c9f15aa8f2f83f4a6bd9bff35d861a53" @@ -15547,7 +15747,7 @@ fs-extra@^10.0.0: jsonfile "^6.0.1" universalify "^2.0.0" -fs-extra@^7.0.1: +fs-extra@^7.0.0, fs-extra@^7.0.1: version "7.0.1" resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== @@ -15717,6 +15917,11 @@ geckodriver@^3.0.1: https-proxy-agent "5.0.0" tar "6.1.11" +generic-pool@^3.7.1: + version "3.7.1" + resolved "https://registry.yarnpkg.com/generic-pool/-/generic-pool-3.7.1.tgz#36fe5bb83e7e0e032e5d32cd05dc00f5ff119aa8" + integrity sha512-ug6DAZoNgWm6q5KhPFA+hzXfBLFQu5sTXxPpv44DmE0A2g+CiHoq9LTVdkXpZMkYVMoGw83F6W+WT0h0MFMK/w== + gensync@^1.0.0-beta.1: version "1.0.0-beta.1" resolved "https://registry.yarnpkg.com/gensync/-/gensync-1.0.0-beta.1.tgz#58f4361ff987e5ff6e1e7a210827aa371eaac269" @@ -16458,6 +16663,11 @@ has-bigints@^1.0.1: resolved "https://registry.yarnpkg.com/has-bigints/-/has-bigints-1.0.1.tgz#64fe6acb020673e3b78db035a5af69aa9d07b113" integrity sha512-LSBS2LjbNBTf6287JEbEzvJgftkF5qFkmCo9hDRpAzKhUOlJ+hx8dd4USs00SgsUNwc4617J9ki5YtEClM2ffA== +has-flag@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-2.0.0.tgz#e8207af1cc7b30d446cc70b734b5e8be18f88d51" + integrity sha1-6CB68cx7MNRGzHC3NLXovhj4jVE= + has-flag@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" @@ -17075,6 +17285,14 @@ https-proxy-agent@5.0.0, https-proxy-agent@^5.0.0: agent-base "6" debug "4" +https-proxy-agent@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-4.0.0.tgz#702b71fb5520a132a66de1f67541d9e62154d82b" + integrity sha512-zoDhWrkR3of1l9QAL8/scJZyLu8j/gBkcwcaQOZh7Gyh/+uJQzGVETdgT30akuwkpL8HTRfssqI3BZuV18teDg== + dependencies: + agent-base "5" + debug "4" + human-signals@^1.1.1: version "1.1.1" resolved "https://registry.yarnpkg.com/human-signals/-/human-signals-1.1.1.tgz#c5b1cd14f50aeae09ab6c59fe63ba3395fe4dfa3" @@ -17087,6 +17305,11 @@ humanize-ms@^1.2.1: dependencies: ms "^2.0.0" +hyperlinker@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/hyperlinker/-/hyperlinker-1.0.0.tgz#23dc9e38a206b208ee49bc2d6c8ef47027df0c0e" + integrity sha512-Ty8UblRWFEcfSuIaajM34LdPXIhbs1ajEX/BBPv24J+enSVaEVY63xQ6lTO9VRYS5LAoghIG0IDJ+p+IPzKUQQ== + hyphenate-style-name@^1.0.2: version "1.0.3" resolved "https://registry.yarnpkg.com/hyphenate-style-name/-/hyphenate-style-name-1.0.3.tgz#097bb7fa0b8f1a9cf0bd5c734cf95899981a9b48" @@ -17160,6 +17383,13 @@ image-q@^1.1.1: resolved "https://registry.yarnpkg.com/image-q/-/image-q-1.1.1.tgz#fc84099664460b90ca862d9300b6bfbbbfbf8056" integrity sha1-/IQJlmRGC5DKhi2TALa/u7+/gFY= +image-size@^0.8.2: + version "0.8.3" + resolved "https://registry.yarnpkg.com/image-size/-/image-size-0.8.3.tgz#f0b568857e034f29baffd37013587f2c0cad8b46" + integrity sha512-SMtq1AJ+aqHB45c3FsB4ERK0UCiA2d3H1uq8s+8T0Pf8A3W4teyBQyaFaktH6xvZqh+npwlKU7i4fJo0r7TYTg== + dependencies: + queue "6.0.1" + immediate@~3.0.5: version "3.0.6" resolved "https://registry.yarnpkg.com/immediate/-/immediate-3.0.6.tgz#9db1dbd0faf8de6fbe0f5dd5e56bb606280de69b" @@ -17231,7 +17461,7 @@ imurmurhash@^0.1.4: resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea" integrity sha1-khi5srkoojixPcT7a21XbyMUU+o= -indent-string@^3.0.0: +indent-string@^3.0.0, indent-string@^3.2.0: version "3.2.0" resolved "https://registry.yarnpkg.com/indent-string/-/indent-string-3.2.0.tgz#4a5fd6d27cc332f37e5419a504dbb837105c9289" integrity sha1-Sl/W0nzDMvN+VBmlBNu4NxBckok= @@ -19307,6 +19537,11 @@ jsprim@^2.0.2: json-schema "0.4.0" verror "1.10.0" +jssha@^2.1.0: + version "2.3.1" + resolved "https://registry.yarnpkg.com/jssha/-/jssha-2.3.1.tgz#147b2125369035ca4b2f7d210dc539f009b3de9a" + integrity sha1-FHshJTaQNcpLL30hDcU58Amz3po= + jsts@^1.6.2: version "1.6.2" resolved "https://registry.yarnpkg.com/jsts/-/jsts-1.6.2.tgz#c0efc885edae06ae84f78cbf2a0110ba929c5925" @@ -19792,6 +20027,11 @@ lodash-es@^4.17.11, lodash-es@^4.17.21: resolved "https://registry.yarnpkg.com/lodash-es/-/lodash-es-4.17.21.tgz#43e626c46e6591b7750beb2b50117390c609e3ee" integrity sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw== +lodash._reinterpolate@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz#0ccf2d89166af03b3663c796538b75ac6e114d9d" + integrity sha1-DM8tiRZq8Ds2Y8eWU4t1rG4RTZ0= + lodash.camelcase@^4.3.0: version "4.3.0" resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6" @@ -19917,6 +20157,21 @@ lodash.sortby@^4.7.0: resolved "https://registry.yarnpkg.com/lodash.sortby/-/lodash.sortby-4.7.0.tgz#edd14c824e2cc9c1e0b0a1b42bb5210516a42438" integrity sha1-7dFMgk4sycHgsKG0K7UhBRakJDg= +lodash.template@^4.4.0: + version "4.5.0" + resolved "https://registry.yarnpkg.com/lodash.template/-/lodash.template-4.5.0.tgz#f976195cf3f347d0d5f52483569fe8031ccce8ab" + integrity sha512-84vYFxIkmidUiFxidA/KjjH9pAycqW+h980j7Fuz5qxRtO9pgB7MDFTdys1N7A5mcucRiDyEq4fusljItR1T/A== + dependencies: + lodash._reinterpolate "^3.0.0" + lodash.templatesettings "^4.0.0" + +lodash.templatesettings@^4.0.0: + version "4.2.0" + resolved "https://registry.yarnpkg.com/lodash.templatesettings/-/lodash.templatesettings-4.2.0.tgz#e481310f049d3cf6d47e912ad09313b154f0fb33" + integrity sha512-stgLz+i3Aa9mZgnjr/O+v9ruKZsPsndy7qPZOchbqk2cnTU1ZaldKK+v7m54WoKIyxiuMZTKT2H81F8BeAc3ZQ== + dependencies: + lodash._reinterpolate "^3.0.0" + lodash.toarray@^4.4.0: version "4.4.0" resolved "https://registry.yarnpkg.com/lodash.toarray/-/lodash.toarray-4.4.0.tgz#24c4bfcd6b2fba38bfd0594db1179d8e9b656561" @@ -21707,7 +21962,7 @@ oauth-sign@~0.9.0: resolved "https://registry.yarnpkg.com/oauth-sign/-/oauth-sign-0.9.0.tgz#47a7b016baa68b5fa0ecf3dee08a85c679ac6455" integrity sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ== -object-assign@4.X, object-assign@^4.0.1, object-assign@^4.1.0, object-assign@^4.1.1: +object-assign@4.X, object-assign@^4, object-assign@^4.0.1, object-assign@^4.1.0, object-assign@^4.1.1: version "4.1.1" resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" integrity sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM= @@ -22474,6 +22729,14 @@ pascalcase@^0.1.1: resolved "https://registry.yarnpkg.com/pascalcase/-/pascalcase-0.1.1.tgz#b363e55e8006ca6fe21784d2db22bd15d7917f14" integrity sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ= +password-prompt@^1.0.7: + version "1.1.2" + resolved "https://registry.yarnpkg.com/password-prompt/-/password-prompt-1.1.2.tgz#85b2f93896c5bd9e9f2d6ff0627fa5af3dc00923" + integrity sha512-bpuBhROdrhuN3E7G/koAju0WjVw9/uQOG5Co5mokNj0MiOSBVZS1JTwM4zl55hu0WFmIEFvO9cU9sJQiBIYeIA== + dependencies: + ansi-escapes "^3.1.0" + cross-spawn "^6.0.5" + path-browserify@0.0.1, path-browserify@~0.0.0: version "0.0.1" resolved "https://registry.yarnpkg.com/path-browserify/-/path-browserify-0.0.1.tgz#e6c4ddd7ed3aa27c68a20cc4e50e1a4ee83bbc4a" @@ -22632,6 +22895,21 @@ pend@~1.2.0: resolved "https://registry.yarnpkg.com/pend/-/pend-1.2.0.tgz#7a57eb550a6783f9115331fcf4663d5c8e007a50" integrity sha1-elfrVQpng/kRUzH89GY9XI4AelA= +percy-client@^3.2.0: + version "3.7.0" + resolved "https://registry.yarnpkg.com/percy-client/-/percy-client-3.7.0.tgz#780e7d780c7f646e59ffb6ee9d3d16e8237851ff" + integrity sha512-5levWR/nfVuSDL9YPN9Sn1M41I2/FmC/FndhD84s6W+mrVC4mB0cc9cT9F58hLuh7/133I/YvyI9Vc6NN41+2g== + dependencies: + bluebird "^3.5.1" + bluebird-retry "^0.11.0" + dotenv "^8.1.0" + es6-promise-pool "^2.5.0" + jssha "^2.1.0" + regenerator-runtime "^0.13.1" + request "^2.87.0" + request-promise "^4.2.2" + walk "^2.3.14" + performance-now@^0.2.0: version "0.2.0" resolved "https://registry.yarnpkg.com/performance-now/-/performance-now-0.2.0.tgz#33ef30c5c77d4ea21c5a53869d91b56d8f2555e5" @@ -23532,7 +23810,7 @@ progress@^1.1.8: resolved "https://registry.yarnpkg.com/progress/-/progress-1.1.8.tgz#e260c78f6161cdd9b0e56cc3e0a85de17c7a57be" integrity sha1-4mDHj2Fhzdmw5WzD4Khd4Xx6V74= -progress@^2.0.0, progress@^2.0.3: +progress@^2.0.0, progress@^2.0.1, progress@^2.0.3: version "2.0.3" resolved "https://registry.yarnpkg.com/progress/-/progress-2.0.3.tgz#7e8cf8d8f5b8f239c1bc68beb4eb78567d572ef8" integrity sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA== @@ -23715,7 +23993,7 @@ proxy-from-env@1.0.0: resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.0.0.tgz#33c50398f70ea7eb96d21f7b817630a55791c7ee" integrity sha1-M8UDmPcOp+uW0h97gXYwpVeRx+4= -proxy-from-env@1.1.0, proxy-from-env@^1.1.0: +proxy-from-env@1.1.0, proxy-from-env@^1.0.0, proxy-from-env@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.1.0.tgz#e102f16ca355424865755d2c9e8ea4f24d58c3e2" integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== @@ -23821,6 +24099,24 @@ puppeteer@^10.2.0: unbzip2-stream "1.3.3" ws "7.4.6" +puppeteer@^5.3.1: + version "5.5.0" + resolved "https://registry.yarnpkg.com/puppeteer/-/puppeteer-5.5.0.tgz#331a7edd212ca06b4a556156435f58cbae08af00" + integrity sha512-OM8ZvTXAhfgFA7wBIIGlPQzvyEETzDjeRa4mZRCRHxYL+GNH5WAuYUQdja3rpWZvkX/JKqmuVgbsxDNsDFjMEg== + dependencies: + debug "^4.1.0" + devtools-protocol "0.0.818844" + extract-zip "^2.0.0" + https-proxy-agent "^4.0.0" + node-fetch "^2.6.1" + pkg-dir "^4.2.0" + progress "^2.0.1" + proxy-from-env "^1.0.0" + rimraf "^3.0.2" + tar-fs "^2.0.0" + unbzip2-stream "^1.3.3" + ws "^7.2.3" + q@^1.1.2, q@^1.5.1: version "1.5.1" resolved "https://registry.yarnpkg.com/q/-/q-1.5.1.tgz#7e32f75b41381291d04611f1bf14109ac00651d7" @@ -23879,6 +24175,13 @@ querystringify@^2.1.1: resolved "https://registry.yarnpkg.com/querystringify/-/querystringify-2.1.1.tgz#60e5a5fd64a7f8bfa4d2ab2ed6fdf4c85bad154e" integrity sha512-w7fLxIRCRT7U8Qu53jQnJyPkYZIaR4n5151KMfcJlO/A9397Wxb1amJvROTK6TOnp7PfoAmg/qXiNHI+08jRfA== +queue@6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/queue/-/queue-6.0.1.tgz#abd5a5b0376912f070a25729e0b6a7d565683791" + integrity sha512-AJBQabRCCNr9ANq8v77RJEv73DPbn55cdTb+Giq4X0AVnNVZvMHlYp7XlQiN+1npCZj1DuSmaA2hYVUUDgxFDg== + dependencies: + inherits "~2.0.3" + quick-format-unescaped@^4.0.3: version "4.0.3" resolved "https://registry.yarnpkg.com/quick-format-unescaped/-/quick-format-unescaped-4.0.3.tgz#6d6b66b8207aa2b35eef12be1421bb24c428f652" @@ -24906,6 +25209,13 @@ redent@^3.0.0: indent-string "^4.0.0" strip-indent "^3.0.0" +redeyed@~2.1.0: + version "2.1.1" + resolved "https://registry.yarnpkg.com/redeyed/-/redeyed-2.1.1.tgz#8984b5815d99cb220469c99eeeffe38913e6cc0b" + integrity sha1-iYS1gV2ZyyIEacme7v/jiRPmzAs= + dependencies: + esprima "~4.0.0" + reduce-reducers@*, reduce-reducers@^1.0.4: version "1.0.4" resolved "https://registry.yarnpkg.com/reduce-reducers/-/reduce-reducers-1.0.4.tgz#fb77e751a9eb0201760ac5a605ca8c9c2d0537f8" @@ -25022,7 +25332,7 @@ regenerator-runtime@^0.11.0: resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz#be05ad7f9bf7d22e056f9726cee5017fbf19e2e9" integrity sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg== -regenerator-runtime@^0.13.3, regenerator-runtime@^0.13.4, regenerator-runtime@^0.13.7: +regenerator-runtime@^0.13.1, regenerator-runtime@^0.13.3, regenerator-runtime@^0.13.4, regenerator-runtime@^0.13.7: version "0.13.7" resolved "https://registry.yarnpkg.com/regenerator-runtime/-/regenerator-runtime-0.13.7.tgz#cac2dacc8a1ea675feaabaeb8ae833898ae46f55" integrity sha512-a54FxoJDIr27pgf7IgeQGxmqUNYrcV338lf/6gH456HZ/PhX+5BcwHXG9ajESmwe6WRO0tAzRUrRmNONWgkrew== @@ -25378,6 +25688,13 @@ request-progress@^3.0.0: dependencies: throttleit "^1.0.0" +request-promise-core@1.1.2: + version "1.1.2" + resolved "https://registry.yarnpkg.com/request-promise-core/-/request-promise-core-1.1.2.tgz#339f6aababcafdb31c799ff158700336301d3346" + integrity sha512-UHYyq1MO8GsefGEt7EprS8UrXsm1TxEvFUX1IMTuSLU2Rh7fTIdFtl8xD7JiEYiWU2dl+NYAjCTksTehQUxPag== + dependencies: + lodash "^4.17.11" + request-promise-core@1.1.4: version "1.1.4" resolved "https://registry.yarnpkg.com/request-promise-core/-/request-promise-core-1.1.4.tgz#3eedd4223208d419867b78ce815167d10593a22f" @@ -25394,7 +25711,17 @@ request-promise-native@^1.0.5, request-promise-native@^1.0.8: stealthy-require "^1.1.1" tough-cookie "^2.3.3" -request@^2.44.0, request@^2.88.0, request@^2.88.2: +request-promise@^4.2.2: + version "4.2.4" + resolved "https://registry.yarnpkg.com/request-promise/-/request-promise-4.2.4.tgz#1c5ed0d71441e38ad58c7ce4ea4ea5b06d54b310" + integrity sha512-8wgMrvE546PzbR5WbYxUQogUnUDfM0S7QIFZMID+J73vdFARkFy+HElj4T+MWYhpXwlLp0EQ8Zoj8xUA0he4Vg== + dependencies: + bluebird "^3.5.0" + request-promise-core "1.1.2" + stealthy-require "^1.1.1" + tough-cookie "^2.3.3" + +request@^2.44.0, request@^2.87.0, request@^2.88.0, request@^2.88.2: version "2.88.2" resolved "https://registry.yarnpkg.com/request/-/request-2.88.2.tgz#d73c918731cb5a87da047e207234146f664d12b3" integrity sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw== @@ -25611,6 +25938,11 @@ ret@~0.1.10: resolved "https://registry.yarnpkg.com/ret/-/ret-0.1.15.tgz#b8a4825d5bdb1fc3f6f53c2bc33f81388681c7bc" integrity sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg== +retry-axios@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/retry-axios/-/retry-axios-1.0.1.tgz#c1e465126416d8aee7a0a2d4be28401cc0135029" + integrity sha512-aVnENElFbdmbsv1WbTi610Ukdper88yUPz4Y3eg/DUyHV7vNaLrj9orB6FOjvmFoXL9wZvbMAsOD87BmcyBVOw== + retry@0.12.0, retry@^0.12.0: version "0.12.0" resolved "https://registry.yarnpkg.com/retry/-/retry-0.12.0.tgz#1b42a6266a21f07421d1b0b54b7dc167b01c013b" @@ -27472,7 +27804,7 @@ supports-color@^2.0.0: resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-2.0.0.tgz#535d045ce6b6363fa40117084629995e9df324c7" integrity sha1-U10EXOa2Nj+kARcIRimZXp3zJMc= -supports-color@^5.3.0, supports-color@^5.5.0: +supports-color@^5.0.0, supports-color@^5.3.0, supports-color@^5.4.0, supports-color@^5.5.0: version "5.5.0" resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== @@ -27493,6 +27825,14 @@ supports-color@^7.0.0, supports-color@^7.1.0: dependencies: has-flag "^4.0.0" +supports-hyperlinks@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/supports-hyperlinks/-/supports-hyperlinks-1.0.1.tgz#71daedf36cc1060ac5100c351bb3da48c29c0ef7" + integrity sha512-HHi5kVSefKaJkGYXbDuKbUGRVxqnWGn3J2e39CYcNJEfWciGq2zYtOhXLTlvrOZW1QU7VX67w7fMmWafHX9Pfw== + dependencies: + has-flag "^2.0.0" + supports-color "^5.0.0" + supports-hyperlinks@^2.0.0: version "2.1.0" resolved "https://registry.yarnpkg.com/supports-hyperlinks/-/supports-hyperlinks-2.1.0.tgz#f663df252af5f37c5d49bbd7eeefa9e0b9e59e47" @@ -28264,7 +28604,7 @@ tslib@2.3.1, tslib@^2.0.3, tslib@^2.1.0, tslib@^2.3.1, tslib@~2.3.1: resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.3.1.tgz#e8a335add5ceae51aa261d32a490158ef042ef01" integrity sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw== -tslib@^1.0.0, tslib@^1.10.0, tslib@^1.8.1, tslib@^1.9.0, tslib@^1.9.3: +tslib@^1, tslib@^1.0.0, tslib@^1.10.0, tslib@^1.8.1, tslib@^1.9.0, tslib@^1.9.3: version "1.13.0" resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.13.0.tgz#c881e13cc7015894ed914862d276436fa9a47043" integrity sha512-i/6DQjL8Xf3be4K/E6Wgpekn5Qasl1usyw++dAA35Ue5orEn65VIxOA+YvNNl9HV3qv70T7CNwjODHZrLwvd1Q== @@ -28464,6 +28804,14 @@ unbzip2-stream@1.3.3: buffer "^5.2.1" through "^2.3.8" +unbzip2-stream@^1.3.3: + version "1.4.3" + resolved "https://registry.yarnpkg.com/unbzip2-stream/-/unbzip2-stream-1.4.3.tgz#b0da04c4371311df771cdc215e87f2130991ace7" + integrity sha512-mlExGW4w71ebDJviH16lQLtZS32VKqsSfk80GCfUlwT/4/hNRFsoscrF/c++9xinkMzECL1uL9DDwXqFWkruPg== + dependencies: + buffer "^5.2.1" + through "^2.3.8" + unc-path-regex@^0.1.2: version "0.1.2" resolved "https://registry.yarnpkg.com/unc-path-regex/-/unc-path-regex-0.1.2.tgz#e73dd3d7b0d7c5ed86fbac6b0ae7d8c6a69d50fa" @@ -29174,7 +29522,7 @@ variable-diff@1.1.0: chalk "^1.1.1" object-assign "^4.0.1" -vary@~1.1.2: +vary@^1, vary@~1.1.2: version "1.1.2" resolved "https://registry.yarnpkg.com/vary/-/vary-1.1.2.tgz#2299f02c6ded30d4a5961b0b9f74524a18f634fc" integrity sha1-IpnwLG3tMNSllhsLn3RSShj2NPw= @@ -29700,6 +30048,13 @@ w3c-xmlserializer@^2.0.0: dependencies: xml-name-validator "^3.0.0" +walk@^2.3.14: + version "2.3.14" + resolved "https://registry.yarnpkg.com/walk/-/walk-2.3.14.tgz#60ec8631cfd23276ae1e7363ce11d626452e1ef3" + integrity sha512-5skcWAUmySj6hkBdH6B6+3ddMjVQYH5Qy9QGbPmN8kVmLteXk+yVXg+yfk1nbX30EYakahLrr8iPcCxJQSCBeg== + dependencies: + foreachasync "^3.0.0" + walker@^1.0.7, walker@~1.0.5: version "1.0.7" resolved "https://registry.yarnpkg.com/walker/-/walker-1.0.7.tgz#2f7f9b8fd10d677262b18a884e28d19618e028fb" @@ -30101,6 +30456,13 @@ wide-align@^1.1.0, wide-align@^1.1.2, wide-align@^1.1.5: dependencies: string-width "^1.0.2 || 2 || 3 || 4" +widest-line@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/widest-line/-/widest-line-2.0.1.tgz#7438764730ec7ef4381ce4df82fb98a53142a3fc" + integrity sha512-Ba5m9/Fa4Xt9eb2ELXt77JxVDV8w7qQrH0zS/TWSJdLyAwQjWoOzpzj5lwVftDz6n/EOu3tNACS84v509qwnJA== + dependencies: + string-width "^2.1.1" + widest-line@^3.1.0: version "3.1.0" resolved "https://registry.yarnpkg.com/widest-line/-/widest-line-3.1.0.tgz#8292333bbf66cb45ff0de1603b136b7ae1496eca" @@ -30129,7 +30491,7 @@ winston-transport@^4.4.2, winston-transport@^4.5.0: readable-stream "^3.6.0" triple-beam "^1.3.0" -winston@^3.3.3: +winston@^3.0.0, winston@^3.3.3: version "3.5.1" resolved "https://registry.yarnpkg.com/winston/-/winston-3.5.1.tgz#b25cc899d015836dbf8c583dec8c4c4483a0da2e" integrity sha512-tbRtVy+vsSSCLcZq/8nXZaOie/S2tPXPFt4be/Q3vI/WtYwm7rrwidxVw2GRa38FIXcJ1kUM6MOZ9Jmnk3F3UA== @@ -30211,6 +30573,15 @@ wrap-ansi@^3.0.1: string-width "^2.1.1" strip-ansi "^4.0.0" +wrap-ansi@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-4.0.0.tgz#b3570d7c70156159a2d42be5cc942e957f7b1131" + integrity sha512-uMTsj9rDb0/7kk1PbcbCcwvHUxp60fGDB/NNXpVa0Q+ic/e7y5+BwTxKfQ33VYgDppSwi/FBzpetYzo8s6tfbg== + dependencies: + ansi-styles "^3.2.0" + string-width "^2.1.1" + strip-ansi "^4.0.0" + wrap-ansi@^5.1.0: version "5.1.0" resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-5.1.0.tgz#1fd1f67235d5b6d0fee781056001bfb694c03b09" From 8a5bf42bc0c554d1bc7c878387b60d2ca9807e1d Mon Sep 17 00:00:00 2001 From: Kyle Pollich Date: Thu, 14 Jul 2022 15:53:45 -0400 Subject: [PATCH 046/111] [Fleet] Use `unmapped_type: long` when sorting datasets that don't include `event.ingested` (#136114) * Add ignore_unmapped: true to fix data streams API in e2e tests * Fix sort setup * Skip failing cypress suite for now * Filter out non-integration data streams from Fleet data streams API * Try using timestamp instead of event.ingested * Use unmapped type setting * Provide explicit missing value for event.ingested Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- x-pack/plugins/fleet/cypress/cypress.json | 2 +- .../get_data_streams_query_metadata.ts | 15 ++++++++++++++- .../fleet/server/routes/data_streams/handlers.ts | 2 +- 3 files changed, 16 insertions(+), 3 deletions(-) diff --git a/x-pack/plugins/fleet/cypress/cypress.json b/x-pack/plugins/fleet/cypress/cypress.json index 6886e5c245cc0..b36d0c513116c 100644 --- a/x-pack/plugins/fleet/cypress/cypress.json +++ b/x-pack/plugins/fleet/cypress/cypress.json @@ -2,7 +2,7 @@ "baseUrl": "http://localhost:5620", "defaultCommandTimeout": 60000, "requestTimeout": 60000, - "responseTimetout": 60000, + "responseTimeout": 60000, "execTimeout": 120000, "pageLoadTimeout": 120000, "nodeVersion": "system", diff --git a/x-pack/plugins/fleet/server/routes/data_streams/get_data_streams_query_metadata.ts b/x-pack/plugins/fleet/server/routes/data_streams/get_data_streams_query_metadata.ts index 44a77a511ca4c..05f7989d8baea 100644 --- a/x-pack/plugins/fleet/server/routes/data_streams/get_data_streams_query_metadata.ts +++ b/x-pack/plugins/fleet/server/routes/data_streams/get_data_streams_query_metadata.ts @@ -24,9 +24,22 @@ export async function getDataStreamsQueryMetadata({ esClient.search({ size: 1, index: dataStreamName, - sort: 'event.ingested:desc', _source: false, fields: ['event.ingested'], + // We need to use `body` to control the `sort` value here, because otherwise + // it's just appended as a query string to the search operation and we can't + // set `unmapped_type` for cases where `event.ingested` is not defiend, e.g. + // in custom logs or custom HTTPJSON integrations + body: { + sort: { + 'event.ingested': { + order: 'desc', + // Necessary because of https://github.com/elastic/elasticsearch/issues/81960 + missing: 0, + unmapped_type: 'long', + }, + }, + }, }), esClient.termsEnum({ index: dataStreamName, diff --git a/x-pack/plugins/fleet/server/routes/data_streams/handlers.ts b/x-pack/plugins/fleet/server/routes/data_streams/handlers.ts index f68c8d287472e..f0a5471832de8 100644 --- a/x-pack/plugins/fleet/server/routes/data_streams/handlers.ts +++ b/x-pack/plugins/fleet/server/routes/data_streams/handlers.ts @@ -190,7 +190,7 @@ export const getListHandler: RequestHandler = async (context, request, response) }); // Return final data streams objects sorted by last activity, descending - // After filtering out data streams that are missing dataset/namespace/type fields + // After filtering out data streams that are missing dataset/namespace/type/package fields body.data_streams = (await Promise.all(dataStreamPromises)) .filter(({ dataset, namespace, type }) => dataset && namespace && type) .sort((a, b) => b.last_activity_ms - a.last_activity_ms); From 71d375848e80b639fc78bc269f6eaa825fd868d5 Mon Sep 17 00:00:00 2001 From: Luke Elmers Date: Thu, 14 Jul 2022 14:03:59 -0600 Subject: [PATCH 047/111] [logging] Add mechanism for setting global meta & set `service.node.roles` for all logs. (#136243) --- .../core-logging-server-internal/BUILD.bazel | 1 + .../src/global_context/index.ts | 10 + .../merge_global_context.test.ts | 103 ++++++++ .../global_context/merge_global_context.ts | 56 ++++ .../src/global_context/types.ts | 29 +++ .../src/logger_adapter.test.ts | 242 ++++++++++++------ .../src/logger_adapter.ts | 29 ++- .../src/logging_service.test.ts | 1 + .../src/logging_system.test.mocks.ts | 22 ++ .../src/logging_system.test.ts | 120 ++++++++- .../src/logging_system.ts | 30 ++- .../src/logging_system.mock.ts | 1 + .../core-node-server-internal/BUILD.bazel | 1 + .../src/node_service.test.ts | 23 +- .../src/node_service.ts | 20 +- .../node/integration_tests/logging.test.ts | 70 +++++ src/core/server/server.ts | 2 +- 17 files changed, 652 insertions(+), 108 deletions(-) create mode 100644 packages/core/logging/core-logging-server-internal/src/global_context/index.ts create mode 100644 packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.test.ts create mode 100644 packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.ts create mode 100644 packages/core/logging/core-logging-server-internal/src/global_context/types.ts create mode 100644 packages/core/logging/core-logging-server-internal/src/logging_system.test.mocks.ts create mode 100644 src/core/server/node/integration_tests/logging.test.ts diff --git a/packages/core/logging/core-logging-server-internal/BUILD.bazel b/packages/core/logging/core-logging-server-internal/BUILD.bazel index ea2e1e1550bdf..d5afc20b5e40a 100644 --- a/packages/core/logging/core-logging-server-internal/BUILD.bazel +++ b/packages/core/logging/core-logging-server-internal/BUILD.bazel @@ -31,6 +31,7 @@ RUNTIME_DEPS = [ "@npm//elastic-apm-node", "//packages/elastic-safer-lodash-set", "//packages/kbn-config-schema", + "//packages/kbn-std", ] TYPES_DEPS = [ diff --git a/packages/core/logging/core-logging-server-internal/src/global_context/index.ts b/packages/core/logging/core-logging-server-internal/src/global_context/index.ts new file mode 100644 index 0000000000000..e7a8a0be56c8e --- /dev/null +++ b/packages/core/logging/core-logging-server-internal/src/global_context/index.ts @@ -0,0 +1,10 @@ +/* + * 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. + */ + +export { mergeGlobalContext } from './merge_global_context'; +export type { GlobalContext } from './types'; diff --git a/packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.test.ts b/packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.test.ts new file mode 100644 index 0000000000000..63840d3ab3fbc --- /dev/null +++ b/packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.test.ts @@ -0,0 +1,103 @@ +/* + * 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 { LogMeta } from '@kbn/logging'; +import { GlobalContext } from './types'; +import { mergeGlobalContext } from './merge_global_context'; + +describe('mergeGlobalContext', () => { + test('inserts global meta in entry meta', () => { + const context: GlobalContext = { + bar: false, + }; + const meta: LogMeta = { + // @ts-expect-error Custom ECS field + foo: true, + }; + + expect(mergeGlobalContext(context, meta)).toEqual({ + foo: true, + bar: false, + }); + }); + + test('handles nested context', () => { + const context: GlobalContext = { + 'bar.baz': false, + }; + const meta: LogMeta = { + // @ts-expect-error Custom ECS field + foo: true, + }; + + expect(mergeGlobalContext(context, meta)).toEqual({ + foo: true, + bar: { baz: false }, + }); + }); + + test('does not overwrite meta with global context if the path already exists', () => { + const context: GlobalContext = { + foo: false, + bar: [false], + }; + const meta: LogMeta = { + // @ts-expect-error Custom ECS field + foo: true, + bar: [true], + }; + + expect(mergeGlobalContext(context, meta)).toEqual({ + foo: true, + bar: [true], + }); + }); + + test('if conflicting entries exist in the context, the most specific entry wins', () => { + const context: GlobalContext = { + 'a.b.c': 'd', + 'a.b': 'c', + }; + + // Note that this "most specific entry wins" behavior should not happen in practice, + // as the `LoggingSystem` is handling deconfliction of paths before anything is + // provided to the `LoggerAdapter` in the first place. Including this test just to + // ensure the actual behavior of this function is documented for posterity. + expect(mergeGlobalContext(context)).toEqual({ + a: { b: { c: 'd' } }, + }); + }); + + test('does nothing if no global meta has been set', () => { + const context: GlobalContext = {}; + const meta: LogMeta = { + // @ts-expect-error Custom ECS field + foo: true, + }; + + expect(mergeGlobalContext(context, meta)).toEqual({ + foo: true, + }); + }); + + test('adds global meta even if no user-provided meta exists', () => { + const context: GlobalContext = { + foo: true, + }; + + expect(mergeGlobalContext(context)).toEqual({ + foo: true, + }); + }); + + test('does nothing if no global meta or user-provided meta has been set', () => { + const context: GlobalContext = {}; + + expect(mergeGlobalContext(context)).toBeUndefined(); + }); +}); diff --git a/packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.ts b/packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.ts new file mode 100644 index 0000000000000..64186392caa56 --- /dev/null +++ b/packages/core/logging/core-logging-server-internal/src/global_context/merge_global_context.ts @@ -0,0 +1,56 @@ +/* + * 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 { has } from 'lodash'; +import { set } from '@elastic/safer-lodash-set'; +import { LogMeta } from '@kbn/logging'; +import { GlobalContext } from './types'; + +/** + * Takes a flattened object of {@link GlobalContext} and applies it to the + * provided {@link LogMeta}. + * + * @remarks + * The provided `LogMeta` takes precedence over the `GlobalContext`; + * if duplicate keys are found, the `GlobalContext` will be overridden. + * + * @example + * ```ts + * const meta: LogMeta = { + * a: { b: false }, + * d: 'hi', + * }; + * const context: GlobalContext = { + * 'a.b': true, + * c: [1, 2, 3], + * }; + * + * mergeGlobalContext(context, meta); + * // { + * // a: { b: false }, + * // c: [1, 2, 3], + * // d: 'hi', + * // } + * ``` + * + * @internal + */ +export function mergeGlobalContext(globalContext: GlobalContext, meta?: LogMeta) { + if (!meta && Object.keys(globalContext).length === 0) { + return; + } + + const mergedMeta = meta ?? {}; + for (const [path, data] of Object.entries(globalContext)) { + if (!has(mergedMeta, path)) { + set(mergedMeta, path, data); + } + } + + return mergedMeta; +} diff --git a/packages/core/logging/core-logging-server-internal/src/global_context/types.ts b/packages/core/logging/core-logging-server-internal/src/global_context/types.ts new file mode 100644 index 0000000000000..bb377aa14e390 --- /dev/null +++ b/packages/core/logging/core-logging-server-internal/src/global_context/types.ts @@ -0,0 +1,29 @@ +/* + * 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. + */ + +/** + * A flattened object containing lodash-style dot-separated keys, which + * indicate the path to where each corresponding value should live in a + * nested object. + * + * @remarks + * Arrays are treated as primitives here: array entries should not be broken + * down into separate keys. + * + * @example + * ```ts + * const context: GlobalContext = { + * a: true, + * 'b.c': [1, 2, 3], + * 'd.e.f': 'g', + * }; + * ``` + * + * @internal + */ +export type GlobalContext = Record; diff --git a/packages/core/logging/core-logging-server-internal/src/logger_adapter.test.ts b/packages/core/logging/core-logging-server-internal/src/logger_adapter.test.ts index c7be02e5c0a98..28f747ef3fcf6 100644 --- a/packages/core/logging/core-logging-server-internal/src/logger_adapter.test.ts +++ b/packages/core/logging/core-logging-server-internal/src/logger_adapter.test.ts @@ -7,84 +7,172 @@ */ import type { Logger } from '@kbn/logging'; +import { loggerMock } from '@kbn/logging-mocks'; import { LoggerAdapter } from './logger_adapter'; -test('proxies all method calls to the internal logger.', () => { - const internalLogger: Logger = { - debug: jest.fn(), - error: jest.fn(), - fatal: jest.fn(), - info: jest.fn(), - log: jest.fn(), - trace: jest.fn(), - warn: jest.fn(), - get: jest.fn(), - }; - - const adapter = new LoggerAdapter(internalLogger); - - adapter.trace('trace-message'); - expect(internalLogger.trace).toHaveBeenCalledTimes(1); - expect(internalLogger.trace).toHaveBeenCalledWith('trace-message', undefined); - - adapter.debug('debug-message'); - expect(internalLogger.debug).toHaveBeenCalledTimes(1); - expect(internalLogger.debug).toHaveBeenCalledWith('debug-message', undefined); - - adapter.info('info-message'); - expect(internalLogger.info).toHaveBeenCalledTimes(1); - expect(internalLogger.info).toHaveBeenCalledWith('info-message', undefined); - - adapter.warn('warn-message'); - expect(internalLogger.warn).toHaveBeenCalledTimes(1); - expect(internalLogger.warn).toHaveBeenCalledWith('warn-message', undefined); - - adapter.error('error-message'); - expect(internalLogger.error).toHaveBeenCalledTimes(1); - expect(internalLogger.error).toHaveBeenCalledWith('error-message', undefined); - - adapter.fatal('fatal-message'); - expect(internalLogger.fatal).toHaveBeenCalledTimes(1); - expect(internalLogger.fatal).toHaveBeenCalledWith('fatal-message', undefined); - - adapter.get('context'); - expect(internalLogger.get).toHaveBeenCalledTimes(1); - expect(internalLogger.get).toHaveBeenCalledWith('context'); -}); +describe('LoggerAdapter', () => { + let internalLogger: Logger; + + beforeEach(() => { + internalLogger = loggerMock.create(); + }); + + test('proxies all method calls to the internal logger.', () => { + const adapter = new LoggerAdapter(internalLogger); + + adapter.trace('trace-message'); + expect(internalLogger.trace).toHaveBeenCalledTimes(1); + expect(internalLogger.trace).toHaveBeenCalledWith('trace-message', undefined); + + adapter.debug('debug-message'); + expect(internalLogger.debug).toHaveBeenCalledTimes(1); + expect(internalLogger.debug).toHaveBeenCalledWith('debug-message', undefined); + + adapter.info('info-message'); + expect(internalLogger.info).toHaveBeenCalledTimes(1); + expect(internalLogger.info).toHaveBeenCalledWith('info-message', undefined); + + adapter.warn('warn-message'); + expect(internalLogger.warn).toHaveBeenCalledTimes(1); + expect(internalLogger.warn).toHaveBeenCalledWith('warn-message', undefined); + + adapter.error('error-message'); + expect(internalLogger.error).toHaveBeenCalledTimes(1); + expect(internalLogger.error).toHaveBeenCalledWith('error-message', undefined); + + adapter.fatal('fatal-message'); + expect(internalLogger.fatal).toHaveBeenCalledTimes(1); + expect(internalLogger.fatal).toHaveBeenCalledWith('fatal-message', undefined); + + adapter.get('context'); + expect(internalLogger.get).toHaveBeenCalledTimes(1); + expect(internalLogger.get).toHaveBeenCalledWith('context'); + }); + + test('forwards all method calls to new internal logger if it is updated.', () => { + const newInternalLogger = loggerMock.create(); + + const adapter = new LoggerAdapter(internalLogger); + + adapter.trace('trace-message'); + expect(internalLogger.trace).toHaveBeenCalledTimes(1); + expect(internalLogger.trace).toHaveBeenCalledWith('trace-message', undefined); + (internalLogger.trace as jest.Mock<() => void>).mockReset(); + + adapter.updateLogger(newInternalLogger); + adapter.trace('trace-message'); + expect(internalLogger.trace).not.toHaveBeenCalled(); + expect(newInternalLogger.trace).toHaveBeenCalledTimes(1); + expect(newInternalLogger.trace).toHaveBeenCalledWith('trace-message', undefined); + }); + + describe('global context', () => { + ['trace', 'debug', 'info', 'warn', 'error', 'fatal'].forEach((method) => { + test(`inserts global context in ${method} entries`, () => { + const adapter = new LoggerAdapter(internalLogger, { 'a.b.c': `${method}: d` }); + + // @ts-expect-error Custom ECS field + adapter[method](`new ${method} message`, { hello: 'world' }); + expect(internalLogger[method as keyof Logger]).toHaveBeenCalledTimes(1); + expect(internalLogger[method as keyof Logger]).toHaveBeenCalledWith( + `new ${method} message`, + { + hello: 'world', + a: { b: { c: `${method}: d` } }, + } + ); + + adapter.updateGlobalContext({ e: true }); + + // @ts-expect-error Custom ECS field + adapter[method](`another new ${method} message`, { hello: 'world' }); + expect(internalLogger[method as keyof Logger]).toHaveBeenCalledTimes(2); + expect(internalLogger[method as keyof Logger]).toHaveBeenCalledWith( + `another new ${method} message`, + { + hello: 'world', + e: true, + } + ); + }); + }); + + test('inserts global meta in log entries', () => { + const adapter = new LoggerAdapter(internalLogger, { 'a.b.c': 'd' }); + + adapter.log({ + message: 'message', + meta: { + // @ts-expect-error Custom ECS field + hello: 'world', + }, + }); + expect(internalLogger.log).toHaveBeenCalledTimes(1); + expect(internalLogger.log).toHaveBeenCalledWith({ + message: 'message', + meta: { + hello: 'world', + a: { b: { c: 'd' } }, + }, + }); + + adapter.updateGlobalContext({ e: true }); + + adapter.log({ + message: 'another message', + meta: { + // @ts-expect-error Custom ECS field + hello: 'world', + }, + }); + expect(internalLogger.log).toHaveBeenCalledTimes(2); + expect(internalLogger.log).toHaveBeenCalledWith({ + message: 'another message', + meta: { + hello: 'world', + e: true, + }, + }); + }); + + test('does not overwrite user-provided meta with global meta if the path already exists', () => { + const adapter = new LoggerAdapter(internalLogger, { hello: 'there' }); + + // @ts-expect-error Custom ECS field + adapter.info('message', { hello: 'world' }); + expect(internalLogger.info).toHaveBeenCalledTimes(1); + expect(internalLogger.info).toHaveBeenCalledWith('message', { + hello: 'world', + }); + }); + + test('does nothing if no global meta has been set', () => { + const adapter = new LoggerAdapter(internalLogger); + + // @ts-expect-error Custom ECS field + adapter.info('message', { hello: 'world' }); + expect(internalLogger.info).toHaveBeenCalledTimes(1); + expect(internalLogger.info).toHaveBeenCalledWith('message', { + hello: 'world', + }); + }); + + test('adds global meta even if no user-provided meta exists', () => { + const adapter = new LoggerAdapter(internalLogger, { hello: 'there' }); + + adapter.info('message'); + expect(internalLogger.info).toHaveBeenCalledTimes(1); + expect(internalLogger.info).toHaveBeenCalledWith('message', { + hello: 'there', + }); + }); + + test('does nothing if no global meta or user-provided meta has been set', () => { + const adapter = new LoggerAdapter(internalLogger); -test('forwards all method calls to new internal logger if it is updated.', () => { - const oldInternalLogger: Logger = { - debug: jest.fn(), - error: jest.fn(), - fatal: jest.fn(), - info: jest.fn(), - log: jest.fn(), - trace: jest.fn(), - warn: jest.fn(), - get: jest.fn(), - }; - - const newInternalLogger: Logger = { - debug: jest.fn(), - error: jest.fn(), - fatal: jest.fn(), - info: jest.fn(), - log: jest.fn(), - trace: jest.fn(), - warn: jest.fn(), - get: jest.fn(), - }; - - const adapter = new LoggerAdapter(oldInternalLogger); - - adapter.trace('trace-message'); - expect(oldInternalLogger.trace).toHaveBeenCalledTimes(1); - expect(oldInternalLogger.trace).toHaveBeenCalledWith('trace-message', undefined); - (oldInternalLogger.trace as jest.Mock<() => void>).mockReset(); - - adapter.updateLogger(newInternalLogger); - adapter.trace('trace-message'); - expect(oldInternalLogger.trace).not.toHaveBeenCalled(); - expect(newInternalLogger.trace).toHaveBeenCalledTimes(1); - expect(newInternalLogger.trace).toHaveBeenCalledWith('trace-message', undefined); + adapter.info('message'); + expect(internalLogger.info).toHaveBeenCalledTimes(1); + expect(internalLogger.info).toHaveBeenCalledWith('message', undefined); + }); + }); }); diff --git a/packages/core/logging/core-logging-server-internal/src/logger_adapter.ts b/packages/core/logging/core-logging-server-internal/src/logger_adapter.ts index d2a2c7f52923a..5439fe0205796 100644 --- a/packages/core/logging/core-logging-server-internal/src/logger_adapter.ts +++ b/packages/core/logging/core-logging-server-internal/src/logger_adapter.ts @@ -7,10 +7,11 @@ */ import { LogRecord, Logger, LogMeta } from '@kbn/logging'; +import { GlobalContext, mergeGlobalContext } from './global_context'; /** @internal */ export class LoggerAdapter implements Logger { - constructor(private logger: Logger) {} + constructor(private logger: Logger, private globalContext: GlobalContext = {}) {} /** * The current logger can be updated "on the fly", e.g. when the log config @@ -24,32 +25,44 @@ export class LoggerAdapter implements Logger { this.logger = logger; } + /** + * The current record of {@link GlobalContext} that can be updated on the fly. + * Any updates via this method will be applied to all subsequent log entries. + * + * This is not intended for external use, only internally in Kibana + * + * @internal + */ + public updateGlobalContext(context: GlobalContext) { + this.globalContext = context; + } + public trace(message: string, meta?: LogMeta): void { - this.logger.trace(message, meta); + this.logger.trace(message, mergeGlobalContext(this.globalContext, meta)); } public debug(message: string, meta?: LogMeta): void { - this.logger.debug(message, meta); + this.logger.debug(message, mergeGlobalContext(this.globalContext, meta)); } public info(message: string, meta?: LogMeta): void { - this.logger.info(message, meta); + this.logger.info(message, mergeGlobalContext(this.globalContext, meta)); } public warn(errorOrMessage: string | Error, meta?: LogMeta): void { - this.logger.warn(errorOrMessage, meta); + this.logger.warn(errorOrMessage, mergeGlobalContext(this.globalContext, meta)); } public error(errorOrMessage: string | Error, meta?: LogMeta): void { - this.logger.error(errorOrMessage, meta); + this.logger.error(errorOrMessage, mergeGlobalContext(this.globalContext, meta)); } public fatal(errorOrMessage: string | Error, meta?: LogMeta): void { - this.logger.fatal(errorOrMessage, meta); + this.logger.fatal(errorOrMessage, mergeGlobalContext(this.globalContext, meta)); } public log(record: LogRecord) { - this.logger.log(record); + this.logger.log({ ...record, meta: mergeGlobalContext(this.globalContext, record.meta) }); } public get(...contextParts: string[]): Logger { diff --git a/packages/core/logging/core-logging-server-internal/src/logging_service.test.ts b/packages/core/logging/core-logging-server-internal/src/logging_service.test.ts index 965337fca4a31..1e8f7bddbb86b 100644 --- a/packages/core/logging/core-logging-server-internal/src/logging_service.test.ts +++ b/packages/core/logging/core-logging-server-internal/src/logging_service.test.ts @@ -22,6 +22,7 @@ const createLoggingSystemMock = () => { get: jest.fn().mockImplementation(() => loggerMock.create()), asLoggerFactory: jest.fn().mockImplementation(() => loggerMock.create()), setContextConfig: jest.fn(), + setGlobalContext: jest.fn(), upgrade: jest.fn(), stop: jest.fn(), }; diff --git a/packages/core/logging/core-logging-server-internal/src/logging_system.test.mocks.ts b/packages/core/logging/core-logging-server-internal/src/logging_system.test.mocks.ts new file mode 100644 index 0000000000000..abda107ae2144 --- /dev/null +++ b/packages/core/logging/core-logging-server-internal/src/logging_system.test.mocks.ts @@ -0,0 +1,22 @@ +/* + * 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 { merge, getFlattenedObject } from '@kbn/std'; + +export const mockStreamWrite = jest.fn(); +jest.doMock('fs', () => ({ + ...(jest.requireActual('fs') as any), + constants: {}, + createWriteStream: jest.fn(() => ({ write: mockStreamWrite })), +})); + +export const mockGetFlattenedObject = jest.fn().mockImplementation(getFlattenedObject); +jest.doMock('@kbn/std', () => ({ + merge: jest.fn().mockImplementation(merge), + getFlattenedObject: mockGetFlattenedObject, +})); diff --git a/packages/core/logging/core-logging-server-internal/src/logging_system.test.ts b/packages/core/logging/core-logging-server-internal/src/logging_system.test.ts index ebe06326f499d..724319dbfb565 100644 --- a/packages/core/logging/core-logging-server-internal/src/logging_system.test.ts +++ b/packages/core/logging/core-logging-server-internal/src/logging_system.test.ts @@ -6,12 +6,7 @@ * Side Public License, v 1. */ -const mockStreamWrite = jest.fn(); -jest.mock('fs', () => ({ - ...(jest.requireActual('fs') as any), - constants: {}, - createWriteStream: jest.fn(() => ({ write: mockStreamWrite })), -})); +import { mockStreamWrite, mockGetFlattenedObject } from './logging_system.test.mocks'; const dynamicProps = { process: { pid: expect.any(Number) } }; @@ -34,6 +29,7 @@ afterEach(() => { jest.restoreAllMocks(); mockCreateWriteStream.mockClear(); mockStreamWrite.mockClear(); + mockGetFlattenedObject.mockClear(); }); test('uses default memory buffer logger until config is provided', () => { @@ -521,3 +517,115 @@ test('buffers log records for appenders created during config upgrade', async () await upgradePromise; expect(JSON.parse(mockConsoleLog.mock.calls[0][0]).message).toBe('message to a new context'); }); + +test('setGlobalContext() applies meta to new and existing loggers', async () => { + await system.upgrade( + config.schema.validate({ + appenders: { default: { type: 'console', layout: { type: 'json' } } }, + root: { level: 'info' }, + }) + ); + + const existingLogger = system.get('some-existing-context'); + // @ts-expect-error Custom ECS field + system.setGlobalContext({ a: { b: { c: true } } }); + const newLogger = system.get('some-new-context'); + + existingLogger.info('You know, just for your info.'); + newLogger.info('You know, just for your info.'); + // @ts-expect-error Custom ECS field + existingLogger.warn('You have been warned.', { someMeta: 'goes here' }); + // @ts-expect-error Custom ECS field + newLogger.warn('You have been warned.', { someMeta: 'goes here' }); + + expect(mockConsoleLog).toHaveBeenCalledTimes(4); + expect(JSON.parse(mockConsoleLog.mock.calls[0][0])).toMatchObject({ + log: { logger: 'some-existing-context' }, + message: 'You know, just for your info.', + a: { b: { c: true } }, + }); + expect(JSON.parse(mockConsoleLog.mock.calls[1][0])).toMatchObject({ + log: { logger: 'some-new-context' }, + message: 'You know, just for your info.', + a: { b: { c: true } }, + }); + expect(JSON.parse(mockConsoleLog.mock.calls[2][0])).toMatchObject({ + log: { logger: 'some-existing-context' }, + message: 'You have been warned.', + someMeta: 'goes here', + a: { b: { c: true } }, + }); + expect(JSON.parse(mockConsoleLog.mock.calls[3][0])).toMatchObject({ + log: { logger: 'some-new-context' }, + message: 'You have been warned.', + someMeta: 'goes here', + a: { b: { c: true } }, + }); +}); + +test('new global context always overwrites existing context', async () => { + await system.upgrade( + config.schema.validate({ + appenders: { default: { type: 'console', layout: { type: 'json' } } }, + root: { level: 'info' }, + }) + ); + + const logger = system.get('some-context'); + + // @ts-expect-error Custom ECS field + system.setGlobalContext({ a: { b: { c: true } }, d: false }); + logger.info('You know, just for your info.'); + + // @ts-expect-error Custom ECS field + system.setGlobalContext({ a: false, d: true }); + logger.info('You know, just for your info, again.'); + + expect(mockConsoleLog).toHaveBeenCalledTimes(2); + expect(JSON.parse(mockConsoleLog.mock.calls[0][0])).toMatchObject({ + log: { logger: 'some-context' }, + message: 'You know, just for your info.', + a: { b: { c: true } }, + d: false, + }); + expect(JSON.parse(mockConsoleLog.mock.calls[1][0])).toMatchObject({ + log: { logger: 'some-context' }, + message: 'You know, just for your info, again.', + a: false, + d: true, + }); +}); + +test('flattens global context objects before passing to LoggerAdapter', async () => { + await system.upgrade( + config.schema.validate({ + appenders: { default: { type: 'console', layout: { type: 'json' } } }, + root: { level: 'info' }, + }) + ); + + // @ts-expect-error Custom ECS field + system.setGlobalContext({ a: { b: { c: true } }, d: false }); + + const logger = system.get('some-context'); + + // @ts-expect-error Custom ECS field + system.setGlobalContext({ d: true, e: false }); + + logger.info('You know, just for your info.'); + + expect(mockGetFlattenedObject).toHaveBeenCalledTimes(3); + expect(mockGetFlattenedObject.mock.calls[0][0]).toEqual({ + a: { b: { c: true } }, + d: false, + }); + expect(mockGetFlattenedObject.mock.calls[1][0]).toEqual({ + a: { b: { c: true } }, + d: false, + }); + expect(mockGetFlattenedObject.mock.calls[2][0]).toEqual({ + a: { b: { c: true } }, + d: true, + e: false, + }); +}); diff --git a/packages/core/logging/core-logging-server-internal/src/logging_system.ts b/packages/core/logging/core-logging-server-internal/src/logging_system.ts index a267651ebe55a..c1bdf38433189 100644 --- a/packages/core/logging/core-logging-server-internal/src/logging_system.ts +++ b/packages/core/logging/core-logging-server-internal/src/logging_system.ts @@ -6,7 +6,8 @@ * Side Public License, v 1. */ -import { DisposableAppender, LogLevel, Logger, LoggerFactory } from '@kbn/logging'; +import { getFlattenedObject, merge } from '@kbn/std'; +import { DisposableAppender, LogLevel, Logger, LoggerFactory, LogMeta } from '@kbn/logging'; import type { LoggerConfigType, LoggerContextConfigInput } from '@kbn/core-logging-server'; import { Appenders } from './appenders/appenders'; import { BufferAppender } from './appenders/buffer/buffer_appender'; @@ -25,6 +26,7 @@ export interface ILoggingSystem extends LoggerFactory { asLoggerFactory(): LoggerFactory; upgrade(rawConfig?: LoggingConfigType): Promise; setContextConfig(baseContextParts: string[], rawConfig: LoggerContextConfigInput): Promise; + setGlobalContext(meta: Partial): void; stop(): Promise; } @@ -41,13 +43,20 @@ export class LoggingSystem implements ILoggingSystem { private readonly bufferAppender = new BufferAppender(); private readonly loggers: Map = new Map(); private readonly contextConfigs = new Map(); + private globalContext: Partial = {}; constructor() {} public get(...contextParts: string[]): Logger { const context = LoggingConfig.getLoggerContext(contextParts); if (!this.loggers.has(context)) { - this.loggers.set(context, new LoggerAdapter(this.createLogger(context, this.computedConfig))); + this.loggers.set( + context, + new LoggerAdapter( + this.createLogger(context, this.computedConfig), + getFlattenedObject(this.globalContext) + ) + ); } return this.loggers.get(context)!; } @@ -110,6 +119,23 @@ export class LoggingSystem implements ILoggingSystem { } } + /** + * A mechanism for specifying some "global" {@link LogMeta} that we want + * to inject into all log entries. + * + * @remarks + * The provided context will be merged with the meta of each individual log + * entry. In the case of conflicting keys, the global context will always be + * overridden by the log entry. + */ + public setGlobalContext(meta: Partial) { + this.globalContext = merge(this.globalContext, meta); + const flattenedContext = getFlattenedObject(this.globalContext); + for (const loggerAdapter of this.loggers.values()) { + loggerAdapter.updateGlobalContext(flattenedContext); + } + } + /** * Disposes all loggers (closes log files, clears buffers etc.). Service is not usable after * calling of this method until new config is provided via `upgrade` method. diff --git a/packages/core/logging/core-logging-server-mocks/src/logging_system.mock.ts b/packages/core/logging/core-logging-server-mocks/src/logging_system.mock.ts index b486839ddac6a..ca09498d92640 100644 --- a/packages/core/logging/core-logging-server-mocks/src/logging_system.mock.ts +++ b/packages/core/logging/core-logging-server-mocks/src/logging_system.mock.ts @@ -23,6 +23,7 @@ const createLoggingSystemMock = () => { get: jest.fn(), asLoggerFactory: jest.fn(), setContextConfig: jest.fn(), + setGlobalContext: jest.fn(), upgrade: jest.fn(), stop: jest.fn(), }; diff --git a/packages/core/node/core-node-server-internal/BUILD.bazel b/packages/core/node/core-node-server-internal/BUILD.bazel index dfbd25fdaeb73..5acec90dbd637 100644 --- a/packages/core/node/core-node-server-internal/BUILD.bazel +++ b/packages/core/node/core-node-server-internal/BUILD.bazel @@ -39,6 +39,7 @@ TYPES_DEPS = [ "//packages/kbn-config-schema:npm_module_types", "//packages/kbn-logging:npm_module_types", "//packages/core/base/core-base-server-internal:npm_module_types", + "//packages/core/logging/core-logging-server-internal:npm_module_types", "//packages/core/node/core-node-server:npm_module_types", ] diff --git a/packages/core/node/core-node-server-internal/src/node_service.test.ts b/packages/core/node/core-node-server-internal/src/node_service.test.ts index 309535905445f..a707e8ec1aed8 100644 --- a/packages/core/node/core-node-server-internal/src/node_service.test.ts +++ b/packages/core/node/core-node-server-internal/src/node_service.test.ts @@ -47,7 +47,7 @@ describe('NodeService', () => { coreContext = mockCoreContext.create({ logger, configService }); service = new NodeService(coreContext); - const { roles } = await service.preboot(); + const { roles } = await service.preboot({ loggingSystem: logger }); expect(roles.backgroundTasks).toBe(true); expect(roles.ui).toBe(true); @@ -58,7 +58,7 @@ describe('NodeService', () => { coreContext = mockCoreContext.create({ logger, configService }); service = new NodeService(coreContext); - const { roles } = await service.preboot(); + const { roles } = await service.preboot({ loggingSystem: logger }); expect(roles.backgroundTasks).toBe(true); expect(roles.ui).toBe(false); @@ -69,7 +69,7 @@ describe('NodeService', () => { coreContext = mockCoreContext.create({ logger, configService }); service = new NodeService(coreContext); - const { roles } = await service.preboot(); + const { roles } = await service.preboot({ loggingSystem: logger }); expect(roles.backgroundTasks).toBe(false); expect(roles.ui).toBe(true); @@ -80,7 +80,7 @@ describe('NodeService', () => { coreContext = mockCoreContext.create({ logger, configService }); service = new NodeService(coreContext); - const { roles } = await service.preboot(); + const { roles } = await service.preboot({ loggingSystem: logger }); expect(roles.backgroundTasks).toBe(true); expect(roles.ui).toBe(true); @@ -94,7 +94,7 @@ describe('NodeService', () => { coreContext = mockCoreContext.create({ logger, configService }); service = new NodeService(coreContext); - await service.preboot(); + await service.preboot({ loggingSystem: logger }); expect(logger.get).toHaveBeenCalledTimes(1); expect(logger.get).toHaveBeenCalledWith('node'); @@ -103,5 +103,18 @@ describe('NodeService', () => { `"Kibana process configured with roles: [background_tasks, ui]"` ); }); + + it('sets the node roles in the global context', async () => { + configService = getMockedConfigService({ roles: ['*'] }); + coreContext = mockCoreContext.create({ logger, configService }); + + service = new NodeService(coreContext); + await service.preboot({ loggingSystem: logger }); + + expect(logger.setGlobalContext).toHaveBeenCalledTimes(1); + expect(logger.setGlobalContext).toHaveBeenCalledWith({ + service: { node: { roles: ['background_tasks', 'ui'] } }, + }); + }); }); }); diff --git a/packages/core/node/core-node-server-internal/src/node_service.ts b/packages/core/node/core-node-server-internal/src/node_service.ts index 10006744cf956..cd73c7f85e6f5 100644 --- a/packages/core/node/core-node-server-internal/src/node_service.ts +++ b/packages/core/node/core-node-server-internal/src/node_service.ts @@ -10,6 +10,7 @@ import { firstValueFrom } from 'rxjs'; import { camelCase } from 'lodash'; import type { IConfigService } from '@kbn/config'; import type { CoreContext } from '@kbn/core-base-server-internal'; +import type { ILoggingSystem } from '@kbn/core-logging-server-internal'; import type { NodeRoles } from '@kbn/core-node-server'; import type { Logger } from '@kbn/logging'; import { @@ -32,6 +33,10 @@ export interface InternalNodeServicePreboot { roles: NodeRoles; } +interface PrebootDeps { + loggingSystem: ILoggingSystem; +} + /** @internal */ export class NodeService { private readonly configService: IConfigService; @@ -42,18 +47,15 @@ export class NodeService { this.log = core.logger.get('node'); } - public async preboot(): Promise { - const nodeRoles = await this.getNodeRoles(); - this.log.info(`Kibana process configured with roles: [${nodeRoles.join(', ')}]`, { - service: { - // @ts-expect-error Field not available in ECS until 8.4 - node: { roles: nodeRoles }, - }, - }); + public async preboot({ loggingSystem }: PrebootDeps): Promise { + const roles = await this.getNodeRoles(); + // @ts-expect-error Custom ECS field + loggingSystem.setGlobalContext({ service: { node: { roles } } }); + this.log.info(`Kibana process configured with roles: [${roles.join(', ')}]`); return { roles: NODE_ACCEPTED_ROLES.reduce((acc, curr) => { - return { ...acc, [camelCase(curr)]: nodeRoles.includes(curr) }; + return { ...acc, [camelCase(curr)]: roles.includes(curr) }; }, {} as NodeRoles), }; } diff --git a/src/core/server/node/integration_tests/logging.test.ts b/src/core/server/node/integration_tests/logging.test.ts new file mode 100644 index 0000000000000..931e56beeab73 --- /dev/null +++ b/src/core/server/node/integration_tests/logging.test.ts @@ -0,0 +1,70 @@ +/* + * 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 * as kbnTestServer from '../../../test_helpers/kbn_server'; + +function createRootWithRoles(roles: string[]) { + return kbnTestServer.createRoot({ + node: { + roles, + }, + logging: { + appenders: { + 'test-console': { + type: 'console', + layout: { + type: 'json', + }, + }, + }, + root: { + appenders: ['test-console'], + level: 'info', + }, + }, + }); +} + +describe('node service global context', () => { + const validRoles = [['ui', 'background_tasks'], ['ui'], ['background_tasks']]; + + validRoles.forEach((roles) => { + describe(`with node.roles: ${roles}`, () => { + let root: ReturnType; + let mockConsoleLog: jest.SpyInstance; + + beforeAll(async () => { + mockConsoleLog = jest.spyOn(global.console, 'log'); + root = createRootWithRoles(roles); + + await root.preboot(); + await root.setup(); + }, 30000); + + beforeEach(() => { + mockConsoleLog.mockClear(); + }); + + afterAll(async () => { + mockConsoleLog.mockRestore(); + await root.shutdown(); + }); + + it('logs the correct roles in service.node.roles', () => { + const logger = root.logger.get('foo.bar'); + + logger.info('test info'); + + expect(mockConsoleLog).toHaveBeenCalledTimes(1); + expect(JSON.parse(mockConsoleLog.mock.calls[0][0])).toEqual( + expect.objectContaining({ service: { node: { roles } } }) + ); + }); + }); + }); +}); diff --git a/src/core/server/server.ts b/src/core/server/server.ts index 6f5e072aa1fa7..5f811723845c1 100644 --- a/src/core/server/server.ts +++ b/src/core/server/server.ts @@ -167,7 +167,7 @@ export class Server { const analyticsPreboot = this.analytics.preboot(); const environmentPreboot = await this.environment.preboot({ analytics: analyticsPreboot }); - const nodePreboot = await this.node.preboot(); + const nodePreboot = await this.node.preboot({ loggingSystem: this.loggingSystem }); // Discover any plugins before continuing. This allows other systems to utilize the plugin dependency graph. this.discoveredPlugins = await this.plugins.discover({ From 4f13ea8435dd5aab9095ebf353213268b1643ac8 Mon Sep 17 00:00:00 2001 From: Hannah Mudge Date: Thu, 14 Jul 2022 14:09:39 -0600 Subject: [PATCH 048/111] [Dashboard] [Controls] Hide controls callout when the `hideAnnouncements` setting is `true` (#136410) * Make controls callout dependent on new UI setting * Add functional test --- .../viewport/dashboard_viewport.tsx | 6 ++- .../controls/controls_callout.ts | 39 ++++++++++++++++++- .../functional/page_objects/dashboard_page.ts | 6 +++ 3 files changed, 49 insertions(+), 2 deletions(-) diff --git a/src/plugins/dashboard/public/application/embeddable/viewport/dashboard_viewport.tsx b/src/plugins/dashboard/public/application/embeddable/viewport/dashboard_viewport.tsx index 7726258b399e2..318db746fbe42 100644 --- a/src/plugins/dashboard/public/application/embeddable/viewport/dashboard_viewport.tsx +++ b/src/plugins/dashboard/public/application/embeddable/viewport/dashboard_viewport.tsx @@ -107,12 +107,16 @@ export class DashboardViewport extends React.Component {controlsEnabled ? ( <> - {isEditMode && panelCount !== 0 && controlGroup?.getPanelCount() === 0 ? ( + {!hideAnnouncements && + isEditMode && + panelCount !== 0 && + controlGroup?.getPanelCount() === 0 ? ( { return controlGroup?.getCreateControlButton('callout'); diff --git a/test/functional/apps/dashboard_elements/controls/controls_callout.ts b/test/functional/apps/dashboard_elements/controls/controls_callout.ts index 73bf8fb50c241..0883957c37d8a 100644 --- a/test/functional/apps/dashboard_elements/controls/controls_callout.ts +++ b/test/functional/apps/dashboard_elements/controls/controls_callout.ts @@ -11,8 +11,12 @@ import { OPTIONS_LIST_CONTROL } from '@kbn/controls-plugin/common'; import { FtrProviderContext } from '../../../ftr_provider_context'; export default function ({ getService, getPageObjects }: FtrProviderContext) { + const kibanaServer = getService('kibanaServer'); + const browser = getService('browser'); const testSubjects = getService('testSubjects'); const dashboardAddPanel = getService('dashboardAddPanel'); + const dashboardPanelActions = getService('dashboardPanelActions'); + const { dashboardControls, timePicker, dashboard } = getPageObjects([ 'dashboardControls', 'timePicker', @@ -25,12 +29,24 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { describe('callout visibility', async () => { before(async () => { await dashboard.gotoDashboardLandingPage(); + await dashboard.clickNewDashboard(); await timePicker.setDefaultDataRange(); await dashboard.saveDashboard('Test Controls Callout'); }); describe('does not show the empty control callout on an empty dashboard', async () => { + before(async () => { + const panelCount = await dashboard.getPanelCount(); + if (panelCount > 0) { + const panels = await dashboard.getAllPanels(); + for (const panel of panels) { + await dashboardPanelActions.removePanel(panel); + } + await dashboard.clickQuickSave(); + } + }); + it('in view mode', async () => { await dashboard.clickCancelOutOfEditMode(); await testSubjects.missingOrFail('controls-empty'); @@ -44,7 +60,10 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { it('show the empty control callout on a dashboard with panels', async () => { await dashboard.switchToEditMode(); - await dashboardAddPanel.addVisualization('Rendering-Test:-animal-sounds-pie'); + const panelCount = await dashboard.getPanelCount(); + if (panelCount < 1) { + await dashboardAddPanel.addVisualization('Rendering-Test:-animal-sounds-pie'); + } await testSubjects.existOrFail('controls-empty'); }); @@ -57,6 +76,24 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { await testSubjects.missingOrFail('controls-empty'); }); + it('deleting all controls shows the emoty control callout again', async () => { + await dashboardControls.deleteAllControls(); + await testSubjects.existOrFail('controls-empty'); + }); + + it('hide callout when hide announcement setting is true', async () => { + await dashboard.clickQuickSave(); + await dashboard.gotoDashboardLandingPage(); + await kibanaServer.uiSettings.update({ hideAnnouncements: true }); + await browser.refresh(); + + await dashboard.loadSavedDashboard('Test Controls Callout'); + await dashboard.switchToEditMode(); + await testSubjects.missingOrFail('controls-empty'); + + await kibanaServer.uiSettings.update({ hideAnnouncements: false }); + }); + after(async () => { await dashboard.clickCancelOutOfEditMode(); await dashboard.gotoDashboardLandingPage(); diff --git a/test/functional/page_objects/dashboard_page.ts b/test/functional/page_objects/dashboard_page.ts index a035e05d9a0f1..7ff6bff172f58 100644 --- a/test/functional/page_objects/dashboard_page.ts +++ b/test/functional/page_objects/dashboard_page.ts @@ -42,6 +42,7 @@ export class DashboardPageObject extends FtrService { private readonly header = this.ctx.getPageObject('header'); private readonly visualize = this.ctx.getPageObject('visualize'); private readonly discover = this.ctx.getPageObject('discover'); + private readonly logstashIndex = this.config.get('esTestCluster.ccs') ? 'ftr-remote:logstash-*' : 'logstash-*'; @@ -605,6 +606,11 @@ export class DashboardPageObject extends FtrService { return panels.length; } + public async getAllPanels() { + this.log.debug('getAllPanels'); + return await this.testSubjects.findAll('embeddablePanel'); + } + public getTestVisualizations() { return [ { name: PIE_CHART_VIS_NAME, description: 'PieChart' }, From 2a6f8e8130d5a56a9118b9dbc789a07693ba9a15 Mon Sep 17 00:00:00 2001 From: Quynh Nguyen <43350163+qn895@users.noreply.github.com> Date: Thu, 14 Jul 2022 15:18:00 -0500 Subject: [PATCH 049/111] [ML] Data Visualizer: Remove duplicated geo examples, support 'version' type, add filters for boolean fields, and add sticky header to Discover (#136236) * [ML] Add filter to boolean content * [ML] Change to version type if detected from estypes * [ML] Remove duplicated geo examples * [ML] Change duplicated geo util to duplicated generic util * [ML] Use name for data view instead of title * [ML] Add sticky header for field stats table in Discover * [ML] Move unknown to bottom, rename JOB_FIELD_TYPES --- .../data_visualizer/common/constants.ts | 5 +- .../common/types/field_request_config.ts | 12 +- .../common/types/job_field_type.ts | 4 +- .../examples_list/examples_list.tsx | 17 +- .../expanded_row/file_based_expanded_row.tsx | 17 +- .../geo_point_content_with_map.tsx | 8 +- .../expanded_row/index_based_expanded_row.tsx | 21 +-- .../field_data_row/action_menu/actions.ts | 7 +- .../field_data_row/action_menu/lens_utils.ts | 25 +-- .../field_type_icon/field_type_icon.test.tsx | 6 +- .../fields_stats_grid/create_fields.ts | 20 +-- .../fields_stats_grid/filter_fields.ts | 4 +- .../fields_stats_grid/get_field_names.ts | 6 +- .../common/components/stats_table/_index.scss | 5 +- .../boolean_content.tsx | 93 ++++------- .../data_visualizer_stats_table.tsx | 25 ++- .../common/util/example_utils.test.ts | 153 ++++++++++++++++++ .../application/common/util/example_utils.ts | 58 +++++++ .../common/util/field_types_utils.test.ts | 16 +- .../common/util/field_types_utils.ts | 77 +++++---- .../index_data_visualizer_view.tsx | 2 +- .../hooks/use_data_visualizer_grid_data.ts | 5 +- .../requests/get_field_examples.ts | 21 +-- .../requests/get_fields_stats.ts | 15 +- .../translations/translations/fr-FR.json | 1 - .../translations/translations/ja-JP.json | 1 - .../translations/translations/zh-CN.json | 1 - 27 files changed, 433 insertions(+), 192 deletions(-) create mode 100644 x-pack/plugins/data_visualizer/public/application/common/util/example_utils.test.ts create mode 100644 x-pack/plugins/data_visualizer/public/application/common/util/example_utils.ts diff --git a/x-pack/plugins/data_visualizer/common/constants.ts b/x-pack/plugins/data_visualizer/common/constants.ts index f31a42cc7784c..1923613d72c58 100644 --- a/x-pack/plugins/data_visualizer/common/constants.ts +++ b/x-pack/plugins/data_visualizer/common/constants.ts @@ -29,16 +29,17 @@ export const FILE_FORMATS = { // XML: 'xml', }; -export const JOB_FIELD_TYPES = { +export const SUPPORTED_FIELD_TYPES = { BOOLEAN: 'boolean', DATE: 'date', GEO_POINT: 'geo_point', GEO_SHAPE: 'geo_shape', + HISTOGRAM: 'histogram', IP: 'ip', KEYWORD: 'keyword', NUMBER: 'number', TEXT: 'text', - HISTOGRAM: 'histogram', + VERSION: 'version', UNKNOWN: 'unknown', } as const; diff --git a/x-pack/plugins/data_visualizer/common/types/field_request_config.ts b/x-pack/plugins/data_visualizer/common/types/field_request_config.ts index 5f21748575831..4db8cc8aa7996 100644 --- a/x-pack/plugins/data_visualizer/common/types/field_request_config.ts +++ b/x-pack/plugins/data_visualizer/common/types/field_request_config.ts @@ -29,6 +29,16 @@ export interface DocumentCounts { interval?: number; } +export interface LatLongExample { + lat: number; + lon: number; +} + +export interface GeoPointExample { + coordinates: number[]; + type?: string; +} + export interface FieldVisStats { error?: Error; cardinality?: number; @@ -56,7 +66,7 @@ export interface FieldVisStats { topValues?: Array<{ key: number | string; doc_count: number }>; topValuesSampleSize?: number; topValuesSamplerShardSize?: number; - examples?: Array; + examples?: Array; timeRangeEarliest?: number; timeRangeLatest?: number; } diff --git a/x-pack/plugins/data_visualizer/common/types/job_field_type.ts b/x-pack/plugins/data_visualizer/common/types/job_field_type.ts index ecb6ade035695..bc44361a416c7 100644 --- a/x-pack/plugins/data_visualizer/common/types/job_field_type.ts +++ b/x-pack/plugins/data_visualizer/common/types/job_field_type.ts @@ -5,5 +5,5 @@ * 2.0. */ -import { JOB_FIELD_TYPES } from '../constants'; -export type JobFieldType = typeof JOB_FIELD_TYPES[keyof typeof JOB_FIELD_TYPES]; +import { SUPPORTED_FIELD_TYPES } from '../constants'; +export type JobFieldType = typeof SUPPORTED_FIELD_TYPES[keyof typeof SUPPORTED_FIELD_TYPES]; diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/examples_list/examples_list.tsx b/x-pack/plugins/data_visualizer/public/application/common/components/examples_list/examples_list.tsx index c4792b314b6a6..71722faab8829 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/examples_list/examples_list.tsx +++ b/x-pack/plugins/data_visualizer/public/application/common/components/examples_list/examples_list.tsx @@ -10,12 +10,19 @@ import React, { FC } from 'react'; import { EuiListGroup, EuiListGroupItem } from '@elastic/eui'; import { FormattedMessage } from '@kbn/i18n-react'; +import { i18n } from '@kbn/i18n'; +import { GeoPointExample } from '../../../../../common/types/field_request_config'; import { ExpandedRowFieldHeader } from '../stats_table/components/expanded_row_field_header'; import { ExpandedRowPanel } from '../stats_table/components/field_data_expanded_row/expanded_row_panel'; + interface Props { - examples: Array; + examples: Array; } +const EMPTY_EXAMPLE = i18n.translate( + 'xpack.dataVisualizer.dataGrid.field.examplesList.emptyExampleMessage', + { defaultMessage: '(empty)' } +); export const ExamplesList: FC = ({ examples }) => { if (examples === undefined || examples === null || !Array.isArray(examples)) { return null; @@ -34,7 +41,13 @@ export const ExamplesList: FC = ({ examples }) => { ); }); diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/file_based_expanded_row.tsx b/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/file_based_expanded_row.tsx index 07e5d01e71d9b..ebe37dda153f4 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/file_based_expanded_row.tsx +++ b/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/file_based_expanded_row.tsx @@ -16,7 +16,7 @@ import { NumberContent, } from '../stats_table/components/field_data_expanded_row'; import { GeoPointContent } from './geo_point_content/geo_point_content'; -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; import type { FileBasedFieldVisConfig } from '../../../../../common/types/field_vis_config'; export const FileBasedDataVisualizerExpandedRow = ({ item }: { item: FileBasedFieldVisConfig }) => { @@ -25,25 +25,26 @@ export const FileBasedDataVisualizerExpandedRow = ({ item }: { item: FileBasedFi function getCardContent() { switch (type) { - case JOB_FIELD_TYPES.NUMBER: + case SUPPORTED_FIELD_TYPES.NUMBER: return ; - case JOB_FIELD_TYPES.BOOLEAN: + case SUPPORTED_FIELD_TYPES.BOOLEAN: return ; - case JOB_FIELD_TYPES.DATE: + case SUPPORTED_FIELD_TYPES.DATE: return ; - case JOB_FIELD_TYPES.GEO_POINT: + case SUPPORTED_FIELD_TYPES.GEO_POINT: return ; - case JOB_FIELD_TYPES.IP: + case SUPPORTED_FIELD_TYPES.IP: return ; - case JOB_FIELD_TYPES.KEYWORD: + case SUPPORTED_FIELD_TYPES.KEYWORD: + case SUPPORTED_FIELD_TYPES.VERSION: return ; - case JOB_FIELD_TYPES.TEXT: + case SUPPORTED_FIELD_TYPES.TEXT: return ; default: diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/geo_point_content_with_map/geo_point_content_with_map.tsx b/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/geo_point_content_with_map/geo_point_content_with_map.tsx index 8a0b1d7a3dfe6..f12b65569be1c 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/geo_point_content_with_map/geo_point_content_with_map.tsx +++ b/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/geo_point_content_with_map/geo_point_content_with_map.tsx @@ -4,7 +4,6 @@ * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ - import React, { FC, useEffect, useState } from 'react'; import { DataView } from '@kbn/data-views-plugin/public'; import { ES_GEO_FIELD_TYPE, LayerDescriptor } from '@kbn/maps-plugin/common'; @@ -14,7 +13,7 @@ import { DocumentStatsTable } from '../../stats_table/components/field_data_expa import { ExamplesList } from '../../examples_list'; import { FieldVisConfig } from '../../stats_table/types'; import { useDataVisualizerKibana } from '../../../../kibana_context'; -import { JOB_FIELD_TYPES } from '../../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../../common/constants'; import { EmbeddedMapComponent } from '../../embedded_map'; import { ExpandedRowPanel } from '../../stats_table/components/field_data_expanded_row/expanded_row_panel'; @@ -36,7 +35,8 @@ export const GeoPointContentWithMap: FC<{ dataView?.id !== undefined && config !== undefined && config.fieldName !== undefined && - (config.type === JOB_FIELD_TYPES.GEO_POINT || config.type === JOB_FIELD_TYPES.GEO_SHAPE) + (config.type === SUPPORTED_FIELD_TYPES.GEO_POINT || + config.type === SUPPORTED_FIELD_TYPES.GEO_SHAPE) ) { const params = { indexPatternId: dataView.id, @@ -64,7 +64,7 @@ export const GeoPointContentWithMap: FC<{ return ( - + diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/index_based_expanded_row.tsx b/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/index_based_expanded_row.tsx index c108ca238de8a..e770a4c6bba7a 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/index_based_expanded_row.tsx +++ b/x-pack/plugins/data_visualizer/public/application/common/components/expanded_row/index_based_expanded_row.tsx @@ -8,7 +8,7 @@ import React from 'react'; import { DataView, DataViewField } from '@kbn/data-views-plugin/public'; import { GeoPointContentWithMap } from './geo_point_content_with_map'; -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; import { BooleanContent, DateContent, @@ -51,17 +51,17 @@ export const IndexBasedDataVisualizerExpandedRow = ({ } switch (type) { - case JOB_FIELD_TYPES.NUMBER: + case SUPPORTED_FIELD_TYPES.NUMBER: return ; - case JOB_FIELD_TYPES.BOOLEAN: - return ; + case SUPPORTED_FIELD_TYPES.BOOLEAN: + return ; - case JOB_FIELD_TYPES.DATE: + case SUPPORTED_FIELD_TYPES.DATE: return ; - case JOB_FIELD_TYPES.GEO_POINT: - case JOB_FIELD_TYPES.GEO_SHAPE: + case SUPPORTED_FIELD_TYPES.GEO_POINT: + case SUPPORTED_FIELD_TYPES.GEO_SHAPE: return ( ); - case JOB_FIELD_TYPES.IP: + case SUPPORTED_FIELD_TYPES.IP: return ; - case JOB_FIELD_TYPES.KEYWORD: + case SUPPORTED_FIELD_TYPES.KEYWORD: + case SUPPORTED_FIELD_TYPES.VERSION: return ; - case JOB_FIELD_TYPES.TEXT: + case SUPPORTED_FIELD_TYPES.TEXT: return ; default: diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/actions.ts b/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/actions.ts index 73e69b00132d3..314856e07554f 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/actions.ts +++ b/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/actions.ts @@ -18,7 +18,7 @@ import { dataVisualizerRefresh$, Refresh, } from '../../../../index_data_visualizer/services/timefilter_refresh_service'; -import { JOB_FIELD_TYPES } from '../../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../../common/constants'; import { APP_ID } from '../../../../../../common/constants'; export function getActions( @@ -80,7 +80,10 @@ export function getActions( type: 'icon', icon: 'gisApp', available: (item: FieldVisConfig) => { - return item.type === JOB_FIELD_TYPES.GEO_POINT || item.type === JOB_FIELD_TYPES.GEO_SHAPE; + return ( + item.type === SUPPORTED_FIELD_TYPES.GEO_POINT || + item.type === SUPPORTED_FIELD_TYPES.GEO_SHAPE + ); }, onClick: async (item: FieldVisConfig) => { if (services?.uiActions && dataView) { diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/lens_utils.ts b/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/lens_utils.ts index 731499cee2f89..034f7037fc29a 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/lens_utils.ts +++ b/x-pack/plugins/data_visualizer/public/application/common/components/field_data_row/action_menu/lens_utils.ts @@ -19,7 +19,7 @@ import type { import { DOCUMENT_FIELD_NAME as RECORDS_FIELD } from '@kbn/lens-plugin/common/constants'; import type { CombinedQuery } from '../../../../index_data_visualizer/types/combined_query'; import { FieldVisConfig } from '../../stats_table/types'; -import { JOB_FIELD_TYPES } from '../../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../../common/constants'; interface ColumnsAndLayer { columns: Record; @@ -200,19 +200,20 @@ export function getBooleanSettings(item: FieldVisConfig) { export function getCompatibleLensDataType(type: FieldVisConfig['type']): string | undefined { let lensType: string | undefined; switch (type) { - case JOB_FIELD_TYPES.KEYWORD: + case SUPPORTED_FIELD_TYPES.KEYWORD: + case SUPPORTED_FIELD_TYPES.VERSION: lensType = 'string'; break; - case JOB_FIELD_TYPES.DATE: + case SUPPORTED_FIELD_TYPES.DATE: lensType = 'date'; break; - case JOB_FIELD_TYPES.NUMBER: + case SUPPORTED_FIELD_TYPES.NUMBER: lensType = 'number'; break; - case JOB_FIELD_TYPES.IP: + case SUPPORTED_FIELD_TYPES.IP: lensType = 'ip'; break; - case JOB_FIELD_TYPES.BOOLEAN: + case SUPPORTED_FIELD_TYPES.BOOLEAN: lensType = 'string'; break; default: @@ -228,16 +229,20 @@ function getColumnsAndLayer( ): ColumnsAndLayer | undefined { if (item.fieldName === undefined) return; - if (fieldType === JOB_FIELD_TYPES.DATE) { + if (fieldType === SUPPORTED_FIELD_TYPES.DATE) { return getDateSettings(item); } - if (fieldType === JOB_FIELD_TYPES.NUMBER) { + if (fieldType === SUPPORTED_FIELD_TYPES.NUMBER) { return getNumberSettings(item, defaultDataView); } - if (fieldType === JOB_FIELD_TYPES.IP || fieldType === JOB_FIELD_TYPES.KEYWORD) { + if ( + fieldType === SUPPORTED_FIELD_TYPES.IP || + fieldType === SUPPORTED_FIELD_TYPES.KEYWORD || + fieldType === SUPPORTED_FIELD_TYPES.VERSION + ) { return getKeywordSettings(item); } - if (fieldType === JOB_FIELD_TYPES.BOOLEAN) { + if (fieldType === SUPPORTED_FIELD_TYPES.BOOLEAN) { return getBooleanSettings(item); } } diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/field_type_icon/field_type_icon.test.tsx b/x-pack/plugins/data_visualizer/public/application/common/components/field_type_icon/field_type_icon.test.tsx index 874cdaa670c49..9962937fa80dc 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/field_type_icon/field_type_icon.test.tsx +++ b/x-pack/plugins/data_visualizer/public/application/common/components/field_type_icon/field_type_icon.test.tsx @@ -9,12 +9,12 @@ import React from 'react'; import { mount, shallow } from 'enzyme'; import { FieldTypeIcon } from './field_type_icon'; -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; describe('FieldTypeIcon', () => { test(`render component when type matches a field type`, () => { const typeIconComponent = shallow( - + ); expect(typeIconComponent).toMatchSnapshot(); }); @@ -24,7 +24,7 @@ describe('FieldTypeIcon', () => { jest.useFakeTimers(); const typeIconComponent = mount( - + ); expect(typeIconComponent.find('EuiToolTip').children()).toHaveLength(1); diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/create_fields.ts b/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/create_fields.ts index 05d07111c80ac..2ac163104eea5 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/create_fields.ts +++ b/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/create_fields.ts @@ -8,7 +8,7 @@ import { FindFileStructureResponse } from '@kbn/file-upload-plugin/common'; import { getFieldNames, getSupportedFieldType } from './get_field_names'; import { FileBasedFieldVisConfig } from '../stats_table/types'; -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; import { roundToDecimalPlace } from '../utils'; export function createFields(results: FindFileStructureResponse) { @@ -28,20 +28,20 @@ export function createFields(results: FindFileStructureResponse) { if (fieldStats[name] !== undefined) { const field: FileBasedFieldVisConfig = { fieldName: name, - type: JOB_FIELD_TYPES.UNKNOWN, + type: SUPPORTED_FIELD_TYPES.UNKNOWN, }; const f = fieldStats[name]; const m = mappings.properties[name]; // sometimes the timestamp field is not in the mappings, and so our // collection of fields will be missing a time field with a type of date - if (name === timestampField && field.type === JOB_FIELD_TYPES.UNKNOWN) { - field.type = JOB_FIELD_TYPES.DATE; + if (name === timestampField && field.type === SUPPORTED_FIELD_TYPES.UNKNOWN) { + field.type = SUPPORTED_FIELD_TYPES.DATE; } if (m !== undefined) { field.type = getSupportedFieldType(m.type); - if (field.type === JOB_FIELD_TYPES.NUMBER) { + if (field.type === SUPPORTED_FIELD_TYPES.NUMBER) { numericFieldsCount += 1; } if (m.format !== undefined) { @@ -71,7 +71,7 @@ export function createFields(results: FindFileStructureResponse) { } if (f.top_hits !== undefined) { - if (field.type === JOB_FIELD_TYPES.TEXT) { + if (field.type === SUPPORTED_FIELD_TYPES.TEXT) { _stats = { ..._stats, examples: f.top_hits.map((hit) => hit.value), @@ -84,7 +84,7 @@ export function createFields(results: FindFileStructureResponse) { } } - if (field.type === JOB_FIELD_TYPES.DATE) { + if (field.type === SUPPORTED_FIELD_TYPES.DATE) { _stats = { ..._stats, earliest: f.earliest, @@ -99,9 +99,9 @@ export function createFields(results: FindFileStructureResponse) { // this could be the message field for a semi-structured log file or a // field which the endpoint has not been able to work out any information for const type = - mappings.properties[name] && mappings.properties[name].type === JOB_FIELD_TYPES.TEXT - ? JOB_FIELD_TYPES.TEXT - : JOB_FIELD_TYPES.UNKNOWN; + mappings.properties[name] && mappings.properties[name].type === SUPPORTED_FIELD_TYPES.TEXT + ? SUPPORTED_FIELD_TYPES.TEXT + : SUPPORTED_FIELD_TYPES.UNKNOWN; return { fieldName: name, diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/filter_fields.ts b/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/filter_fields.ts index 145a8fa5f8867..4ca65eec6635b 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/filter_fields.ts +++ b/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/filter_fields.ts @@ -5,7 +5,7 @@ * 2.0. */ -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; interface CommonFieldConfig { type: string; @@ -32,6 +32,6 @@ export function filterFields( return { filteredFields: items, visibleFieldsCount: items.length, - visibleMetricsCount: items.filter((d) => d.type === JOB_FIELD_TYPES.NUMBER).length, + visibleMetricsCount: items.filter((d) => d.type === SUPPORTED_FIELD_TYPES.NUMBER).length, }; } diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/get_field_names.ts b/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/get_field_names.ts index b6868ced4de69..b0750278ab9e3 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/get_field_names.ts +++ b/x-pack/plugins/data_visualizer/public/application/common/components/fields_stats_grid/get_field_names.ts @@ -9,7 +9,7 @@ import { difference } from 'lodash'; import { ES_FIELD_TYPES } from '@kbn/data-plugin/common'; import type { FindFileStructureResponse } from '@kbn/file-upload-plugin/common'; import type { JobFieldType } from '../../../../../common/types'; -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; export function getFieldNames(results: FindFileStructureResponse) { const { mappings, field_stats: fieldStats, column_names: columnNames } = results; @@ -44,11 +44,11 @@ export function getSupportedFieldType(type: string): JobFieldType { case ES_FIELD_TYPES.LONG: case ES_FIELD_TYPES.SHORT: case ES_FIELD_TYPES.UNSIGNED_LONG: - return JOB_FIELD_TYPES.NUMBER; + return SUPPORTED_FIELD_TYPES.NUMBER; case ES_FIELD_TYPES.DATE: case ES_FIELD_TYPES.DATE_NANOS: - return JOB_FIELD_TYPES.DATE; + return SUPPORTED_FIELD_TYPES.DATE; default: return type as JobFieldType; diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/_index.scss b/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/_index.scss index 7ac8aa4365732..5aaf24b82a1a6 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/_index.scss +++ b/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/_index.scss @@ -31,9 +31,8 @@ $panelWidthL: #{'max(40%, 450px)'}; } .euiTableRow > .euiTableRowCell { - border-bottom: 0; - border-top: $euiBorderThin; - + border-top: 0; + border-bottom: $euiBorderThin; } .euiTableCellContent { diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/components/field_data_expanded_row/boolean_content.tsx b/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/components/field_data_expanded_row/boolean_content.tsx index 907bc6166afff..210f69c435a45 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/components/field_data_expanded_row/boolean_content.tsx +++ b/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/components/field_data_expanded_row/boolean_content.tsx @@ -5,18 +5,13 @@ * 2.0. */ -import React, { FC, ReactNode, useMemo } from 'react'; -import { - EuiBasicTable, - EuiSpacer, - RIGHT_ALIGNMENT, - LEFT_ALIGNMENT, - HorizontalAlignment, -} from '@elastic/eui'; +import React, { FC, useMemo } from 'react'; +import { EuiSpacer } from '@elastic/eui'; import { Axis, BarSeries, Chart, Settings, ScaleType } from '@elastic/charts'; import { FormattedMessage } from '@kbn/i18n-react'; import { i18n } from '@kbn/i18n'; +import { TopValues } from '../../../top_values'; import type { FieldDataRowProps } from '../../types/field_data_row'; import { ExpandedRowFieldHeader } from '../expanded_row_field_header'; import { getTFPercentage } from '../../utils'; @@ -44,72 +39,42 @@ function getFormattedValue(value: number, totalCount: number): string { const BOOLEAN_DISTRIBUTION_CHART_HEIGHT = 70; -export const BooleanContent: FC = ({ config }) => { +export const BooleanContent: FC = ({ config, onAddFilter }) => { const fieldFormat = 'fieldFormat' in config ? config.fieldFormat : undefined; const formattedPercentages = useMemo(() => getTFPercentage(config), [config]); const theme = useDataVizChartTheme(); if (!formattedPercentages) return null; const { trueCount, falseCount, count } = formattedPercentages; - const summaryTableItems = [ - { - function: 'true', - display: ( - - ), - value: getFormattedValue(trueCount, count), - }, - { - function: 'false', - display: ( - - ), - value: getFormattedValue(falseCount, count), - }, - ]; - const summaryTableColumns = [ - { - field: 'function', - name: '', - render: (_: string, summaryItem: { display: ReactNode }) => summaryItem.display, - width: '25px', - align: LEFT_ALIGNMENT as HorizontalAlignment, - }, - { - field: 'value', - name: '', - render: (v: string) => {v}, - align: RIGHT_ALIGNMENT as HorizontalAlignment, - }, - ]; - - const summaryTableTitle = i18n.translate( - 'xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.summaryTableTitle', - { - defaultMessage: 'Summary', - } - ); - + const stats = { + ...config.stats, + topValues: [ + { + key: i18n.translate( + 'xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.trueCountLabel', + { defaultMessage: 'true' } + ), + doc_count: trueCount ?? 0, + }, + { + key: i18n.translate( + 'xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.falseCountLabel', + { defaultMessage: 'false' } + ), + doc_count: falseCount ?? 0, + }, + ], + }; return ( - - {summaryTableTitle} - - + diff --git a/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/data_visualizer_stats_table.tsx b/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/data_visualizer_stats_table.tsx index a2d61d104d138..8b38563591e3d 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/data_visualizer_stats_table.tsx +++ b/x-pack/plugins/data_visualizer/public/application/common/components/stats_table/data_visualizer_stats_table.tsx @@ -20,11 +20,13 @@ import { RIGHT_ALIGNMENT, EuiResizeObserver, EuiLoadingSpinner, + useEuiTheme, } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; import { EuiTableComputedColumnType } from '@elastic/eui/src/components/basic_table/table_types'; import { throttle } from 'lodash'; -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { css } from '@emotion/react'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; import type { JobFieldType, DataVisualizerTableState } from '../../../../../common/types'; import { DocumentStat } from './components/field_data_row/document_stats'; import { IndexBasedNumberContentPreview } from './components/field_data_row/number_content_preview'; @@ -70,6 +72,8 @@ export const DataVisualizerTable = ({ onChange, loading, }: DataVisualizerTableProps) => { + const { euiTheme } = useEuiTheme(); + const [expandedRowItemIds, setExpandedRowItemIds] = useState([]); const [expandAll, setExpandAll] = useState(false); @@ -289,13 +293,14 @@ export const DataVisualizerTable = ({ } if ( - (item.type === JOB_FIELD_TYPES.KEYWORD || item.type === JOB_FIELD_TYPES.IP) && + (item.type === SUPPORTED_FIELD_TYPES.KEYWORD || + item.type === SUPPORTED_FIELD_TYPES.IP) && item.stats?.topValues !== undefined ) { return ; } - if (item.type === JOB_FIELD_TYPES.NUMBER) { + if (item.type === SUPPORTED_FIELD_TYPES.NUMBER) { if (isIndexBasedFieldVisConfig(item) && item.stats?.distribution !== undefined) { // If the cardinality is only low, show the top values instead of a distribution chart return item.stats?.distribution?.percentiles.length <= 2 ? ( @@ -308,7 +313,7 @@ export const DataVisualizerTable = ({ } } - if (item.type === JOB_FIELD_TYPES.BOOLEAN) { + if (item.type === SUPPORTED_FIELD_TYPES.BOOLEAN) { return ; } @@ -361,6 +366,18 @@ export const DataVisualizerTable = ({ rowProps={(item) => ({ 'data-test-subj': `dataVisualizerRow row-${item.fieldName}`, })} + css={css` + thead { + position: sticky; + inset-block-start: 0; + z-index: 1; + background-color: ${euiTheme.colors.emptyShade}; + box-shadow: inset 0 0px 0, inset 0 -1px 0 ${euiTheme.border.color}; + } + .euiTableRow > .euiTableRowCel { + border-top: 0px; + } + `} /> )} diff --git a/x-pack/plugins/data_visualizer/public/application/common/util/example_utils.test.ts b/x-pack/plugins/data_visualizer/public/application/common/util/example_utils.test.ts new file mode 100644 index 0000000000000..bc1c489cd77a0 --- /dev/null +++ b/x-pack/plugins/data_visualizer/public/application/common/util/example_utils.test.ts @@ -0,0 +1,153 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { getUniqGeoOrStrExamples } from './example_utils'; + +describe('example utils', () => { + describe('getUniqGeoOrStrExamples', () => { + test('should remove duplicated strings up to maxExamples', () => { + expect( + getUniqGeoOrStrExamples( + [ + 'deb', + '', + 'css', + 'deb', + '', + '', + 'deb', + 'gz', + '', + 'gz', + '', + 'deb', + 'gz', + 'deb', + '', + 'deb', + 'deb', + '', + 'gz', + 'gz', + ], + 20 + ) + ).toMatchObject(['deb', '', 'css', 'gz']); + expect( + getUniqGeoOrStrExamples( + [ + 'deb', + '', + 'css', + 'deb', + '', + '', + 'deb', + 'gz', + '', + 'gz', + '', + 'deb', + 'gz', + 'deb', + '', + 'deb', + 'deb', + '', + 'gz', + 'gz', + ], + 2 + ) + ).toMatchObject(['deb', '']); + }); + + test('should remove duplicated coordinates up to maxExamples', () => { + expect( + getUniqGeoOrStrExamples([ + { coordinates: [0.1, 2343], type: 'Point' }, + { coordinates: [0.1, 2343], type: 'Point' }, + { coordinates: [0.1, 2343], type: 'Point' }, + { coordinates: [0.1, 2343], type: 'Shape' }, + { coordinates: [0.1, 2343] }, + { coordinates: [4321, 2343], type: 'Point' }, + { coordinates: [4321, 2343], type: 'Point' }, + ]) + ).toMatchObject([ + { + coordinates: [0.1, 2343], + type: 'Point', + }, + { + coordinates: [0.1, 2343], + type: 'Shape', + }, + { + coordinates: [0.1, 2343], + }, + { + coordinates: [4321, 2343], + type: 'Point', + }, + ]); + expect( + getUniqGeoOrStrExamples([ + { coordinates: [1, 2, 3], type: 'Point' }, + { coordinates: [1, 2, 3], type: 'Point' }, + { coordinates: [1, 2, 3], type: 'Point' }, + { coordinates: [1, 2, 3, 4], type: 'Shape' }, + { coordinates: [1, 2, 3, 4] }, + ]) + ).toMatchObject([ + { + coordinates: [1, 2, 3], + type: 'Point', + }, + { coordinates: [1, 2, 3, 4], type: 'Shape' }, + { coordinates: [1, 2, 3, 4] }, + ]); + }); + + test('should remove duplicated lon/lat coordinates up to maxExamples', () => { + expect( + getUniqGeoOrStrExamples([ + { lon: 0.1, lat: 2343 }, + { lon: 0.1, lat: 2343 }, + { lon: 0.1, lat: 2343 }, + { lon: 0.1, lat: 2343 }, + { lon: 0.1, lat: 2343 }, + { lon: 4321, lat: 2343 }, + { lon: 4321, lat: 2343 }, + ]) + ).toMatchObject([ + { lon: 0.1, lat: 2343 }, + { lon: 4321, lat: 2343 }, + ]); + expect( + getUniqGeoOrStrExamples( + [ + { lon: 1, lat: 2 }, + { lon: 1, lat: 2 }, + { lon: 2, lat: 3 }, + { lon: 2, lat: 3 }, + { lon: 3, lat: 4 }, + { lon: 3, lat: 4 }, + { lon: 4, lat: 5 }, + { lon: 4, lat: 5 }, + { lon: 5, lat: 6 }, + { lon: 5, lat: 6 }, + ], + 3 + ) + ).toMatchObject([ + { lon: 1, lat: 2 }, + { lon: 2, lat: 3 }, + { lon: 3, lat: 4 }, + ]); + }); + }); +}); diff --git a/x-pack/plugins/data_visualizer/public/application/common/util/example_utils.ts b/x-pack/plugins/data_visualizer/public/application/common/util/example_utils.ts new file mode 100644 index 0000000000000..cc4a9a3ca9bfa --- /dev/null +++ b/x-pack/plugins/data_visualizer/public/application/common/util/example_utils.ts @@ -0,0 +1,58 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { isPopulatedObject } from '@kbn/ml-is-populated-object'; +import { isDefined } from './is_defined'; +import { GeoPointExample, LatLongExample } from '../../../../common/types/field_request_config'; + +export function isGeoPointExample(arg: unknown): arg is GeoPointExample { + return isPopulatedObject(arg, ['coordinates']) && Array.isArray(arg.coordinates); +} + +export function isLonLatExample(arg: unknown): arg is LatLongExample { + return isPopulatedObject(arg, ['lon', 'lat']); +} + +export function getUniqGeoOrStrExamples( + examples: Array | undefined, + maxExamples = 10 +): Array { + const uniqueCoordinates: Array = []; + if (!isDefined(examples)) return uniqueCoordinates; + for (let i = 0; i < examples.length; i++) { + const example = examples[i]; + if (typeof example === 'string' && uniqueCoordinates.indexOf(example) === -1) { + uniqueCoordinates.push(example); + } else { + if ( + isGeoPointExample(example) && + uniqueCoordinates.findIndex( + (c) => + isGeoPointExample(c) && + c.type === example.type && + example.coordinates.every((coord, idx) => coord === c.coordinates[idx]) + ) === -1 + ) { + uniqueCoordinates.push(example); + } + + if ( + isLonLatExample(example) && + uniqueCoordinates.findIndex( + (c) => isLonLatExample(c) && example.lon === c.lon && example.lat === c.lat + ) === -1 + ) { + uniqueCoordinates.push(example); + } + } + if (uniqueCoordinates.length === maxExamples) { + return uniqueCoordinates; + } + } + + return uniqueCoordinates; +} diff --git a/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.test.ts b/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.test.ts index 8f9e4ffd3b898..0f3ae62eae209 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.test.ts +++ b/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.test.ts @@ -5,24 +5,26 @@ * 2.0. */ -import { JOB_FIELD_TYPES } from '../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../common/constants'; import { getJobTypeLabel, jobTypeLabels } from './field_types_utils'; describe('field type utils', () => { describe('getJobTypeLabel: Getting a field type aria label by passing what it is stored in constants', () => { - test('should returns all JOB_FIELD_TYPES labels exactly as it is for each correct value', () => { - const keys = Object.keys(JOB_FIELD_TYPES); + test('should returns all SUPPORTED_FIELD_TYPES labels exactly as it is for each correct value', () => { + const keys = Object.keys(SUPPORTED_FIELD_TYPES); const receivedLabels: Record = {}; const testStorage = jobTypeLabels; keys.forEach((key) => { - const constant = key as keyof typeof JOB_FIELD_TYPES; - receivedLabels[JOB_FIELD_TYPES[constant]] = getJobTypeLabel(JOB_FIELD_TYPES[constant]); + const constant = key as keyof typeof SUPPORTED_FIELD_TYPES; + receivedLabels[SUPPORTED_FIELD_TYPES[constant]] = getJobTypeLabel( + SUPPORTED_FIELD_TYPES[constant] + ); }); expect(receivedLabels).toEqual(testStorage); }); - test('should returns NULL as JOB_FIELD_TYPES does not contain such a keyword', () => { - expect(getJobTypeLabel('JOB_FIELD_TYPES')).toBe(null); + test('should returns NULL as SUPPORTED_FIELD_TYPES does not contain such a keyword', () => { + expect(getJobTypeLabel('SUPPORTED_FIELD_TYPES')).toBe(null); }); }); }); diff --git a/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.ts b/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.ts index d9617ae61e2ec..5d1293f0a22b3 100644 --- a/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.ts +++ b/x-pack/plugins/data_visualizer/public/application/common/util/field_types_utils.ts @@ -8,52 +8,70 @@ import { i18n } from '@kbn/i18n'; import { DataViewField } from '@kbn/data-views-plugin/public'; import { KBN_FIELD_TYPES } from '@kbn/data-plugin/common'; -import { JOB_FIELD_TYPES } from '../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../common/constants'; export const getJobTypeLabel = (type: string) => { return type in jobTypeLabels ? jobTypeLabels[type as keyof typeof jobTypeLabels] : null; }; export const jobTypeLabels = { - [JOB_FIELD_TYPES.BOOLEAN]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.booleanTypeLabel', { - defaultMessage: 'Boolean', - }), - [JOB_FIELD_TYPES.DATE]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.dateTypeLabel', { + [SUPPORTED_FIELD_TYPES.BOOLEAN]: i18n.translate( + 'xpack.dataVisualizer.fieldTypeIcon.booleanTypeLabel', + { + defaultMessage: 'Boolean', + } + ), + [SUPPORTED_FIELD_TYPES.DATE]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.dateTypeLabel', { defaultMessage: 'Date', }), - [JOB_FIELD_TYPES.GEO_POINT]: i18n.translate( + [SUPPORTED_FIELD_TYPES.GEO_POINT]: i18n.translate( 'xpack.dataVisualizer.fieldTypeIcon.geoPointTypeLabel', { defaultMessage: 'Geo point', } ), - [JOB_FIELD_TYPES.GEO_SHAPE]: i18n.translate( + [SUPPORTED_FIELD_TYPES.GEO_SHAPE]: i18n.translate( 'xpack.dataVisualizer.fieldTypeIcon.geoShapeTypeLabel', { defaultMessage: 'Geo shape', } ), - [JOB_FIELD_TYPES.IP]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.ipTypeLabel', { + [SUPPORTED_FIELD_TYPES.IP]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.ipTypeLabel', { defaultMessage: 'IP', }), - [JOB_FIELD_TYPES.KEYWORD]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.keywordTypeLabel', { - defaultMessage: 'Keyword', - }), - [JOB_FIELD_TYPES.NUMBER]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.numberTypeLabel', { - defaultMessage: 'Number', - }), - [JOB_FIELD_TYPES.HISTOGRAM]: i18n.translate( + [SUPPORTED_FIELD_TYPES.KEYWORD]: i18n.translate( + 'xpack.dataVisualizer.fieldTypeIcon.keywordTypeLabel', + { + defaultMessage: 'Keyword', + } + ), + [SUPPORTED_FIELD_TYPES.NUMBER]: i18n.translate( + 'xpack.dataVisualizer.fieldTypeIcon.numberTypeLabel', + { + defaultMessage: 'Number', + } + ), + [SUPPORTED_FIELD_TYPES.HISTOGRAM]: i18n.translate( 'xpack.dataVisualizer.fieldTypeIcon.histogramTypeLabel', { defaultMessage: 'Histogram', } ), - [JOB_FIELD_TYPES.TEXT]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.textTypeLabel', { + [SUPPORTED_FIELD_TYPES.TEXT]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.textTypeLabel', { defaultMessage: 'Text', }), - [JOB_FIELD_TYPES.UNKNOWN]: i18n.translate('xpack.dataVisualizer.fieldTypeIcon.unknownTypeLabel', { - defaultMessage: 'Unknown', - }), + [SUPPORTED_FIELD_TYPES.UNKNOWN]: i18n.translate( + 'xpack.dataVisualizer.fieldTypeIcon.unknownTypeLabel', + { + defaultMessage: 'Unknown', + } + ), + [SUPPORTED_FIELD_TYPES.VERSION]: i18n.translate( + 'xpack.dataVisualizer.fieldTypeIcon.versionTypeLabel', + { + defaultMessage: 'Version', + } + ), }; // convert kibana types to ML Job types @@ -62,30 +80,35 @@ export const jobTypeLabels = { export function kbnTypeToJobType(field: DataViewField) { // Return undefined if not one of the supported data visualizer field types. let type; + switch (field.type) { case KBN_FIELD_TYPES.STRING: - type = field.aggregatable ? JOB_FIELD_TYPES.KEYWORD : JOB_FIELD_TYPES.TEXT; + type = field.aggregatable ? SUPPORTED_FIELD_TYPES.KEYWORD : SUPPORTED_FIELD_TYPES.TEXT; + + if (field.esTypes?.includes(SUPPORTED_FIELD_TYPES.VERSION)) { + type = SUPPORTED_FIELD_TYPES.VERSION; + } break; case KBN_FIELD_TYPES.NUMBER: - type = JOB_FIELD_TYPES.NUMBER; + type = SUPPORTED_FIELD_TYPES.NUMBER; break; case KBN_FIELD_TYPES.DATE: - type = JOB_FIELD_TYPES.DATE; + type = SUPPORTED_FIELD_TYPES.DATE; break; case KBN_FIELD_TYPES.IP: - type = JOB_FIELD_TYPES.IP; + type = SUPPORTED_FIELD_TYPES.IP; break; case KBN_FIELD_TYPES.BOOLEAN: - type = JOB_FIELD_TYPES.BOOLEAN; + type = SUPPORTED_FIELD_TYPES.BOOLEAN; break; case KBN_FIELD_TYPES.GEO_POINT: - type = JOB_FIELD_TYPES.GEO_POINT; + type = SUPPORTED_FIELD_TYPES.GEO_POINT; break; case KBN_FIELD_TYPES.GEO_SHAPE: - type = JOB_FIELD_TYPES.GEO_SHAPE; + type = SUPPORTED_FIELD_TYPES.GEO_SHAPE; break; case KBN_FIELD_TYPES.HISTOGRAM: - type = JOB_FIELD_TYPES.HISTOGRAM; + type = SUPPORTED_FIELD_TYPES.HISTOGRAM; break; default: diff --git a/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/components/index_data_visualizer_view/index_data_visualizer_view.tsx b/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/components/index_data_visualizer_view/index_data_visualizer_view.tsx index 0b4103687bbde..079804a47cd7b 100644 --- a/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/components/index_data_visualizer_view/index_data_visualizer_view.tsx +++ b/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/components/index_data_visualizer_view/index_data_visualizer_view.tsx @@ -399,7 +399,7 @@ export const IndexDataVisualizerView: FC = (dataVi
    -

    {currentDataView.title}

    +

    {currentDataView.getName()}

    { const fieldData = nonMetricFieldData.find((f) => f.fieldName === field.spec.name); - const nonMetricConfig: Partial = { ...(fieldData ? fieldData : {}), fieldFormat: currentDataView.getFormatterForField(field), diff --git a/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_field_examples.ts b/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_field_examples.ts index 0e04665256e20..dfc68e6dac9ae 100644 --- a/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_field_examples.ts +++ b/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_field_examples.ts @@ -15,6 +15,8 @@ import type { ISearchStart, } from '@kbn/data-plugin/public'; import { isPopulatedObject } from '@kbn/ml-is-populated-object'; +import type { SearchHit } from '@elastic/elasticsearch/lib/api/typesWithBodyKey'; +import { getUniqGeoOrStrExamples } from '../../../common/util/example_utils'; import { buildBaseFilterCriteria } from '../../../../../common/utils/query_utils'; import type { Field, @@ -90,20 +92,11 @@ export const fetchFieldsExamples = ( if (body.hits.total > 0) { const hits = body.hits.hits; - for (let i = 0; i < hits.length; i++) { - // Use lodash get() to support field names containing dots. - const doc: object[] | undefined = get(hits[i].fields, field.fieldName); - // the results from fields query is always an array - if (Array.isArray(doc) && doc.length > 0) { - const example = doc[0]; - if (example !== undefined && stats.examples.indexOf(example) === -1) { - stats.examples.push(example); - if (stats.examples.length === maxExamples) { - break; - } - } - } - } + const processedDocs = hits.map((hit: SearchHit) => { + const doc: object[] | undefined = get(hit.fields, field.fieldName); + return Array.isArray(doc) && doc.length > 0 ? doc[0] : doc; + }); + stats.examples = getUniqGeoOrStrExamples(processedDocs, maxExamples); } return stats; diff --git a/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_fields_stats.ts b/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_fields_stats.ts index 4dd0b3a7ba40a..a549e40704c0f 100644 --- a/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_fields_stats.ts +++ b/x-pack/plugins/data_visualizer/public/application/index_data_visualizer/search_strategy/requests/get_fields_stats.ts @@ -11,7 +11,7 @@ import { ISearchStart } from '@kbn/data-plugin/public'; import type { FieldStatsCommonRequestParams } from '../../../../../common/types/field_stats'; import type { FieldStatsError } from '../../../../../common/types/field_stats'; import type { FieldStats } from '../../../../../common/types/field_stats'; -import { JOB_FIELD_TYPES } from '../../../../../common/constants'; +import { SUPPORTED_FIELD_TYPES } from '../../../../../common/constants'; import { fetchDateFieldsStats } from './get_date_field_stats'; import { fetchBooleanFieldsStats } from './get_boolean_field_stats'; import { fetchFieldsExamples } from './get_field_examples'; @@ -31,16 +31,17 @@ export const getFieldsStats = ( ): Observable | undefined => { const fieldType = fields[0].type; switch (fieldType) { - case JOB_FIELD_TYPES.NUMBER: + case SUPPORTED_FIELD_TYPES.NUMBER: return fetchNumericFieldsStats(dataSearch, params, fields, options); - case JOB_FIELD_TYPES.KEYWORD: - case JOB_FIELD_TYPES.IP: + case SUPPORTED_FIELD_TYPES.KEYWORD: + case SUPPORTED_FIELD_TYPES.IP: + case SUPPORTED_FIELD_TYPES.VERSION: return fetchStringFieldsStats(dataSearch, params, fields, options); - case JOB_FIELD_TYPES.DATE: + case SUPPORTED_FIELD_TYPES.DATE: return fetchDateFieldsStats(dataSearch, params, fields, options); - case JOB_FIELD_TYPES.BOOLEAN: + case SUPPORTED_FIELD_TYPES.BOOLEAN: return fetchBooleanFieldsStats(dataSearch, params, fields, options); - case JOB_FIELD_TYPES.TEXT: + case SUPPORTED_FIELD_TYPES.TEXT: return fetchFieldsExamples(dataSearch, params, fields, options); default: // Use an exists filter on the the field name to get diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index e36d4abb75a1c..780ea4fe5f40c 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -10516,7 +10516,6 @@ "xpack.dataVisualizer.dataGrid.field.topValues.calculatedFromSampleDescription": "Calculé à partir d'un échantillon de {topValuesSamplerShardSize} documents par partition", "xpack.dataVisualizer.dataGrid.field.topValuesLabel": "Valeurs les plus élevées", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.falseCountLabel": "faux", - "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.summaryTableTitle": "Résumé", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.trueCountLabel": "vrai", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.choroplethMapTopValues.calculatedFromSampleDescription": "Calculé à partir d'un échantillon de {topValuesSamplerShardSize} documents par partition", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.documentStatsTable.countLabel": "compte", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index cc42d39638c58..5f076322b4917 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -10508,7 +10508,6 @@ "xpack.dataVisualizer.dataGrid.field.topValues.calculatedFromSampleDescription": "1 つのシャードにつき {topValuesSamplerShardSize} のドキュメントのサンプルで計算されています", "xpack.dataVisualizer.dataGrid.field.topValuesLabel": "トップの値", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.falseCountLabel": "false", - "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.summaryTableTitle": "まとめ", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.trueCountLabel": "true", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.choroplethMapTopValues.calculatedFromSampleDescription": "1 つのシャードにつき {topValuesSamplerShardSize} のドキュメントのサンプルで計算されています", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.documentStatsTable.countLabel": "カウント", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index a0848f0acf9ad..5f8dc58573275 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -10523,7 +10523,6 @@ "xpack.dataVisualizer.dataGrid.field.topValues.calculatedFromSampleDescription": "基于每个分片的 {topValuesSamplerShardSize} 文档样例计算", "xpack.dataVisualizer.dataGrid.field.topValuesLabel": "排名最前值", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.falseCountLabel": "false", - "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.summaryTableTitle": "摘要", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.booleanContent.trueCountLabel": "true", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.choroplethMapTopValues.calculatedFromSampleDescription": "基于每个分片的 {topValuesSamplerShardSize} 文档样例计算", "xpack.dataVisualizer.dataGrid.fieldExpandedRow.documentStatsTable.countLabel": "计数", From cc6d132ee7491030ca987083cd40a553e5cf028f Mon Sep 17 00:00:00 2001 From: Candace Park <56409205+parkiino@users.noreply.github.com> Date: Thu, 14 Jul 2022 16:33:51 -0400 Subject: [PATCH 050/111] [Security Solution][Responder Console] Input area has arrow submit button (#136233) --- .../command_input/command_input.test.tsx | 26 ++++++++++++++- .../command_input/command_input.tsx | 32 ++++++++++++++++++- 2 files changed, 56 insertions(+), 2 deletions(-) diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx index a06d6ae7c38b7..2701ebdb136b5 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.test.tsx @@ -10,7 +10,7 @@ import type { ConsoleTestSetup } from '../../mocks'; import { getConsoleTestSetup } from '../../mocks'; import type { ConsoleProps } from '../../types'; import { INPUT_DEFAULT_PLACEHOLDER_TEXT } from '../console_state/state_update_handlers/handle_input_area_state'; -import { waitFor } from '@testing-library/react'; +import { act, waitFor } from '@testing-library/react'; import userEvent from '@testing-library/user-event'; describe('When entering data into the Console input', () => { @@ -92,6 +92,30 @@ describe('When entering data into the Console input', () => { expect(getFooterText()).toEqual('Unknown command abc'); }); + it('should show the arrow button as not disabled if input has text entered', () => { + render(); + enterCommand('cm ', { inputOnly: true }); + + const arrowButton = renderResult.getByTestId('test-inputTextSubmitButton'); + expect(arrowButton).not.toBeDisabled(); + }); + + it('should show the arrow button as disabled if input area is blank', () => { + render(); + + const arrowButton = renderResult.getByTestId('test-inputTextSubmitButton'); + expect(arrowButton).toBeDisabled(); + }); + + it('should execute correct command if arrow button is clicked', () => { + render(); + enterCommand('isolate', { inputOnly: true }); + act(() => { + renderResult.getByTestId('test-inputTextSubmitButton').click(); + }); + expect(renderResult.getByTestId('test-userCommandText').textContent).toEqual('isolate'); + }); + // FIXME:PT uncomment once task OLM task #4384 is implemented it.skip('should display the input history popover when UP key is pressed', async () => { render(); diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx index 89ba5f6561435..a4ff5b03b45e8 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/command_input/command_input.tsx @@ -8,7 +8,7 @@ import type { MouseEventHandler } from 'react'; import React, { memo, useCallback, useEffect, useMemo, useRef, useState } from 'react'; import type { CommonProps } from '@elastic/eui'; -import { EuiFlexGroup, EuiFlexItem, useResizeObserver } from '@elastic/eui'; +import { EuiFlexGroup, EuiFlexItem, useResizeObserver, EuiButtonIcon } from '@elastic/eui'; import styled from 'styled-components'; import classNames from 'classnames'; import type { ConsoleDataState } from '../console_state/types'; @@ -110,6 +110,25 @@ export const CommandInput = memo(({ prompt = '', focusRef, .. }); }, [isKeyInputBeingCaptured]); + const disableArrowButton = useMemo( + () => textEntered.length === 0 && rightOfCursor.text.length === 0, + [rightOfCursor.text.length, textEntered.length] + ); + + const handleSubmitButton = useCallback( + (ev) => { + setCommandToExecute(textEntered + rightOfCursor.text); + dispatch({ + type: 'updateInputTextEnteredState', + payload: { + textEntered: '', + rightOfCursor: undefined, + }, + }); + }, + [dispatch, textEntered, rightOfCursor.text] + ); + const handleKeyCaptureOnStateChange = useCallback>( (isCapturing) => { setIsKeyInputBeingCaptured(isCapturing); @@ -285,6 +304,17 @@ export const CommandInput = memo(({ prompt = '', focusRef, .. + + + Date: Thu, 14 Jul 2022 15:40:54 -0500 Subject: [PATCH 051/111] Bump moment-timezone to 0.5.34 (#136406) Fixes a warning during bootstrap: `info [bazel] warning " > @elastic/charts@46.12.0" has incorrect peer dependency "moment-timezone@^0.5.32".` --- package.json | 4 ++-- yarn.lock | 18 +++++++++--------- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/package.json b/package.json index 9294089cb355a..4f98a16e13959 100644 --- a/package.json +++ b/package.json @@ -412,7 +412,7 @@ "minimatch": "^3.1.2", "moment": "^2.29.4", "moment-duration-format": "^2.3.2", - "moment-timezone": "^0.5.27", + "moment-timezone": "^0.5.34", "monaco-editor": "^0.22.3", "mustache": "^2.3.2", "node-fetch": "^2.6.7", @@ -911,7 +911,7 @@ "@types/mocha": "^9.1.1", "@types/mock-fs": "^4.13.1", "@types/moment-duration-format": "^2.2.3", - "@types/moment-timezone": "^0.5.12", + "@types/moment-timezone": "^0.5.30", "@types/mustache": "^0.8.31", "@types/ncp": "^2.0.1", "@types/nock": "^10.0.3", diff --git a/yarn.lock b/yarn.lock index f8f09a1dab087..83f4084c5dbc6 100644 --- a/yarn.lock +++ b/yarn.lock @@ -7562,12 +7562,12 @@ dependencies: moment ">=2.14.0" -"@types/moment-timezone@^0.5.12": - version "0.5.12" - resolved "https://registry.yarnpkg.com/@types/moment-timezone/-/moment-timezone-0.5.12.tgz#0fb680c03db194fe8ff4551eaeb1eec8d3d80e9f" - integrity sha512-hnHH2+Efg2vExr/dSz+IX860nSiyk9Sk4pJF2EmS11lRpMcNXeB4KBW5xcgw2QPsb9amTXdsVNEe5IoJXiT0uw== +"@types/moment-timezone@^0.5.30": + version "0.5.30" + resolved "https://registry.yarnpkg.com/@types/moment-timezone/-/moment-timezone-0.5.30.tgz#340ed45fe3e715f4a011f5cfceb7cb52aad46fc7" + integrity sha512-aDVfCsjYnAQaV/E9Qc24C5Njx1CoDjXsEgkxtp9NyXDpYu4CCbmclb6QhWloS9UTU/8YROUEEdEkWI0D7DxnKg== dependencies: - moment ">=2.14.0" + moment-timezone "*" "@types/mustache@^0.8.31": version "0.8.31" @@ -21234,10 +21234,10 @@ moment-duration-format@^2.3.2: resolved "https://registry.yarnpkg.com/moment-duration-format/-/moment-duration-format-2.3.2.tgz#5fa2b19b941b8d277122ff3f87a12895ec0d6212" integrity sha512-cBMXjSW+fjOb4tyaVHuaVE/A5TqkukDWiOfxxAjY+PEqmmBQlLwn+8OzwPiG3brouXKY5Un4pBjAeB6UToXHaQ== -moment-timezone@^0.5.27: - version "0.5.27" - resolved "https://registry.yarnpkg.com/moment-timezone/-/moment-timezone-0.5.27.tgz#73adec8139b6fe30452e78f210f27b1f346b8877" - integrity sha512-EIKQs7h5sAsjhPCqN6ggx6cEbs94GK050254TIJySD1bzoM5JTYDwAU1IoVOeTOL6Gm27kYJ51/uuvq1kIlrbw== +moment-timezone@*, moment-timezone@^0.5.34: + version "0.5.34" + resolved "https://registry.yarnpkg.com/moment-timezone/-/moment-timezone-0.5.34.tgz#a75938f7476b88f155d3504a9343f7519d9a405c" + integrity sha512-3zAEHh2hKUs3EXLESx/wsgw6IQdusOT8Bxm3D9UrHPQR7zlMmzwybC8zHEM1tQ4LJwP7fcxrWr8tuBg05fFCbg== dependencies: moment ">= 2.9.0" From 3044cb7ba56a4f5d94bdf22de0be675b23693412 Mon Sep 17 00:00:00 2001 From: Brandon Morelli Date: Thu, 14 Jul 2022 15:04:57 -0600 Subject: [PATCH 052/111] [APM] Document serverless-specific UI (#135178) Co-authored-by: Alexander Wert --- docs/apm/correlations.asciidoc | 6 +-- docs/apm/how-to-guides.asciidoc | 3 ++ docs/apm/images/lambda-cold-start-trace.png | Bin 0 -> 531901 bytes docs/apm/images/lambda-cold-start.png | Bin 0 -> 215264 bytes docs/apm/images/lambda-correlations.png | Bin 0 -> 679193 bytes docs/apm/lambda.asciidoc | 51 ++++++++++++++++++++ docs/apm/service-overview.asciidoc | 35 +++++++++++--- docs/apm/transactions.asciidoc | 7 ++- 8 files changed, 90 insertions(+), 12 deletions(-) create mode 100644 docs/apm/images/lambda-cold-start-trace.png create mode 100644 docs/apm/images/lambda-cold-start.png create mode 100644 docs/apm/images/lambda-correlations.png create mode 100644 docs/apm/lambda.asciidoc diff --git a/docs/apm/correlations.asciidoc b/docs/apm/correlations.asciidoc index cb72a1b305fd7..ca77c6c8c6afb 100644 --- a/docs/apm/correlations.asciidoc +++ b/docs/apm/correlations.asciidoc @@ -21,7 +21,7 @@ NOTE: Queries within the {apm-app} are also applied to the correlations. ==== Find high transaction latency correlations The correlations on the *Latency correlations* tab help you discover which -attributes are contributing to increased transaction latency. +attributes are contributing to increased transaction latency. [role="screenshot"] image::apm/images/correlations-hover.png[Latency correlations] @@ -74,7 +74,7 @@ The table is sorted by scores, which are mapped to high, medium, or low impact levels. Attributes with high impact levels are more likely to contribute to failed transactions. By default, the attribute with the highest score is added to the chart. To see a different attribute in the chart, select its row in the -table. +table. For example, in the screenshot below, there are attributes such as a specific node and pod name that have medium impact on the failed transactions. @@ -86,4 +86,4 @@ Select the `+` filter to create a new query in the {apm-app} for transactions with one or more of these attributes. If you are unfamiliar with a field, click the icon beside its name to view its most popular values and optionally filter on those values too. Each time that you add another attribute, it is filtering -out more and more noise and bringing you closer to a diagnosis. \ No newline at end of file +out more and more noise and bringing you closer to a diagnosis. diff --git a/docs/apm/how-to-guides.asciidoc b/docs/apm/how-to-guides.asciidoc index b634c937588b0..88b331de2acf2 100644 --- a/docs/apm/how-to-guides.asciidoc +++ b/docs/apm/how-to-guides.asciidoc @@ -12,6 +12,7 @@ Learn how to perform common APM app tasks. * <> * <> * <> +* <> * <> * <> @@ -30,6 +31,8 @@ include::correlations.asciidoc[] include::machine-learning.asciidoc[] +include::lambda.asciidoc[] + include::advanced-queries.asciidoc[] include::deployment-annotations.asciidoc[] \ No newline at end of file diff --git a/docs/apm/images/lambda-cold-start-trace.png b/docs/apm/images/lambda-cold-start-trace.png new file mode 100644 index 0000000000000000000000000000000000000000..c6f6efd0557ceca76b22fe21013499418ed92cd8 GIT binary patch literal 531901 zcmeFZby$>L)GrKzfYK-}tsp23A~}?VNQi(mC@m%33=K+m2_xMpDcvp2(A`6K&CEB0 zKJW9q@B966&h?$^`mS@%Gjq+{_l~vJ-uvFU*81IFloX_K?^E1IK|#Tlm623NLBSG7 zLAkSvg@K4cmA~VJf`VgZCLy6DDK$=td3q|@*FNA}?R#X6GB0mVK~tB45%9gW`Zc$9rlFAV-UspRs2 zXvjhDa=wSp3HFWu7{tBtYt{`PC5fhnNR~SPu4rS8Xc7TQJ6UwxFIwTd=oh1yuFZjc z(X#3`Hg8dS_2Et~PH41WVfoQM5YP%-)&AlRIX;TvqxM91a(0^K6_iC)p)VCEDCy$X z{8^&u&33dCv8^a{x<$=XueCFp6JNVKH#0JO;~pBJjOA(<^H8FMx+x7lT{V)R4jm+@ z3%aD|L`hmEd07T!Gw%4}XEm=SZk*UmxR+20bw;38Y%V(H z^NLHB+G!e|m;`6NbU6~Ec~Sb-f8+qYVt%aA8p=z*qd?S-LBLMb zEl#BRA~`dfNTqQo;5l=0)(B|jHRcVAyKuw?;}4Y^Yri{TUuj045;10pzww^TSBfD* zE5m62RX*D;6Faa;PbX+RB*mhr)NXy(#z*uKN#<(T{U4cW_gJo@+@}^@%jCrgnWX&B ziLs(vV=r424r|a3+bZ?r?|xJ}q74^)!T9MjtGn3eAluzZJMWkLZ##~~lnG+Ke+z#1 z*u{p$ZB{&jGNm zWvc3?h)y({E;WZ}A3R)kC%AXC2)t~5ei%{x@BsajB>do)e<NGu#@Kuqo<7H0yP0?w1^6{#A)Ua)kFIju$U%LnJw+Fg8Zt?$GImk5^x(tJO= zrJJUn1U}6W!(7EzU86s~)?R!OF^Y!Y3Z)e^>^!w$SoEut06Z5$aXs_WtYWcxrA7w$ z47a?yFozpUHRT@?6&Q)u;|TaQ_Ic=l?Bm0q*Aq=pgZ`x#Y|{*=0jSoqC&M1(kJ*pUnjLl*+jV%x%fVl zHFa|7O1e_9ugwpNAALwB+SVaDhY0YFXqC$fR`MJ;% z!(-^5Mcy~$Ru0~Ig-6d6aV#TfOX(71PiGyW_%uNItX3n;3toblFX39?Fyu zk~Hk0EK`2X&^<}Yp$D6$26d%}2pQ&a!w( zdh)18vYwghMDZ%3ER01AyN{_Dbm$zSL~`>A67y>F{qwU5zKpNu#pdlQ3FbS#+D+7? z(FnGXKcnl4x?D9|HCioNH9mS`%TyblE?<^)@iyuye@tzR?Q7vRo;B*VqMtv1`v0tU zt^X}a#;}E{cZIzsswHz#oMY6P z*O{1a@ls*S@S=JDMDCdBP)+*b>*zwWqMng&-!(EdvTOB@ql~LbH2S21i#o=WvQ+aN zlpxt^B`E^oRvXNZB=cZZEkJWLb5jH#|y>;)4^%sTQi$>C&wr8Tl=F;X>hZI9*zl) zmeP*4?LZy!vw8g*vG3l^-`n-8TO52918~|1+O*q<140ANLq9WMW;kasOHqa>P&(j) zsrCfF@zon%G%h)XyfwgFL0{SG)C$oGb(4Q1-}>e;Bjk-jl6~@aGDgyRLh%dXPt!(H ze8+qb5{q648lU;3b?I{+k*$Ti3!%0%IR0!`due?9;#dS*E7&mDg`|#kPfPiEVw^@? z0jt(?x5ECy^de*RagDh$MlJ3l{|WP=LCvP>vP#)X4bxH6$ykZF_Nv);`z1W;IB_Rp9F*uwYd1{E zTk%vYRZm&TTb0aF&E4IjoV9it5>6K;ajkH6KRh{#ah-5;bkT4za#nSjGu-A{Nsvp} zsJ}NaHvgjm-wk+jc*1-zwQ-zN5^Y_)kGHUqVJVF*WlaU09Bd7TR8N((ftEl^O+8Hv z%|c$3N>m3=hqxkWYFH1*`%+`urh8n8SBW0u3J{#6?zW}&h){>z4ZItVUhTi>_c&0+ zPYA0LYXGkZd-vWkRx-7t&^H2V@<#d_#xB3Ml`&ga`g(d}sc&C1r5L5uBt^d321QBn zN@olc4i}{Fcc^y-8BiFAJ!f)M-GRQGsp+u^T>f%sa~ON5_(1AOzs$>I8O3i2H4KM3 z%1R^UnRPvmJx8l?4+mmwm@Aq0-}%0KpY0ez&TqV)5Nsx8mR^xWn)iWv__S!Td}7ly>tQo$FSEyMuBA zGbtr;ph%!nA;T|XP?Dj5*>_n`ew05eT=ax&J+(cn#v1J)$f#MJ1v@cx72G;=R>;sz9RsD8T0c-7R%WHgU=!Ll& zc@5>JYb&b51r%!BYVn0I^MQ8WjlS8w7sXkHu_e1t!&$5~O)9M}e-0A2eucz}#nu&s z6p*}c&>PeP8c8e$T!k`H%JF$lKc2QXx0_rK_>{a|&f3oEua#;gKjnHxy3SrX6H*mx zbzQDg-;lwWwysk2-f|ajg{p6RNWeu0{L4m=egFRaxXQjtlS?&hZ$wx>+(f!xh{ zCwLZI4ytW}y@%)(;0@u&@X+FpQn*t1hf>L#$?sw^;8pQlzo2=!>TY`d;kYeU`XubR z;A{S$i>C0hbc2SjCtY=lh9KuzuCleg9!{o`l&^qsM}ec0TJAIxg;b*yVaH$lvrES! z8~D2Vx~BD;E@f%s8K=$G)J;^T#}?)_s}6Zv<>zbbXT!VFCFt7xHoOIQd*1{j zzc4W$Oi29&9sxtG!9rCO`5JNt~B+1K=66vs_#-@Qh0y32_VbUb%Jk=d&};U z^qPG@kD+NEGPu7V|2b>cTM-rK1|oGL8bhUdnweXC}_9wcTi9Q%}~() z7rqw)~9b zgCgWCfVj0Zvj0HqY-wR-C*Ukhf15)9agU5DKmVs9=?uP(1dD`9PGMEin`gN=h; z^dCw8l~mQv$X3GI5+T!GZ;r zmhq>TS;Fo;8 zAbCrD|3Zq;W)bgR8X5~7F1m~iMf+o{)p3`z+EaDCqWsDUnBuvtQ;uL>%1Loaeq-hK z!YMevVX*1^a&Q{arOL}}24;Fn6)+~9$23)AAW|q_wb>y&_gCy+6S#W?VPcSTd9Kqq z#GJ-M*ssI)vx^PxeC>xNZ-9j0%k@j|-_$P$QN%@P^hAJZT%g_py^!#FST_WJL0+c| z{b3?9G7?Pl()xnf08H}0>xm&7*XpUXF7SKU(G^1p;OMH&=^dC8_0>8ua`hDR7o}&% zWMv1s{=LLtoLk!53?xGY*Mqq+hc}{;E>If|ZD8S&SkTh$QOd7h0k}9f>+}y<(p)gO zafH(4-gjE3R2dBoMX(=pi0aZ6JYdN@sUDL!V*slj826q5RTEF7u*bfcP zIj6+tJX64zXfl|YozoPMDs8oXzU1&Viq}=Ju)LP#~BXuHxrP^>HSE5^#ZJD0<5f z*$ii(9l$JyyPj!^^zb4CCxylLmLoD6N&30%z(cG~VFthP*H9jplEs5SJ|lR~Z42V_ z;Vh79ZoK8Wjr z9%b~vDRKLD_yjFF#t_EKTs3$_2}7U{gg=skt0yyjSFl%b5dlm z$ptoWY`w#Kdr1YZBy}IN8+~v3e(rOP+SAXl^5(s(qqOL9)y)Qk73APFDNk%`)QscR$M%cA{_5xg zbC5OT_+3Hvs{kHs%||YZ!HMoT@i^%r3Cu>7g-a?dT4lf%?8VMW6`2l-Q{H?06 zsmz(=d0Mv5{|_u@!cVKKf~oz24p+0roCX_=#&;UtD0{SMn0y!!nA_C)!O-^n21n`# z3zbO!uPEImaV%c;mk#3O$%h``WhNHx+)D8Nz zkRvD!CzHiFXI$C5Gd_$nCI;G7!tv{fX~vX=g$;a{3S_ zmr*@XD9D-!VW%>9%6uKJXC|X^Mgt;dC0`BT?W{-6BoBH;^L?B&Su2g*x5y-9F%pLu2JWrtffcCKSN2}HZXq^tC_*LxF?N`o{gv8in?W&5{;dBZ z5eT~$(Lk&%$eEOCkRUkDQM2cG@ZzLIPD?I^TP@+w)QDW*pOrM-{&ha{dnH#_*bOPE zhix}OM`PumJv1rgC;=Q_asTH(yLxf;ii*Ck^{{@(U_C7JjDKNToE+)`O#v^QA3^qe zK%Kb|(XXIG_pL%rz9Xf(aijLmRPrAWTfTh+CvP|{eY62eN-%Rgx{2NZUH)9+R!jvR-vr~lnfbkeA(qkwuAP$p z%?g6QU2@#NddXJ;_ zQeM@UkjOB4+l#W??)|t66*^y1J_f_%ZpLv`KEsXT{9^$uD;`x`DVYfQd^D@>UplHA z4g|BN`4k}$w8<)%vk@tE`M)5vHNz^rWOQOL^6+Zt1f5h@;-5h`&cMbeU@qnVt z!!9LVb3nyg2Blsuo0F5cY|1-ckJ^%6G556(k7^}ZVWEtqhl>6kvc)kc$$I`kTG86< zCmo7R@QXWthq^fnHDb!&JQ8lm+6q9SWu3KCjWMt zzX!=b#vz{M0#?fc>Ly=}{yMupT}aah)N0K+@Q-HHtqqIG`a5sT(Xa9DpB=^_^ad)} z8o;WDrJKv!-WYiWISa|}z0ATeDCOpDp=(zen%$=+a&%yjBZmFg+*bux)ALAbKOy)# zwoikxg||B*$m45kEt2}jronS)6q&YH4K8;R)=f*xR$0M%#ejT&Z3O?LD``PAfmdVc zsvefsx~SQ_J`TJH`H15J{tnc*wAVTevtF!!* z<(i!}TnKJMwA}M!l;l^b!>kYApL29kBtip#)Lc!GGa~o8!C%F;#n`CU!T2yD!{0oM zlmFYF*sR2-7-PAEdcF zmWJJknXfj(Z{9T$(mywNhx3Ngm(NEQl6oHm@KQ2+M9@zl_Br_@Z4?tlLJ+o@%D>@% z+vDH<@PGAq@UGdaW>lZfHdyY~r%az5x;wN^Bq``d;lM@To)6RSyO?{&82uO{+BjU^ z$29&@&lAQzra53xY6LZc_Pq1_5Lu*D;hI1j)$Gpt_Qz*&eYkT zmZ}o$mcxw^2jZEM2jgwE*~&hwg8&y8LIdD__@?Nm>*SLlgub!o7;!Yt4t@oene&a@ zpwVTo3`d-Tku&Ej^GRF{FfQj^gyQg4Lq}>B zG3PI(8wt}JfV=W-4t&$JFT*}8+<5UhU(OiaJniR+4l^0@!a1ODEuXA6NN~*>Eu$Lz z?j52?elXR21L1#byZm5<<@M6*90S2rF|^iW&2_->Ao#KJgGLVRS4L193^m3sqrO8N z3W8KHa@p%c=nJG>eXMbcGoEU1*;{mRo6=t68#S9S{8sZ%0kfDcIu`}1^C{qu+tzv}+`@+ee*3W4UZ84)oF@Vr z$hG(*^0x_Kr)lJYyTNBF)xQfmJ--8(^Ci&9$QY7S{N=r+mmrvq%2HBxmv{VPezlAc zC)bI$tGm*huj+d?#c;CF3m??e;&n3qm3J&Vd5*17)v`zRJu7jtw1`+QLA8RAWSld` z@R>KF+d2cNd@JWuL>^H>)<-o)L^2Hp{ENo0Yl|-;vZ;J7vt0Kw=f@v?=7xJzNrD~^ zCJR|5qATxz!mCMyi)f`QMs3JbSHHQF=fsOS+Ybb>4m0%}Glpw1dXLp5p;@gr4aRLo zuewBcu}1$Eb-Z9Ack<7|Bwz0TcyjgFWq#GB?{S3dd%Na=oBvaaQ@1+hOYm!=oXIrB zO0&d2dGfSa#3f#eb;?Ejg7!&}hU)Qk2KH$=qJs#mq{S=eXxxmMmyteU{Lynl z5Ag+Q(P7|T++CSaHz6T5ppAXN3t$85{WiU52XdG;^Wn70IcB$D=1F8^zi|HDX*bk@ z#Lzrj2z1N2aYbaPD0nMdqLJo~VnDSx4#fd>z(G`s*@4*hP;MS>>Tk19E%C=8FFg*w z_?K$;%v4-gSr0`6$I1ab4K62hoZ^7BTUF)eq~OK^;1;=1)jmJ~HzD5v8Wwpwpcu4$q1!NNqAhiq>+&oeOTw+A}iE}vVrwi`oH{;iUABR`*0X~=yhn}h* zDcP1UoYItmsU{0u`;)f2`3N851zSOl++QoK>tUm-wntSJ0_6LIYhbA^>o#jH8-R*$ zwzH8}sn2%~f8|kvX<{FJ%d{8*B2)&(mal+?dv`8KiG6sbtpkcj_Gc18!k?QdXiiWb zO%Xi`OsM0Nc)xZ2!Vg9Lllfc9Ba0TBpjtO>`&dtF2`sOyDw0aNL6U#7{o5e__K^RH zu}}(dI!;*wiMS=#z3+B9yWqr1=@@JWE$!3mL0^4}5&((tw7jvfiMgqApdzL&6(yjU z*o!s1=?6~G#0BWd;=2qjttDVS`e+_)-3uvlX;=svuV#WQbY6%W@0fi087_nu8aLrU zVN3ULg3j7=uyW1F8kQhr*pcmtK2x(lbk4V93~zZfU3pdy-^8k)zg_bLYbF*bJl?ej zvpXBsE`D3dv#Y_pDa+NEfUU@LbDOe28$)9-=?=6s)4V@abl5$3396?U-r^zHIeoHp zFPX$nlpLh+HA>_>u1=f9-fg4r<{j5#8l)L2xAI^-*HW9(5bK2<1#;$Px@NB)7J^Sc zi5Kj;&3erKMB*qCX_gvc=KW?~`{L+^((YqC6~-Solv`hvXUJLjhpuRixrM*gzPk%l zz9+(c_4M3h>FW9?<^FRpaL@7Q57h-Hk<=`{$x7PRdCQ$Yj@R$)|`(ViWp^|D7vfnZ2DOr2)?LmcN z&1n{FM_1j%Mu03?@pVUrQV?Cy=k(x)33L|_1ed|qq-q% zO{S;!ZIa`Ta>xhpdb9HiMKg*CL9W2QOWQ@r!Vx-pUgDA4sdLi@v_(N*(Q%hSt#v(w zl^DE@jzvWNNm+Q_dJ<*w7p;=R{Bhi^)z{qN4*C}y-aP7kJ_{6!->iO{qALYZeIx^t zRKm|GU!YWRW2vN^*BjlMmNipQ#ONjD^SiEbDN$y~(er<~{jql!DR|LFrZJAMKm%~S zc7GT6)_&cj#v~fitrWd|=-GzR?1S#GvL45LxY~l@G5O9jG;$BCR1JtZ9k#F_WJt4- zWfaC!d)&=1^_q_qyoudzCSKbjV+HLn$5*| z?hmn+<1stTWk35-q^KMD)0ncE;8;bOvJb~o&)!^!R)! z+oPX3fI++_fCoDGdkGh+6R5E6{hp%lqZe{PSSqp zFe7WG&nvH1bRa7Tp})o-@f|b%%bCkazpH6h4YBq7RVJ-j@|{x8zM-$$bF~%hiV3Oc zc`xY{E)fx&>hbi1^~64}-}mlQz0T5N(qX?7+iB5^d+C?lp6dWe30p+ZmEaYsR<8t& z`%6~R&-QPpqPUd6aRVP19_2m?`cU`_w>khFQPaR~R6t!&10M@WAQjb9KvK70E#}~FJAgh7qQOPS zfZu9^=Vv6<$|U?#z_=feks_vmB-i2Yl z?Y)nFex)Rf7%tE}<{dk3N0j;l{?)$fi6z0pN$>g0#vS)e?L$rYBmPf2;_%1~x}A>D z!(reeVb4k}Txq&puZ!Vh=ip7(*I>CyM_B7kV&Yf@~bnA_P^`{t;WtA)8q$F+=F?)|DX4J1};I z`g4=-PdIdaLHC{KWf5qs!z(bSf`0la_leJ0Yrf?yaC3j(LSrEpK1L`3r}O1`n%@*+ zjURYWUUAl*XMmQIzrclD$PxRD)Djo<%QGg>YJOs{mV%TqCF}YpFGy1z{2`4WflspQ z5;JG=@GI3#oHsr!QBD@i*nD@~sa0Ey=eh|}$@(s0axSD8ROxl@5DTC^`2KZO2QmB* zT7WZ}Pv}#?BH`BtW9tbUH2K(qE5CJd&=0#GP-+_K1I0~pp^_xg2`=$qJr`&!^6ynB zEz);KuFp#m`{yt-JpkT~^vCIR{eCwR4BEuYh=IH|r?P)-gYiOwxTmfjCPY>OD9K)E zZoI6jo4%IaXE?`#9crUC9N)BvkWZL4Oxh8yZmeYpsgZ#(nS$6iC|I#=hhNeownl^1 zznTJA{Z(FBDv;B-tkoMLR$NDGD3!}(+FH!Y=AglWW?^5vpOxVOM3H0<)fwitRHCEH zR=a#$Su!by4-Is~gMZ`O2k-=hgJ3q{OO~NDz0=*xT!jasdpl_X*l`@!G04+H!9oDhB4YJ>3sDHb^xYs6QKl3Vj z^byaIG3vUH{jntC-u`4jtpDzo@fXG%{>{x~-vsQD0U~(?yP;t|Oit3wPVHIa;o8%kT$RAWoJNJBel?Ri`!;ZjC?59S0j~Sl8)jBOg zz>j|g{2$ar^Y$G%)@)AmvI?*ek(=HUN~JlWFurWWGFZ{2T?m=;-sZ!c+TxS+@AftG zm3!Ej5g=GW4y<`k&!4W-$5tw&`?0qFrW)s-c%+Txob>koki={LT{`JcJ(GvvWih%) zzh^|4fs|$Uf@mYGzM9%nw3sy7Q+h}YP=ythHq`m{T@g}Drq;u+B0@zLE31;BIl#MD z)6OLi4BhiN>x(E0oB9EO)tFPJc$D+SE5Wmb>)0mOLyh2#1Suc`G`(NF$qY7W=UOQ)&X2h>_^ga+JZ4 z=sIY`o}&c5D`=ICzr9ryw}5wEJ$ebvN#3=0QYy;DY(!nKaBq|I-!>?1EWjsKZsGQjH#IPuqI zWN@!eU49w_aN{;UYjF~;`}zHndJ!o1$r%lw!|rHkcs%bJD1?1qe;x1*UJl!9fLQNF zRND3oiV(7jWmTYp#c(J}b-~XK;2D^7j&FAlI%1Of0yOy}LG_ess)Gk)7N4STmsTe1 zkB#Cd=^fWzbY)3WTjbQfiMM-2xDeb7kl+-w18{desznWu zu?{8#c||(q;v?wq7&BpVF}az$`2oxGQR~#HS%B-NfO3L8+}Z)2_S_DbG@*ysgd8XK zj%y%xA&yX;tFLxhz=}O@NX)bv1}dYV5JuVA!dWOm?BiDagR`t2j;+oSV@6Tvpu+Pr zdVl@rNu?jT$tPb<`hCc_htPL4>F(I2jr9_IP#u|~3SVM;k(?-ctA(c_d85bD_Fq>6ZiH?L@EP(O7 z`wtEXfi41icw;PC65`|h1{3L1?G8fNZ_Gk;?7+Ds;yTV2rBEoxK-w3-N5J6fm(_JQSW2e zYW#&ux|G;M&AJI8&5vM@6Iyk~6BvE%1St!rTagZEL!1vV3EMoi~@yKQ1C6`DRK~6&w zfGNP8U$3w3i6#O8#0`%j9XN~_ENm)794gWZoc|NB2tVGgc;VJi31Kf}DOtUu6q&c% z67%&gWXp}10zTz*fwqlv7Um!gsR-xhN}I5c>g?V=7}y#qN_0Qq${)+&whlOdfsdwN zN^=&*i;DUB7b+mhnK>~%;jx%>o3TeT0ig>(=!-zp_f4}DbW+d(eXicOBj}JLFZ61X z)HISiGqTlP9SLvn-xdyEtpH-hoYW27JEhO~H;}EMOL+u*h9g!0UYKCd#H1^wC6*DM zx?17KTZGUcT169n!_^fUdegxD1GX~IA1&Fw5}!j|BW(kx``UrB*k!{dQi52Y#=8)v z={YU%Le+aA*?CJ{c$!`Sg{Yo4valoS6$p$}Uk2y{$;P^8A*p14>0u<>G!m~g-TCG> zG|F9kbpY&7Hfwd@5TFnn`7!xrJu`$I`32J;kxJSSvxas`LED@v&i@KxaxX}{60rRX zX7xwO1sJ7XNs8DfFRJBfU1W-%WW=-ngB&}f*?Zi`Uhym4^j4JEttcdt%IzoI-MNd^ zRzeAgoidNlqSPq%bnxkzTd4Mri)hjs%vvdohPT;#c$LBWYbsi-j?iK>wON4-RC}OT zHUpc%^dZ_qa*%B#!e|(MDux~KWz759)BOowDQgvdD=J+J$2f8c0x&)xjDz? z826L5CU4C0AX>*_{KEoP+D+=7L-_mt;?e2`ZB7*tbiI`E`chi5`VRKb_Y>?w3|=@q1=USSMDER z;bOlp_srFFDi$y|nttd>;)@?7?{6^1UU#x>1EvA$?-dq+Cxd$xD@<|OzSmJ9acr;D z9k>WBM5;{Od!^SweXsalOCy#iAk@;WqxKYcBUKcB083U4tvWYHf8+#3ix$FK0tt*x zP3bUnhrB2Xk=Q|i#NJp%eYwfc82|~Lv>uFEcE%gNZRCP01C$NRqko!c6}~vV=hVpc zNtTcuqBuIXYX?OheIa%C*&`6%1B~TxW#-k(Krot#H(!(T7zJyutsA*aoe=zICeI%{ z2Kbynm(m3mdyD!qf)}xlzJHwxta!o0OAR(G)92nly6O8uR)u^p2tSR+f+M1y;}V|x zW_i=^vqG!-WwhpKHbA?epIv>Fvd@x(EYg6p z@JpbNF)5!XBtHXh z0~h4klLTlggIQ;3YTgfZHYjlv%vwnfd6vNsz*4zduzoZ}AMfSQ(7=^1pyR=wLF8=P zbUl5wf=O3Xa?lACtrM>Z8r{#d8L}E5Y#Q@hTVjEK017Y2Mjss)wGstm9Yy(Yg;C5} zM0`Ij#b|vgZGBI|XM~&A+v3#~PsR~F1&*Ih*gTOqMwW^34V`e5>y!~JPumtc&TD{e zuPxE=WK2cL)wsBcPPqKUFdh=#`vk0~!(9vOTrbnVXMPJjW0g}xxXwJ)sfB$SK+Mdf zgFa6Rf5X(C3r``OD(%;<3V5R-*4jeYaizZzXuo-l#6n6Y-V`_496ncX{f$@a8;RCI zSeD-xH)$e;bo}_IkkQj>kFJ3e4c;d5(+pQBSJDtKSH~Wid>yc{Q&l5U>!1=V z+oRCeo|E34hoNsgFT{+?{hN~%l!XynL~Gu**vQkaX9njJ3tOj(2A}5*qhDn`>!TG6 z`Cg&w78-UDTgxHxIq{R2(>`owirtkDH*K#4`r#FP2{U)XIpqK%s^mLjCd05%0nZIS zE4P6U?{zVd86izb3m%qGe``NcJK8U2^sMYp!&H_Q8QUm4K#f-R`h;3rX`VuC!BjOn_9xG6L ziCVFQ`zH$`CZN;mh%Amw!*bYml8v0nIN}UJ1T_o!Demz;pS(z9!oD)#bfaE>tc$cz zx>VSLXJCE@uEz+ZkYIRzN^{oBP2i5j3#&lr7+=1h0B*MtyK?L-hPu5YuA728t90h{ zBMldOuORykdz5sBp>kTHb_D(dHU(Wx+b}d8>|J_I%Pfb+m%*ps=j&%&6XJ;HGp{+7 zN_Nm9J$|w#EX^wgAVG46y!eU0|2+_F|I;u$OZ@G9TUP=fI66jnqzSP-Mq;ZXlSnG~ zuAwSiKL9W4Iz&i$FQQDor#vS`2%k=+(NYxuYlQd4z{R(3h<*+#W|%j~BaeF}NnyBl z0#R%v^ug@QHk_)nIVjiWaO-{j2muuXh2QrEk*>-!ZzGPJT?td#Gv%)2iKvU6!b6Owgpj@xPs(&&Pwb782%2 zi{ysL)SOow=#yQy#DZKuVOvBrKVc$9SEN_eaM)A*l$_Q#1WrS?dnM2e0QJ=ezaOE@%HzQ?q#DTSefm6IXzbnLk&} zb_vz(!te(i-Gx_cYK8y;H(^39ovwNL9$%>>MH+cD|Rr42Ym`-SR;4PJgS&hN7-#M&IOBUBHdx1_pTz=AosQDV~POV9^d zX#C=>+mPz8IjFwVa&>-A_N4dZ0-@n{nt*e|?e8z2#+*8pXaV;<)@rX;uYgAgTb$QP z8)oP1=T1x2g}9C{bfZfSJS7H4gUqWByT)cF0L#ujqXx-%gBMY=NK_4kE~Abh-w)$W($d2?u5i6hC_o3kms-C%Z{!iEsDGJ$kUJcUKzR%yy?Tv>YT^=MS0Dec7+mVlwx|C(tWeQ z1lhO0F~f0#SL(LvTEWbT@4Bgex;vm@s|ohNEhL2QjQgD(-2kItHDtr2ufc1yP&Ry7RjT*S4mY&@Ks4+HJY zJ`X4gWAxs@-%&Kca^iC1sl4}C)c)sZ1SD|;t7Y-wzbL_fag_feP5-}Pai>n`TnWVa z8ZTez5rrrFJrFsbxLCrx@&nDC)J>iZ`OH08QiM;@9TNmQ%(uGRCx2NV27D{BV*Kr- z!}?H{>qCQns0Cu|ikzSd=myltK5Do4e}VkUR{rn|g7E}A0&LyLbIwg%;RCZ^)6}Ol zvk5}SV+OrWAfU3#4MSL*5=D9=Mg7xmHj#O<8oE#toc#JLOTpd(_!UJRXD{aFHK_aw zCOzR{e{(x)gNp&Bu&Rb-S@n7O=~fJs^yUYfT z(66MhT>A4T;B4D8t~{?Jnf3KwCCLfDbQwVvyYOapRrxpqJV;(38AGKC<^Pt^dJCY< z_1SkF$L!0ZX%f@r0<4qfCS>L$c-H4J{plov>7rR?j=7-My5PPrW}JV zb2PiJeq_Ku9+|Zhx8wU91H<|TJ^v-yOM$S`R8?;V2{80)7zSQ5a!pXv& zm7*7zTJWrIrwk{w=(UF%HZeZ6v<~)7@h}Oe3vi{&<_#};;5zKM{#X%#Oo6AZjfBrB z=|cGgWjs^y;$#-zqRk{9f)2Vf`i?u{5<77@A4fJgq(mwSwb6H zFiZa9{;nwL4N!w84QN5zxL4|3dda7RO9*Dl8UhWONz>9b90pifa65+QDSG7Jv;yIJ zC+mITG|K4bb?^^sS%A|AYVb=K4cR{20aPnCv3A%+l>rrv+jECrjSHDH-`|qnNjYtT zGQ5vp2@{rrX~4@l5LiS!RHUh6`KGQ8YI05dKHh-lrrEZ&OgiwRW-iC_?2nCwU7Ff} ziO%7*3j-Q5UG`@ha1FSdCR~D0war@-etvS*cX4h3M+`X_DNtYl1UTL(xw`Dz(}k~H zTBmvo!6Au^#+Vx3JN3Wcft2(G!4>z5uXf!`jJet?<`#rEf~X0C=9&P}0% zU{G~f!MpnF%^Noo4+cN#YB%_rU9)PJBEw7RH24rCoB0aHz$f^n2mf)m1cBcS;T;F) zhE*rvm=OPY)0K{iQl@h1L3*&+i?Gobl9nZg`<hJW=(^tfS%f#}GGE7c7TUM0 zEa$7oz)Pthj!l<(I&nDFmbuuqsjxBX1HWK;h^=wYMiikx)) zX(z8z?_lFj*4j+tsTPOiMg|>M)oYuhVtFG*e4m+zXsH4n`pbx=9LI;89?R+-j^vRf z+5;Q9(EI=6VYmIP_&DpEPU~zCd#)&WvtJ-TO;Tgw)+X;X8>mIFp_oOuZAM3d~wG4&@iklG-wq>i1~U%i{HHh!erR zDe-E#5j=U{^~80YKjcM z{Wtu-M|&KlUD5hMKliou6oH~gSp}~y<7sT0LA8q)TASQBo)_|GCoY*bt3Pm|hTaSZ zog*Sg`p*ppG)=rS!ssIpdAs7YdXIBNjxUe!X&Q=!_9B^L*oDG?iGB;o{Y`66Ate@T z)_$M0wEiFVzB8z)?t5261w{o!1*rl8(xpg;NLP_+L8Jr)>Am+TUFp(mq=S^uJ4AZ# zAUy#op_dR!LXvayzQ6x1b7$_?J9B65oR4Rpb5_>c*?X;aUQ}_<=T2YZ${ee*RH+{wS{RYbSUC13 zr!!TBrGUcnq4I!d7UahjqB|}rlF6~v7P=0(53L?Yg!{YV z!5;G>>sv9><$g!~>bkf83>FgCPti<{NL?ZL2Di85sXP8H7RlBNJ>n&&I*Gxrvh()8 zU8>Yh;_i9(FW8&}E-k*ERJWBPB{~}_WUEa7B^uG_YAJo93ofO%^IPEtwgRiZ)?8la zjh+tY(Xzk9|gLfh+~EUl0;RI;}{)wm;sA=Ql*!`qSk6(X8#K7ErO8eoO7* zQA!%-g+HS7u|Hr1(uup7336@ceCu;yUlTUF99zG(EpKTMiDMm{zy{e38qilb(x7Oo zTClZHs@N;UJHr2_xk$HKV1Ft3kfFwH<-bC9{6XDk_nO9!z^;T5G>C}#?$SBz`JMpZ z>`+gfY&(2Bn6)0q-CTHq%xvE0gP%vh_+Y+EYy-Z7u&Daukqb216^6I|knYoE(|U0L zjAYg)&fpPj3H%_%150_LrQ9CxdI{X86dAjNyBuiG)&}71X_6tqY%SU0H9d6-=oQS9 zu1*^X%vA1=))>JhKCevH#3uh)Xo>H9d&pDf!4!w{m-MP?cmH2)xkHGf}3 zw_>jozhJvKcoJ4C(5ooR42m8dbSj;uwe!YTN%)PtGaF`gB>`%WW4<$s(c6?Y1qqU} zpfMww&2a0JCt#Yre{h6`zkZI{+QeP`*LjCi zo|42Re?Y9Q9OiEfDFp43)pFzsbZ8~#8YUDmmF|)+N>NwGd0sbR$F8E~rV7eEsz204vD2p+A!b>JZWQ!k8e z5YBPerf9I8DMv2?M_*k!M`TY}@-CruXrwPzkxGIGQNZZx;L4fVXp+mYrGp@nus!%l z-H}i!Hh83t1mE%4yXBb#Bc$4QWk-RZIEtG)u7h`=XBb9FXS|Ei$y2Ok3iuc1@%+*F z#VVv<68fQyxJxIl?mqe&4|i;B!v8@A{1{sz`Ck|0F@n@`cpYhga4PGO0BYKV?yVCP zu+h@!fIL_-GNAYAI<;_<2b>ke#?KSH17!69?RS7y;X*_ObpY{)V{q)FKCPE;-v(Xt z32n2+Z^VUB8SxpalUSvzTv27~aWUo8N>6mJ(M0u5M^SxA4!3hxsD8`x(L|A2Ne(5A z+O57XAY6p!i=Acnvna4D!l4Yl=jNL1h|bw#zA*Kn{JSWe z+H#40@F&@duRXX7gw=HS8BVKm$DLBOv9rJlf#9LG?`+glY|gvpo=deR0mpm#iC|m= z|CT&^7ST_r6HMw*k?hKPV%qNf=BZ{##OJXuk%#jZF@QVF_cb;Iz((M1cy%-p)?$EU z^pK^3@lz`EXS*f~ndiwZXa4IvknPXw^R}>h+^Xv$75F@J9U#`B9=atucm!ROxCiEm zc6C$CoNo)cBDixCmvj|y`UVr!>~2`tzujq)52)$#ZWatVFh;n9IBG1M0@F^sb*@KNgT@6VZgxGcccc zl6BEG`5u0zRjRNl=!wtF^4Ro?$Xqd)U98N`vUljIq;|A5B1 zE~qU{Kf4&!F^`fo>1_`=LGIxnUb(sfviz#uhn*D14bq?BH6#A@vm^q>yG@*wh$R82m zi(a;kr`0%~m(dF73YQ6Iz@`sK2S&pNZ4o}HEq)091uR%k==|5@^}QU3%MBaBMO5 zOk6C)=&TD1*pVXXfW$JAqrIHmf53Z|RB=6C;1L#5Ab??O0nRN#t2fghNYRplF>{CSu$(lB#!uWQ6;Ny3!Km?Q!?y@2cHa#ZxERbMV zXnk1;IU)?S(}4Z~aZQWP^*SK-p$5)?p7r$#Woq67VybIbbn?kM2$$uuvxjkFY*ni~ zau8kzT~T8H^E-UBc+T(u1g|HF@KK!8!tt;e6z~Fz7j)B_r#ceOrZ7Ig+rPjhgmd%m zHY~3>1AZjOYk&7DYgt)Z^A*E-91}nrWMN5#0Y{ZC#Pzc^VT5PqwYXOE?=&xn&}g$< zT=K^guM6@p0}HNo#37N>;5|?h4YXod(Ur$_k{95!hr#*AR)F$7%WXeOpfmJGxvPDkE%*JYxgDZ^QA!@9gCI zB&h;6s`_ROYnrSSKOU1v0<3d=>NexsNhtmF>;F;&{PnlDQ`CH#Bk65-g`6}%#Kj-V zXsGi#YEzSysr?HH$RF9Fy$b#Sr&YRN;H$W&7(N669KP+lgm@05%Y_1(7{kSuqZrH4 zfImGufDGsfa~BG~`d68a5d3PiH5QI$ zqgL$lzIc#ZKjU+%=eNFP6?1_lWnZ)LV~)n}Jp3#Qvp6?vakv<2rO3Ia=A+&R7y1nD z^7oe@$TL8v@%)Fq%hEX*jP6{w*7kLg4rc9L>Huy_tHgwb!ej!xlBFaUos_X)Oc@<1 zjRfI6&L%n$ecP$B^ojBy%61;HdMsAXBjLt$bK0cZiQPC)&|DX?<~KEUe`Cr`OS$b8 zj3v*x+^!^xTxv)B&9i?7wDy~&_kHp42FfEqI^{s}s5K!j071v5j68RV6nP+C$DMIf zkDqJCpd>_%-@}d7yk(}$YR~;axo1%gmJtfqmo-@(IrGJQtk zYEaACfD;$Tp9kap{xQ`9XnOB9b8YDfiP1rHmc-T|M)nUkgHa1CN|5vz=6^gkg3En# zZWGs{`M)wa_yPadcprSv&;aSoJ8<<-06odii#P0cQB_wW-n=F|n`d#^esz@DqyIfC z2*78~jS~7nLiLLQg^NZj6zo|ik4PJK?q-TV3l!W8;Mu}l9(Doi^+q2M9$Se&kcC;^ zFTGbnv}1=3Elv6W5M*NmEe`_TX{Fe~@#LeAc~~{T$6COi7V&K62!i4Va*P0MCK@|) zrf^Y;HkVXRp5+pDk3sk@ho-P~y0t8$f`;;=Fz? zNGctYGvGhiIYj?XbNDs=;02}^@;7K7Ox*3Z3^Y+7%qZ62HaJbf%L`Kdo_rnW=PRR4{=J&(In~c0Y>GuM0RPZ9d<3^qVIlNO}azD9T&VJMrq3^z>Z|6?vRJqR7|tjBi!f z5MHzBH!1j6eU5;z4JeVrmS8PV8>>jKNzL`5-1Cy~ZCh~oC~V_&!GYA90{Dmvw1YRU zq9{PO;lPT7201D2K2a&FJZRb(ap56soDisG6Cy8!0MAAD=RezDt8X>6622Y_1j($YEFaPbGC)}_6=Eu-V3aqrB~>5hUc`O+hTueb2|O;_e6 zX2JjuT2k>a#j8sm4j6otYQc5jl{)OK>U#%FBJ$vv1^va74Vi^MWT&9>s< z#~l6)mrpzqjWL3~ASs2Lw47zhk_0SJIpa#wgA#&!{hYAhea1O2qE=!f<l>{pe8Vm%`Cu6=kxkvYCUkv0^bvCOIuzb# z{A46OfS7Z|Z{w1z<%6Y2kv65k65q@=+P^V_BMX~~lxTbyEZ;HsCk1;74E(a~VAVBw ze5TjejzSHu-}>3md!er6QLDE1BJcV|mcK-++8I`V7#OZc7$}_fk0!j<_Hpw5vZ(Pp zZn^dS2tbq}qJTwk(hjKi>_c6`K`w<%mfuF_x-kNLBz+rR;!jx8|LZ8f^;pJ3A)x&F zQqDDgjgbV4p>s8fWr{wARgbLulF_7jCEf$t3EO01KX*mGAlMpVzho&L9nmJOx}69^ zAGmhSLSk<%?j|@|#IB-1-*qpjspGcJ0{rB@WK;X-FwZp+tJ9BwU3I9AmR!LSxh%jV zBnWNAdZfi6hWn2u50Hrw0iljlwo~bjttEcb8bY)RxC1d(-KwO>6K#`UO=1<~McJ;Xh{La@Fkt#};F#0FxMRxe&r-H%wEF(Yw2x8H#* z@Ncp6`VT&?zlJHRBK*j_PGYWkNXnLyD#i+)n2-<8WJ@I$+;OyE)*AAm<(Z*U`+MCz zNqsViMsi%4YWc_*i@aDu7ErLa{fd~MV)H(N2tojo8*u9`^!q^~=%UKy?>C+V{T4iG z5K6>CCo?29Qdm*A>Bz!ht}w&TMf!k$L=bs+ z0tRPc)-jUdRy44ofYBm9A1I{KJ-N|fNpQUw--$BFR z`v&U`tI<)s+?v`c?i)`8d5wv%*8O?3FUE5R=|A4R{;Nbmm$(I0&?KMPvN&>HpL)%v z2s`<Rtd&S=Mhko_C_hV~h>T8~)~+8w*oQA9bNqdi{9U zNqxXhMtv-#37E1UF~oCVFalEA0vrIke&Ug7<4I^+_$fb06gDH1i}{&kBw=YLDaOb- zq$MzHOfuNWsa-PZzz5+udxUg37F<7Z^fJQ|Kwid;eiva|ttR}18Tbm9ja4@NfI|w% zPdWTbVc*VCFAyq;*Tt40v6+nVF`vrhR=2eIL5I*bIBC=FT%U#$nLaOE)FsA1cKNym2iX05z_ziki4rO#)KHL7@v% zEMca#%?Ps}v2`wG*;1CQE|1n-PX)UMG#<_&b+lw_12liggvtLcF&jky5(XI|U`e=^ z_wWtIT4l9+7sPLXIw@&{MnB%TI+_ED`UvCgf$!r+CucT*T;`Gc^T)%u<1Eaq%VJQp zNh5K;n6yhhJg-00E$n4cr?$^HW{_=q(7=Npg{^{!^PmLJfI}aR>2K6BEsHhBw{cDK z0V&^+aVO|s2ic&gBP%&dMOe)aXwU1f?rh#IahtHeedom96%hrJGeZAZJKr(TYfc*; z>{OB?AvA&rx&Ku310L?TvoHX;a0Ho6Dx51)3xF|)VaXa>MzvZqs*3>lJn*21TB*z6 zR1JUB-MtESCmtOky^lVx`{1hSW-;v<@!1kKw;Fg*Z0ULF`NhU2^Ouyf+99l~nKg)+ zKUki73MM#4j0JvydKmv~{{JtrIW-h`tEU*tx3>kZCv@%vT% zC~CQHco~@>H9sLz*<_|0c{GHGKed!E@LOucVL3Pl9O@-LxJjC!SGM;q)fq!v& zsm~DMYLDFl<*XtoNU>`ArkvmmT!GU0-ujzrD~LqU8*KFh2;SMHcDsXV#q~D6lm1Xr z$&YMUC6znZk5uL%e)wz@1Xmg+r|Kx(55g~;gyp$=6JXzC!tyrn;qK7w?HfVnC6xrU z7oNTkxH`L-ev57panm>-S+5&|z;R(7UIyhCF{%6S*#?BM21{w*c;!N2nTW(KLcoZl z5zikzCR)n8Fzgai0Dj5@Hzu9|7R?UKM|+SH)H+72?v7>aqSI>B`c+}P_BzYKdGmlN z$vWKf+k)%qo1qwO;#5qs8F6|%+K~O$ocGQM8mK;F{qk<=6>w<8G$H%WNB!4Co}_LQ zCOZ7f4L%M{9kRIF?-FdtX!9wc5<`D>=Az=E!y zEs{Z%fTKS0`C9N?GhIASG+$$Ka#Vrm^E5IM%B8`L^Xrg$34u$)UM7x((`2JhtZq(6 z9#f%4^-$&VR`VFg%jm|LebXxZ?NN|=riss22h~TB%SLfRp%O>2D^}}vE@w9Bmvs1o zj(f+#jBLIJY1+9z{xHbx39Gw)DPL3y{EON-YOY0G{LY9%;KzWo=*}l^LR}4l2eqTZ zX=IKACsIVikMeP`=xXnZ7a3MuVvW8}HHT)-nsuKHiPHO6A5Rz;>QXl7}(Vm_U zJ;f|n3?fkjD6rCpoAY@;`C{IpXM6N^3O~HWJXAX;y^0f4ZJI1d^p#S=?B7zS%#$JU z12ub;S>tLRV2I%{PU@2Q`C3~IK|}F6dxtj=YlbkqPEC^Lz6r~b^DKltI#Jr^ul5Cg zrHH1n+VaV*#LB^IP9(*Zn|EV1gBXz83Tu--Iu+M5B#4jpVGB8K&QhTK(Bt^MWMsq^ zLPU0`>^6teCT_KAv@?u>?KwNTR_JcoXK)oFq~E+O{|{55aq2Qf`t0_96k<HiD-|Fnjq@-?Lxm62EHK<0`Y2X9m04kwOA$#nIr zW)Fta&573*oFonsQuJO6JoR6-{YKfI!c($Q$jIe#>F*zr8oOim`5GomsPgk{J5OCj zyzJqH^?U=0q3mMs@kj|=C3Rm*3tL@~>v!JkztV-)-;;V}ThDf_kfG_;(P6s$59lYS zo5fiE*|B0G2)3ZUK%J3b!riob+vbf(a-Zi3vhv^&p=s+9iwp@%;|ZQOPvBSP8%R~S z$EA^R2}1;v62#ypztlf_axa^2XXVI;0Y4`#h4tp|Uf&|tyxQTO$Qc3SgS?vVwK11RIWKGj?N9S=Iv>i~12c1Ck5w^^ywiTAIY>%$q> zVnMcV+eRRDNwyFNdN8(;hPER!cWCf&KDyC-BbMrc42p3?h3`KLjJsC|X7dAjnwGHq+N_g&4B{Y-L#kQ7=Uu&^+0Fh?%&GB%LL$_2NLzYe#5Sqyo$E56j8`D%a|QymLi=oGbM-4o_=5My)?ItXvsh@(L6Jw{eIKzJHvQmfV`m%HQY8 zc9DZBAFIwCPIEeOe7|k-3#%iO{Si9~X-L(|XuKN>X7=~ZetFGFM67Wpj|H>vu^P%` zjju+g2m8#7Ube}}IIBchm=L{BtC+busz2}T!+)Y2Cy*}Gc?ETTayQnX3ZAK14{CWI zLKlv=w{8>$`#tz^13#D)FOFAdhFq2#ZRT=nXh`G{wBZp{P*QH2zdrkjPB2iqBL0ec z@a*+pwlNSCV``C3l6eBVJ;zJ0Fzdm+dgkSr15F>B^J_AmTYUL1T$oyy_^6kzVHYQp z*zEG;&UkWq^7pel4B}r0E|_g*I-ZS9ajEBJ&%>V;bWQ!z^BKtCrp@B2ALHs0JU@mF ziaQdVapogrGQH#i6OqKyOlw;or(XMdos#cox>yQ5-S3a;R}q>uJAK|CzDZ*`e<7`T zq76j)XS?~m;hgCpd2knc<+|)n zm?JMWGrLyj^&H*RjT#HV92&3wO&B!<+;$zH)9^&PQfmTes)1Pc+^q;6Xs+gz?O6C9 z*uo{2D8F3(Wg6^XzAJVo+i$lrNeot;R9}!uf`-NKGMilF!na}Q;e;o-oH?q6@3$8U zCFSR;yq`fhkv0|>)V|kNZ5C{@7aBR4vj!=Iz)a+e?RS!Xer8%3AS{Iv6--7W{)|P&X~TpIgWaxzOVcVHH;-(cZ8=XWUEy?WE=ikPV>Ciqy(}QOZM-HilA} z6d_0=^NQI@hqRl%Oj}$!ru{H(3i8`jkWsiiC&YRVy*~ED4{v-?sP-sY^>{-EeRrFI zPJ=&*lS3u*nh7YSEKWF@W&{sV9p^g)_0$B&Z$!kGe+GJ4OJ3!w$0V>-4C(I)a|Ba7 z33S_o4K?2O+8=p30d(LbC&L8y+~2v0W=i~Qe5pd|NQ~gT!Y}+*4T7jKt}&Nq#O;7P z*387j%Q46)Xy!u+_B+8NK#f!2nn9s$_BZK7iKQTQhpj)gL5n}$ z0L4x!4C3dR;jf>~AU%;<1vS>^>g+$v%*bW*3$-Zo?Kap3ft6lq4130r$rd8@#yx?D z5)Wh@F5hB1%3g`Gz3{N7q0RZ00Hhzs$R2v4=^u)AeOu)*z2ge>#|zS}k8JtMG8tlV z5qfH3PbgRcFh3#FuNSR0^>i1)xdTZA+X0OicaU1S7Nrs{N^APRb*V=G@Tt_hlse-H&3+3X z8J`g8`Rl;xE(uIbTWN2IZ-Yy`7<(l$q};U-K=M#>mdsPWYpE?ufgf;jB_8#zY{Pt#nz&^v+|fH@9R+ckR>uw8pg$bGGVHHo4Co(#?8qJ0 zyz6x1gul;dKI2PuW|A~WuN|=Z<7`Z$RfiRKKt&sVdCG=*23cTC%d)Y=wxao70S{3ySq07!fZqCJw!c8mS~!X z7U@qUCJ2z1g@FmuEYa0xyN)ip{mor^AzA#JcbT`o|DOA(VhGC7oYAhISiUbEqIJS1 z=F1j^vxZ|ttOE_VR#9l(0ym4Hr4yb}$mUnxm%;%p-|jmqPFaY3LAxbVufMQ+Y3hp)sy{|oFSbz&R{K6fg_P+0 zkIbvW?g%b70#%9BA82I!tf4e%!`c^jB756-JN%N?0=BWQ*I;W=PEPfcjdWUnHu)X9 z-D!~tbj6o2*8!8&3~%%}SV}9Ed+nuve-w~pT+@ki5<=@k}EIDtiED@M+t&B2RGi7 z5S{A$ok7g@`^*tD6mDY#C#oM^y~yG6tD&Y=&`o>88%Y}OhL_XM@ z9XG4-*t=#rOaQk2Xg?38NQ5(}-`7;Xd!H2ui3mtK<$Ya{hsO@Z#4pe-YPHhTa<^w* z?-&+jP^YMA`*RMJ_ap-=bd9lien~C_W}TsvhjC89zX{L-I5Vvh3wz}6*b@HzYwH@w zhN$(AU%f^l-)?@z@@;={=2iLdJejW%#ASa5gAfsAXT`NIVJ1` zBc}Rhbbst4sn;U6&ThniqM^Nfc1N=D@0A0NazOxD0T)Zz)O5K->uGGmt~eLNVQ|ZUY{O&`Td5331@?QRToULD&cA zmG8tWt}V*tjKVjM&o&ewl7r(6E2C_45iMC~FmwU3Ww3|3zVCodBq+UABxvN*WGIh& z37-^WuDQo=fn=-MsrA2oKk zNXV2xV$_Fsybt}B2DMZIH|0JF>BI(}0ZZx0IUJ2rN@U;1K3-uKwpjJLu}?Qz*?@tR zdP&$Aw*DksK)-hK5Jk0aATH<~U`^lT?qUOa=1;9metchRVDfz|f+>|!N?EPlYw=h^ z4JSpLIDSU3RB)W=!JP&N}pO>kZSecX|}s2Kk-` zp(_xk@ab!(ud1P-1vSNF@w@&#K)|UF&L1yj@?HO+HVZkz(6h|meNq!gt*eDr@9ML> zaAk_FY9D8sA~HY7A!C;K%LtiZk(Q+tBNW4J|} z8|H&QWH0U3sqshLaj2N=BP*OaLJ_xou|$Richdev?Ov<&)>9&-t9zIBh0gcvIe9A1z#wPL(L&>Y=K|P#GCkoOGXVzl+jFqZJ61c2 zy9Utfmr&{S8&_)y|v?%^RrF$GVU$7o&t zuC&W@^UxVEBq+dS2w}B*9$L&L8Nx7Me6&j_4z2q9OZoVeui&Z~8lz8$GVmda6hSqlP59C3-6tZ6j+ncx>j2X!Bpi zW&E*Ue7*$sj*@tY3)Z@|p}SsjuOjDtj&#bjEi;zlxLlvfo9 zcR!BK?ey(bVItKt9y|Z-n#xx8m43H=kqVlq+grFgdO3yXtn>DJL>yNG0GF>4> zI-m+_$=7i&Yi>xCkfmceKc!6n(v5HO*m}M-iB!M1&6+0}))w>x2mZ!MH(5oX9~4s$#4OMoGFBP${1Q?nG*Pg$ag3kxmWe;>Ji_#u8Ckw3&E+1wAjLr| zrs$sKu08d--f;%6b6dxnkd0ULul^N_!fv)9HOuE0OB4B(p0l8{P`$VgYBGr{%^nBY z(V0z??c`y>C$=!RY{sX*Zj`o23BPNRD;IgQ6<0L{M49NpUh=VU3fhsyOu>%AZ<2wf ziwVrPG1vDwIcaE>3~K4s!+Q$88j%Dtv9{;bu(vHYY^xhvtg8A_?7SnmOGcH%A=)KE zS2s}#!#g29T2jIVt0#%gIDX;bviDTyay6~_wO{VYQj%$=!ZI4T z`M45Q^X?Vqdk)=x-8-Kvvgku)_@&X+Sa`uc9F@OV@{bI5|7z(U-Kp+5?$TsJh;q8mU29{Z>5TP=j{7<`6zo5Fj}u?J z5g*8^ph)iC-3cSXwg1hecQYY9x5u%lQMwRueJX6@f4$h_KeDKzpq0vQMC`E&`|z|< zfP>9HqCP8T3I0+rq^~uOwfx^cYqBDEaoENfKfoLpShGAh5v-&wo|JBTJ?UwD{5Q=tq1`jimqb%7gYb7n{g8VTHT!YIdO zoQ(-m*0$yB z6P}wtelgASa$I>1OZDkE%WJ!%3^S*V-!~F3ynXUrug%VyR|IifzTh3KK=>%Q2Xc^z zuUbkE46P}74BOCxHim1K@Qd&Fp43qGdQ{-U*cxI!uI&98*hzkSpWv6SF@ zF_7A%T?3;Y`a0&2KyQx#h=i$M>g{V~zwYMU!S0j03vg-r@o-qD+}dAt>hjtOk`ABn zr`>?R^vu`d(4}L2_J}&X;GQA%%{dn0~0cVk(|_{8OyNJ4>TVS6vAX=}h> ze$#-$YN)go&3bsSCd_7}gws!m>A56w?7A*ywk68%&w@J^xe3QW-b=Kk&b(meIighe zS=RbsA%gjgx_piXwAznkif3IPM6a%J3ix5gnm~`WsGhCNW>mj97_RLIYwn1C3RR%) z742k*bN#fnvksq>{(t&KuV8O$w}7PBc<~7TJ`RF(DLqAk*X+g{4&ugR|jP}JC}1b_5()1b|l$<_x)RG-4astSL`*`q0=(th;%tn|c7 z+5AmlE)%g_WvgMieJj)XuIj4j+534hDIxRiDo&^O=b0|-1LQH5#8-G{;X7-?b54;a ztZ?J~%E*_IeM-nvFUn|MFOTnu;S#&D%3uK*6?zd##-xS_)}bF6)GuSZT#KgoH8$ly zd4~Xb11QR$tXJQ=47S`ZX4ZXxIT^^kOO-}C-Y)26?LzSIj6s{-LIz9~Dity!?+v@k zE9^imKN;O1KTaf37%bFhVsObe_xh8o0%6{f0X=$5Dwn+SeI@OfU8U%S zvzNxr)YspKuggbJ73XOjr0IQqYrpoMxFjVn zwf~O2N+(0;4cHxnf>#eVQBV|<9<{vhsS%?zPWffhqwCRMo-6V?-Bj5U%`d(j&AU=i z@~1pM6$xBos$z-hDDN%y8viuae8z7Q6B(ZE=!}W-yfrcj;*6#@zz@nTk4Yce{K?@O zUe6WDyBR!#%7+W(TpTphuQSMa?q?kQzI-SDW6x`D&7XI;mbune*h)T-I)>Y+qud~DS+a?58MVLMDcx(-_#4=}M71bC zu;F`z;BvUA<%rx$_9`&0p1WB&5c8gK-PTomw|4O5+IqV{MtyDe>wJOIht!na>H_=| zgF&gBD&B#=QvtcO$+i&AE0;o-U=8%drmxYN%b-g`jQqv|pg&h6te<`p(Ej;Bjul;7 zTvgjx^-iU$io?vBJ(@|%<0hdSZzeXgE<8~?kG{mA0z6^Vp!yP(!y8G@*MfDt>Mfo$ zb(uAui2=ZoC$GG!5Zlc9D2kp7d?Ucap=5QZ=Efn~)S@|G6aUoi*LW+H&hGqj3K#MIWzRQ_WUwBJZr1dO#2;@nqjE`ep?O6M0 zFaK8louo!UO2#FK;6rtYgd;Kx(tPWVWYnVc#41?r_4UqbAplkif6}bNOs(qU{UqW^ z=tIf}z!T}7CffNNrTdZU53A(94m{!mfJNL)_TcFne`}9<_Z%X?q#E zJ(2<3#9K~^lcML5#$Gmwhtk1mn*{9*oeYVI2Nu`m{!wVFT#Bk!=$D5!KoQ|1S*EnY zPr8E-$HUpQ*9N-(%TfcJHSm0uWNpwa=NA$JjBZ|GL65(31;Xq0&d)x7ZgoFnn2T@1*wZ*9STN+VY-sUlGhje>Db^E;d{hBy)>@BTg6_GS=+WfKiZg`Ls0B z`MWDTNX=8l;|WX8+)*cr{Sz--GA0|h?xJVLe9*4;mc-B8_nl1YGRNvtKku=8|K~}t z!tBWg@(}he)#|R*>y_+Cj8SGsmbtJp5R)OLJlZDz+Wg6ZuJJEY7JDON1$hc68mo;+ zxEJ|7>6OR4tiI#K(N2-ENKGP;UR2#yuxNw0QS?-3YDy_R2ek=NRODddv zTr5kSZ2*)q?sf^?STb10d{;h?jHc7XFL+-gUi=A>)T~gw7myRi!F6Cy5(N`<*U~*L zLYEG=_@mmE<7B**{;s~7$Y0*PpLL^8V);Bei%qx&9aabXV#SVMc_4Eq28$Y?FGvcb z9n@v#9{yS#=;6{8Y*qga_K+1y_N~xe*s*XC zNS*BQk6RZspPs4cu{DI=&XA%wrMY7C$?o0g&g(ZB(1xLC%3BB{I&PpOnQEL6j`%I! z?Chp0FU4<__9vg_^Yb8?ik86i7wNR==B`VTEL1&}>iIP8IowFt-1kb%Hofd-*xO!n zBDFt9vdSe>g#J(0%H(7xy4dcCbV1!PE4rZ&L%y-|z1kYWm_d)uan+e#*slljmv;wm z8r-rJTm+l%Ghk;J0WNYj?#7uww}CrS?5~hqeuSsNgg-t8Th1QAmo$IIgx>Ko0}R3` z+11UyIFK__8n(elR=aiCzRyw5X-(y7_qHzw5RU~r@2PQ% zD`e{*aJp;^Xjqcszt7IY!ADRXX}dOlp#;}z3+)Lx6}siH7`eV!)JSGTKnj+nrDEvO zcr-rK&)6+l*f?iY0cyp`^IVp4<0nnT{gHxFgDT3wj7H~#-qdOi!*$SHmGp`Ks{1|b z<7C?Yl}T-$O@)lj$!Zk;RGlXOe5DzEq9C|`9_s!ovgl5_WO=UPa#imA34Ep}B9~nX z5oA9sQ@tx2Ut1!l)S^xZ>-ASBXOX8Q0j^+AH0~I;Nk0KjBakPNlDR5{1xv8DJ%M?SoNUwB8f&2{E9p@T)Nl_yQ|Ono3uzB&5{gX;JTPS$C?rYXPz(*96yqY66vr?;+z8o zcSY7{Z@!hKRBu~&$1Co+bN6(|@A-~+a$1EAg>xoanj;u7GEE!UDDcCIhNrusvHEjI zsO7bLg4p37Y^K}y`~>|TCyXRIMt3b!)MTTc(^$V=p;kLkFI;#>N^X9Ul|faXECEuoFO<@L9haG9+gmpvwJX1K-EAO0J10oLp@$*d zwjbGIFKmyf>`kE$cK?-JConY5&_i_pl@zFic>n$ev|hNg81oE15~fs~$6Y$Fh#x!_ z=40#JNm+=D2@3xw6`i{S!qj~}C>weCExreC7#hc*@bMKhX+u<!70j23P zD2_M-O}}9sB}p~@+~L5acBS1t^0$WOh~n5?TK04PcRdOQwGXEsf0S4@*!Kl@&~`*n z#tFUs#E3W&nS1m1Y?Red#&hM4*U%;5V`8=8WLUA412N?mlqVb5L*m+HWTu2NgVI1Z zEU#!2%Y%4|Cl4F50F)5Az$fchf{e0b;uUBq3^>uqW$2?uG=3{UDPds1JAiJ7}kn?kESA1w8&^IE*7?epd7Qn&Qzijsxf_Hi9_agJ*D-@sM4XpfJ#URNJ)ouNa%JzV8*%q!!nS z@ac$JPKcZ8^*yGHhu}xjy`WGjYwJ}_oqJ>Vd<^##@S;d@bEW=PT~b~`?eCyuX+s6< zYZ(9asRFyrW>u>=66wfdP~xmb#Gf&uXIc}0-xlKMLH%`;cwb+uOQgu>-P_Wt?Nl~o zjA9NyzXf>ByrV9^YYItlVSYgWZ{XETR8K7VX-7a5PUBZf0{TV;ZynydVgG!ETD>G+ z{k%!xJcuSm#(mP(>U~OkOID6BnQ0kCn=|>9Cb@JCJAI@B!QSly5t|FiSP2$iLn5rH zjfe?N$SbXe}3RfS?!(ILvlr; zx6VK$E!#fN5v6l4(+2F^183Y~*f25+C*JBe$MO7L3V19}u0t0&Hphjq?EJce)O+aoQqV9Oo8xK*;#wAE_)Ib6M!J8){n1R~JMGspcM zc7Z{>j*C(`l4agn^_np!oGM;2!SgT7siG(q_rg+Kz2?XV&p$CH0xMX9+I2-2b-%&G zdQsr_%$V9;)=qFmebIgJJ$Q2uO#~iarJ+Wq&D?;EbWx*tE`3%o8{Ke6M@8*I#v24z zR@q1b_mOlYxuizXE@k+1aH(zclGxCQYtajvm%gnROyOlOytLuTYtwBkHWLt>_oMYf zyjE{V_hGjsh|kmqIMozq|0v)4vhk%i(A0XHZWhyYalFT74^ilhEVX@Wj5e5JQle)n zn5aGhjlmg$IOQl}k-PWl243>7J=P}}Q@$6cBf2GaU*>E>RgLVDWYg#tf#%$}A~t;3 zUx&=2lfmBIap8bG8|sqWAtMIG1KbmAX-rKUT^J7Pd*nU>`Pd&pgzcs-%za~~ZMIS> z)y~W9e~0PiTpT9OtW3UlNvmLpqY{`~k%gf)q$Q1tysvR<;!kv{)Jp2a=#@k}$^n9N zsQMI-nj`1CGEd zKL>7Fuz~FP$ME-PV#<5pNGb1^d@W@wo8;0MX}F_8Fu%(8pm2I@YVYp})xXX#ug^e& z*WvtYImo}~{+CBT<(IqyJO*c8@7Ln+$oW1v10~A>!ya~lf4a<(AIg}TEx)O;H^;b6 zk){v$c{;$`ju~u-xXi*DY7A=A`P>TTAH5`HE)S=s*(^kSQ@)L*d@!nw2s}$;rxLYl zajKsPA8%+F#>k_&G}23k=wO5(Ra#JySKzY%`8ae|U%XyfmN2Fmp|LW4Ii9OXx3uQ# zIrL54eD!wV23ej=+|QMZJa?*7CAYqt;clD9cLOD)Vx;vHV;F%ict!L$lMMA-&0hW< z(c5EXw>a_ukbT0k>tF#1m`v4$l0)S?tcCr9ysEssZ==l}_wZW_+Q75U@$f$25(iwE z*$EEU*deEDT<2EXM`B&$@@J2K`ZYd()`{F^#a{2f^=nuk5qrAO9Q5_QQvZ*jC-3hh z(!7JD@f&;#3iQ9ePl2{))U-9)WyapWPrv()IYE>eZ2gizr|q(~@*|}hCMH!SD?HsX z=Oor8p6l{9O}{rLiS=fRc{h|)!XJ|E`|DP&52p3TdE_e1g4g6d?+a%3=HuknFWhPL z-91x4^>NT`QYTQn5Z!=eYUPg=4WH-I1GG1{qW^cC)yba!96NS6X#oIs&XlBcdTsor zx#u`!0n3n`>m>Z7`Wl9yJYr)U3*;(T^^&K$ZabDbxt*nex+xJ^(JfUy%0fItodDAsAUqoyiU_ z*cMvfiQ7ctvaS$ip8PL&6-Y@Fw@yS7bAJu55~yrImO5ybMnLReyg2REItrP6Nplu` z-@@gh7rxm&$>qId151!-)nRW-@dpZ*YQ<9L72@}$Y*$=%{k-M75uM(%)zX-p+-d5X z>Zd)gJmeD4zc?F5rl6aU)kFA^lMVR5oJN2w zP4m7j?hWWLvunD4Zf7f0b|E4E3$?-4;3Eg~Pb?ICr`$BmHqgV^6FFlteRxk^MDa-n~2nYX||pfyXi@Mk@TIk9$q_p~3Z z$91uPB4W0B9I}PhmV|#5EUyVb7}$O|hD2hh0;bJH+}{q9lU9w|(M}RFetnbPMpsDA zusW<2`CI`;6Wj;Vmv^7UB=A(6Np~8`lK(Ne(MXt`ecS4*xGCXIdVfl!;F3k|xL)Z2 zpPO@G*~gRX6h4Dv#sjgnq=t9#QwqI1I<{~&T1f)Pq$)S z!?a$bQ{>}%aQz2XfZp6EACK)O%cY1n4mwuEx(L8{ELL`ht>f=y;2am4%UE3m$P@0l z60=sW!ysDq?K2whtFfE8EcHo~+Fcx>X(YMQuCxpIxDjdOChqkqgfpBU3PH^NVQ^D* z#>H?F9rPXQ0g-q2rgEIA2zpMeuu?1U;=$Fcq>|!S+2T2bH;}U(D_az4aRtz&{HaC( z>!4S!#Ti9S84vYfMj{?c=91iHeR8NDG$W8D%C_|qVjy6y{&c?!M9^-6rG7*~JaxSM zGwM}3ACHRwcP3`lE$?y`eYFx6ftU8tea&`0EZeB?<<8EdfD*$Y&pUWYezT8i*ixa% ze$Z9HSEWNdx9S-~wP~BZT{XasL;Bx1&1iY76pK!tlGI9>`*gZro5LZilNTQMz`iHB zt9s?{8Q~)xzz&8k^d-HuN2TbuFpHW8T-zhia)^R!_{xd;0FEn>#~>-uXW{kv;jg{pdOl8JfG8iaC7e|!3Z4g;`p_p2Xm#wMi}-*!Hy zZ5t$h45VXWLD!6l11K6*`xyxSNq^W{7In^1Vd9Xc*#3JA^vz_{Nv~(w5vGvJ`Gyrs zFETwdcIKbFGUk~_O5T8|*2C!bwV`cmQMYdOR~H4b{zCx&{&?nsN&m#a+^1j#EHHK1 zLMQM<$pwI;>BZiQX#=%4!dLy1`M|XH_EbUCrO;XHlP?P+C@00DI7CMzR5bQ=Iv*$&~^-fS8U^r_`PCq?W^Ok zx9`vveV0n1(KLq$+|V%F-%5(oFkRBA3lxp)fdZ9uBrE^di2OSJmpdEI%Hz1-z{E`4 zTo=-KHh>0f{lPV@1kVI2X|48}>UnyzGu||?8~$?zfw;!KzC%!==Fa=&b{enGI^sbh z&4G0HH8fasjf{Sh3dsNio1LrNBQ}Ig-3D=3Q;L~GB2Vj|8K~L#G{*leNR|=<^dMV* z_%szMPoHp!h0|GvajLe%t2|b)a&pR_7ZcnMOIZ?oE23Z0Y_i=l7YR{l9~~rEf0)cR z!4~iI0lSI!;rNL9#Pg6tu0Sy^YYS&URVQSzA?h{@5uLq`Tc^k#UWImEnf)6yHnh+a z2y+zDr3$x)z!@oqb8X~trws0HR}cd$&J5jTp*ZFBV<`DsqBwNV7Tei14>F^dG5AK0 z=-QPc2NK#B;kh2)Hg@Z4uS z*rYhUTHuxaTcnd;rNJjV*ciQ|t6Gn?w4Vwpn8g`o^D^U0=Yh!t-F*#Hm~(mSLzE)y zvR7#iHWx#ACn^bORF>w5J|z1(gg3?S-V%`xz^seJ3qeID!WfnpvFj+RUc)yp6lrKd z91Zj!t8qp@Bw>KZ-OfcuFRx&a-PsR`9>LKMWP$Wz>Pcb~=_mabiDV&>v*N%UsK_j) z4bFN#QBRgj`>w1Sl6){^t7a^1;fpjbGT&dVC`2yd@uDm13JXfv`A_b@)KFjjK`$C( z_L+JdM4*zw^?OOW-i2@)BJZtq7qBdt%^JM4d7Fk{IIGl6(2TdT(sOZMdzl|lhdmQu z4)9~ACEM}68?omce|m*%t$h{$0iqxY_S+bg!hgXC@P1DJLgtM6BlyAZn!DlCCZW9L z8^Kh*m}i?2^4o+=pq>mR%XWHD&*8V`+gSF0O4 zJ`#T8lAl(KpM6&S%a+wm^v4%Yl@DVo|GW;qA@B2(?qoTg7Wt-%>b@YU7gip$iI$kC z{Z~E9WzJ2`-Ep3kwyDLTaMvaxzy3lbV*i&`j$)XZPhqj<%sw3I0w>)q)+y$F&9pem zezw8JQ)v{(WA}&YvzW}#?$@XbQIgog$Lh3beB;@0YRlzQR?;6w7!G^gsiobO74a|g zUR*Sd?ry)93xn&qb6+BjY655Y+d6Y-2x~P3m`uGhAYrU)huTGA;1+YjY9b`9Ds8tH z&Z#MGGXLWV1ocwwOBZ*I1As@UO{|%3QFgF_dZ=Pn^tU9{Mk?MEius6vi-XTKBSfsh z5T_b_g7w5~9z&;W?9^2^MIDAmJ;L_rgrX?-E1~ShDPda17FEWhVd2*|58NXXq9C4g zpdR%A`2qMkbfYnKZsn zl4)5+Z{l^`x*k4YT6pGbcQj3^qcwD!#Z3&veiBs^)&5D1%(0?f!cZRhh+-dt^k70> ziWmW$;Lfm$r^L*Ak9@X9&Gic3dMX=Kzs>Ty*kgUf8(Sk}i=d!ec!R!l zqNyP}=`gTl=1>U`S>ya7LRhqocYwGpmzgi8q@nIS#QoA-q#lFoq)&wZum~xq@(Bi? zjhz<1GhZ~sSlbl;aC%Hvj`a+AqUK(%^S{$j6JpnG;`^scwUkTaZua9I&iRucLGkTJ ziW9O}*H=^wwloEy$jQZ3kebZ@b!%O>XHoJ&-~Mxn_W!^1|K;0QE0ScB4pXu^C6xk} zYLAsz-V?WG|8o@+F}o%#ZXdk?tFm7-6L7UdBtYy!8aF)ipdvNN5MMg$xeR_h%n%Bx zHIWckAOuHG^vN6lv!-7m(OOb%JDarf`aeDs2^n+@aJCD zGahScDP*U8laQVawR@}#fTj%by|Q%kRd#oYNCSr;qD1C#4vz3L9cd;`7S#7lC(fwx(a zSNIb?YYgX*;rl-cV`UzK*rz2O_i1T9E&SKL^_|+?H%nW4d86H4-J;y5Kc-R$tHZJD zk72~6L<;qr*)O;MXw|)q3XeXczHnqyPl8-U#ZsigMi;b;KOMFSp|5|o`b&_A$7uvT zqoHu!E!eCJmuS^h*1%!$i22ux%Hw)k+S>XmfP!2*YUshW@0og`?vzW&CS>VQd7UgI zb_p!Q(Z^J1&03oUyUU%3(PaX^%hZCsseW~p%_-Xz^)X|oK~M6C^3$s)nXYHllm6mY zlk&{<$)oNPJ13_P{CFM2>~${9lE<#-6dMVGC@j@y!xXy~PtCWOjo87WU7%1Sk-I!I zP@ARC10aI?hL0*3nAuh6rp|O&57fHsdY7Rt5|Q)88^25Ojn?nX-Q865lOX1CQ6jLl z3+H1+N!6r*6(k}7(y|bwMmE!78-Af9@i6fvKBp<;as2@EleVu2@CJ_Y6eim>4Pw4z z`saP|(KdI-McQM3Ko1ytE-fe$nR>LuvzKq2r~`kmd;@XLI@BxWY3DN}CE#5SFJ)jf zTHYuf8dlB8C3@yLINMyuFpJ|CH4IOn#if`;Jc^o%z%Y|pmfxe2C3s~|e606=g23zT zO=i~wMUF}98Qku(1!GtYf`o&rf|Kaw;(%F8ABZ4lM-=60#fntJF7Lb+G;Su7m?&%7 z9xdj1ugF!q**bjxW$wpbdfdn1)Uw?9CY@!Buj@T!mTt=1LKp#)?-qEWh7V;*TKOfU z$TMo?^9S*IxF3}%74JYkJ`J>5QTm-*PKQZKe~Net{N8i_oGI5ziCvJt(96WUI~{`; zh>sGJBS+E&mCg%B+H9b9`ZxE$P|l;kP+_U$4oF zP&K{`X+pY$3v46u#-PZD&1qQsc(Yg;vxS5^UbZYnzIo1SwvV3y8gGs2l`dGTJpA>N z(=mpL@_koPK)mV$i!$Pj$=>JB)Du?nUQxbZDI1>U6q$R$^t_t|s6?!hiVO@99VHct z^`Gf7eV)lqc0WiO+kaOv6LfU7w8rtRMC(MWlvt3a9CvW1!FEX2xPT<*=f@9CGtM{8 z!_chjS+*bXUd(Gscy`YmM6ZoNPa?{%o5{HCee3tXaDr9*%B5_L`tt+I*mr(E!8TP! zP1%JH-bS&mq}Tp)EpR3rX0Ttb0V!N9PKBJ>fXU2?ll1WP1B97D6}2?x9^-8;{ZQ{G zg0{CsV_d^g6JxDjhyUJac!fu2Vw#)r7P&|CUyI}@fGxm?Ects0gi4i#FrEr5a;N1k zmS&~j>-xx5Ub6V%U&io-sFV;wtRe9HmgSxc3F; zc80Z=rum+MdtQ~vD?_acm(+;q!j^BuH70Cl$9vA)S;DW`{}@ryQ_Vh6aU@FpLD#Np zr%d_INRj&q;^*^eT;YRgi#)Q59ZVQ;pHQN!fGxhG8kU9IJsW2dUDLa8Je)#HM@ZN_ z5Mmw{vvM@K`@iQmNKcC4?cR;l*e&GzR`TM1Z#<1!_4&5B%NV+;H_Pim{F{fj@8?0j z2ha73CgT4OQ;3M}f98?}P>#^%?=38pzfxJn@Gknl8v;I9S3F|4f439z;pjytfSXTs z?Z2VF`f@9%cf4K*%PK0oB0$%qnB9)&7_Cj4xbNq!KabjH;^1tImIm1%EGpVUQnVerT zS%1zOZO554_r#BE-nSh_?*MPc+A3I?$$uqH?$e+f^Hw{6kw{Knr|0in4HXfjI9W){ z4CmXf#10B+U3FGW_&F$0Q8dTA|ZV`i6u})pKe?oYNckkbUvy z*9G1QT7=Cqas~clUJ^9_$Gjq8<1G=KbA+7Jvb!3NG$opDawyuo7ZQ2C=6)dqbE$?}@>ZreR4R`lAc3IrJKu!rH|{d)*4SGop03bpb~ z>tfx$9-Vb5zgDdW{w3hr+toW=Lva%4G0b{LA$pTX1Ir?k%SRjxne7JRiI z6ne$f%7bq%xK>Nu=2jk~5k?Y?-}4Gh{`YWYD2^KbrQR#f^i8Tq?J1;H>qXVoiGm6Y zrstv-y@KPs&Jm3G51Y}S0K_iY$Vv2e2UE}u`&J?W`{ts+mht00^!ApcEP0;R)WTAE z#mIVAg;qmb>8U=mj-Fm3MTk2Q(RYQk{rHbi-2!3ncm7oYSGfIQ2(ylqS#1XK;oZ&e z$5#_sXNK}#@#4k9j*orMAlt{=cK125`ko) z34)nU#TT{fXCa(@`sXZ5=YBi1{8?)fEy$m2uNXv=riZ!uBqA`2zVVzyhyw|e!T%t0 zTHQXb>y;QarT69ReEx7Du{SFv!4WPDwJsMzHTqQXEUp~4ZVO#+6jSq=D_%a3Ao=Zr zlmGZ9AC^ObdAa_RMT2tdPuXXDGne$H^A5^&4PK3LGL_|=RPq0`Uh?kxe2V=1@JifM zqV%ZJKyVj6oHVibx4QCu!f&yVR&WhuVY<@xaBnj`%Kn>-A#Y797Zsri1-*ev?l~1P zHH-Yq>e-r7b=`9K;=Ft5q$YVWUaO9JV)VH4K_2D3Co15iEViUb>pLEmFP+bKUtcZR zwD)Fq3o8My?lPTyDp>7nk|9qVumF?2evKzc$V)e!5PUMLfk3=I!Pj3iL_u^rF<;FN z2EoypeZL0o?oYi@3xC5rYpX_92PJ+Qkf<;s1!rW4!xx7jt6Si&E9swb4H!=c!?(kF ze8h1S>H%iDLt^*sjyn|?ysOFetIg70B>9+MH@o#esnTx~+QH_3f9%z1feTpIDgZ72 z{q&U5d_WlItN3v=Q+W%3_+zo=$!x!U?Osfa^NC?;bJ>En?)w)Q0_XkGu zSiqVa6ZLm`4(mA`+`LCk-&Hz|VRW6O8gcWLvD>%*L7hC;$v~}9FTgEYmVfkve2(7! z`u=v=1e;b}(1sWA<|{%1v$F+>*<12%6b^O8jQMT%glbaZr%8!QxX{y}-!Jmn;WunK zu%8J%+57esECH%`^$@xL^*nhF9@H;!G0(891-d0$o0CR`dYddAeh5`?3vr zK2x%}_3n;EK_!+(KZuv^(ZATp@ppW%x8HI7XN%ya>__1ph7j>{B@c{10^q73IPdXn zS?LVd+a@d@`u&*s^~{bEZ6L}HEd(zK-6jK7LGk4nK9B&SdDZNVM9#MT6EFl`V;8bS zCEow0ho}V}Wm>I1=Cv*gzk=+0vlW}M2|asQ49Q`N*wOI{4?g@Ph`7u1HSMi8k5Btj zCvC2zgj-|-P*X?eUms=o~Bd~?kH#8{+wbvpsdSlq<1ik79;X;sOp2?zp$4mQls zB@(4iUnE5SsDEa3^x6^uh&1KcK@1_@0C;ocVZd(NSj;y}LR%sSL0SjRw0)nl4 zn<~{b{|wuP9+&M0ckY%qK*_FzTx*pcf>d@!QGoe1cKwB>$XT$U#ifxR0(& zoV>Sul{PKy@VTequJ0sI2$6K6>91EG{e|w|G|~0tXm1cfis;IPb&!26Q;scUj0rC` z?t00udT_2oJuJvWq1h!v8i^AtcJ0n(>0+11W<2751;=38ndc%L1}7b3c@VydjQMD? zLOV`oJUIj+7+ZE@*?(>0y5rMS8H>q zgzuRXf!JUC*gTaCw2O(Rd3f2#spf)%S+EN{9K=f4O?5&m(BC~R&j8cWyst8@+9Zr4 z0yB=HkEZO0g4aB9woe=OubT8Ay#Io$m3I!6zAp-Ra~0{ijIG`rn@JBaD+DI94o0J= zmkYG(HRqI-Y805b3pN`iQp7#ZW}rvFL&wm|S!?%DB)j5RNvh^b&qCK6n;81CXNdFb zsN>2Si>#gdI{gUat)v*82Vm=sF%6rsl~n|8@M;O~8v$kUW^xMcy0YGiv;hDsSZW#Gr=k zBlvNg1J`mq;DNF6*gI#Gy_sb^-xkL3V&fKm*sJ@VHPS`HQ<`QGI~v8XfY0~NPHKQ7 z1-YH!&A8O34^`S-3|q-*pJhuqKlnJFu0QOD7oQ|!l6Hw^|3b{55tH(`%<+IMq&ePx z8Kcge&~WRyc@Q+nNsTP*ic`f0fi80FjmDRVc<9XE*Y&@wS^p9Gd%tS=B^}Dbew|Y+ zgt{#d*j>6F$5J6)Br$kb^#{lG(amw?q4>D^OUa;@XQA6UyAJi9u;j;%;pKRIl}})C z`H!%MFZ*x?&FS{%{A!3y;Uzfw>T_H9si(ixs-;{km5^~mF8Ax}w*%78-Qrzi@1;J~ zeegv8H<7JEM7x1h_WaDP#S0rWMMx=f(BCkO>!vg!# zowULeqI4k&d;@zZV836t^JfZ0TetjIobd`-gWZjjOX%B2FH=ZhA6DZ0Q`#Rmsp^bY zcXp3{q+`2*l|rx~8g?+tV^$KbHCZOkPNcATyILA+?Q5Iyyu!X1+No5&b(&qy*O`|Y zLZ;mvXhyY&IrgnwO#i##4Q9hWWSqMi*{%C*d|<-sOQesFLds}Z=|I1DPwiQ@8CcTm zU>l#e*7{;w{PDIa5AS1CH%#R3?QeS2k~kuj{@LNytT>J`qmDDt#42dJ%TmMVA?j$62tSO+RV(OypC3dzwu>9K`>q&JFl5Nv#+WL5eTegxH)vzWijU?t$Gs zTh8tyu>bXN*wNt@V0fgILyaEe3>eI~et(uI^i5KBX-fQN+J%a3LIy-of=sHLxz-sr;~|*CT^9kymINEQelEG zAX24q|5c8Baz&%ljSikgQfTwKh-A}ExA&DV!R59v#2?}uAgud;v;f-4be<%Jk|xpP z=c>U~_eQw!Or=rJ^TRdAXRrx8dNf5*Ow}7BbtL5B4kj#O_zat9Ue>KjhLIv)M8KP}I{s0$pNqDaFr-fVCdE5bJ;+vJza1LMX z_v@BT#NhQvSTxON`etawpnX-L3AXoyDsOrT^?c6%^BO<&r6IFMaAMny5<#3;z$pS+ z`MwStF*=1ev571bURdz?xg%T_fuaRK}R`;ML;6$1;A+fltWG6uzU9Eg2q?*5O4sjJleJsTvqys ztDb(zEA7h4%GqkfA)Hgw45Pr$7tl~|PcIraji*$wC(_s(9nJckkN;F^8Tv{EtMCxA zU|LRX{OVw+GUb$^Mehapr`zN^Yr$&8C6c-V&A#40IxaPGB1^hH#2q{SG;P8}K)2m%#7cNb@6 zNB(sUy~{%QzRu}lgD(2R#E93%Dr70SW^ z%sL*geEdrObNjj#C~M^(TTqEjeuO632h%@)!fY|+Y`PK1kMQMvQSWHwp}-r%Dw8xx z=VcB&8jN|qX^L7LT1G@J-JYN>_}xzFVa{b8?rJ$uO3=77v(BVdlTmz=Y|uuOEddu? zrB`XiaI3*`irep8NBZ%}uizBqD*|wIZO&}Sm_@c^7-wH7aamr};lCDYh1)g{9DCDr z@pHMTv87-_cO2XGS;nd}2M5uJR57D9hl*b15Mihsk-a>cTb9tBgLz*xl;oU^<4{v6 zGfds|w})CuOl0cH7?H%oWKr4nIrS$#nEKH2VRI2`cXs1XmByV`Tz~6ywXYwOeIi{T z^bcx6mTMO%k3%PPs+Q1F-++hHHFnmEZ&2IpaJ=*c=n^WF7it|}4V)e37dkEFMKjc7 zgS*!BAeL4%mUwNe+XQTM6nvC%qy*e8fxqYX5yPj!zc#dCTcwGRrM-6F-OAlR1kafj zd}AL7M)Kr}1AB8PSC)&VS^nh3sEiB59h>Ms|E?GadnYP&xiVaE&Dua?06&b-2@f?2 z%b2(f!;p&5G9?An(cB-2q+I{UtGp{CC09>zFtfC3kQfy&t8a`61`pPO?M_q0gi$*4)CPczt z=leGc{1gbo@GGaJUCllqzn+JxmBD(*kNQ>aY6Vpkdk=<$!>w zUFJFlVDhAlgm5E_c5vSQY# zZVmI^slWg+2qjtjLi}PIC+bdEm>P!OC6hSzh2D|q%Pu6S zd_fU0zP_IBzH_o!%a+)bNeZ~EIWX5zx@g6H?P$9lKn$#g!X#GbU=?Fj>3)mklx zAj(4}zeqEm43>MERo5;L>~(9u@DvErX}G%_^pj2*hANdaFiq7yk-U(}4pUEYCF-S@ z?g^XqMXHhSROl3z-%Z-6!XgTIn*?^9+LnG98*knl1dfrL)61-M_`Y<6YobvfE(8eXV z)9Vb{TGr6k=X;jKt`hyFkbV4Tmgd=#y>^hm_4PMteX@0*QKbi^$fZ+y`448t7{sme z=yszi;$@)i`b>du5`)Kx0$Ts!CdzP&a0tj``g|q`{FFmj_zT!N7LFkc8Oy}-fxt0{7dp^KM4{!zY|>X!u6-2g8xzpN3K#=c5tV& zAFIw~XP$md-VG!cW^hL{fvp$Aiba2!aj4ueayUdl?X;>)ZXGXl%$$99UB<>adZ1}H zx?F08zHG@9@n|*f*1*DIbqB)5MzD2bOH}BW0EKf`PdQLS?)!;#O_U$nG zE>bSE|FMP#f05!w`MDTfPN zeCB*K6PyLkDX>N|fRGR~WZIE!TLQe?>m9wT{SmOW1Yu$p3X^4ftLRp{ zl3R(CGNbh#Tcuud?0sPsp6^-6-SYL_QFD|iFj!EZdSmzWt~#KdOTt3O z{>L$&tiRO{_>6sl_{xTrwdHzDf`{9dd)KR!-^2;C;S=w6M*(f0o^|{}OKvMBXQpem1xlPBBm0 z4dMg8ukOhoQtCO!(C59>4*w!Ykkzdn?xQKQ_1%>G#?int=F}OAy+l?!2RO)_;R_cB zQ(t)n^6gR&@o6*vBlV8c7k=0YLf4!rA?s4~OI-2RK0Ve<4Yu`@$ zhTQMzfHSSRSWrfyxug|8^P>-iIpRAnqN($^u?5Ix zx%yfiWF3>eLmv`MPLg$|Ef(zY>=RJ<;{&j|z))u+d2(&IH)6mmGPoB^k#zx%8MVl?V$x^uKO$-CBpWJa*gs=6ya~2Q1(y44k@+#$u;GK!Ir#y}7Tc z?+qVNaRatSp$g8U35S=d=L$`H`aL&mj!oHJJ$}};@1ekH1(?&Qxl4rWo>H2-Q2Rg- z;5O0OmI`KV!yjeQ?OkCpy8wmok}Z^=Ez zIqbyT9WUaMJV90C7a7;A5Qze}<(!NYiykswE;~lKo$AkKi0=+DA<@ay2sPXuC7VY5 zfb^RtlQSTze&RKYIZit!7Q^;yd~EZhc3|cvghe55EftD$Lf?oBujHj{ehc*Cqb^=N z$vn>YCSLM!O~GUiXaz07z=+F~k2$p{;g}2q$RPCK^A-B+barXQC0r^9i_kqaJOJaj zGu|Eok$+ilK&=%OFR4LrQ-;>IIJB6r$=t78oK7*E@MrJlF*G~Ncl~taF8Pnu;@$d1 z?3HsZ!4F(3;5dr1Ii+K_P3BQ~nN)HZ)zjN8B#0ZAcSRrvwiO2h5BxCK9t5~GQ};rI zA71Bo4T5t#SBqXkaZ|K2t+!obA0pIF>^fya^0~i_$oe@Foz`s`J`v<6g}PFn(S$hz5ias1kAhSrOZ{;jd&d=zie!RcW; zW%Of8!ct3aHZoVSPu=Ji*l!NrH2=$n8qWkY09t!#u=c~8JNqiy5`IUj!x{yH+OP@7 z@9PWu&cXrCqswx-RQ)x+zk~j;Z1O?Tj$(Y?GT6WCK8smoL#`~`7Mf;*L?jpU;KokVh~m@?okzg&)Ac>a}9KHK_ke8v5&Vdz--L_=c~L()}6CD4Lxhw zeGzRqnXzN~%m8|N;hahjJ-<(zW2jOok9#8{W?b91^PNv=!G&x@_ZC&q_XMS@_Osyz zZQsZp`NlC(K{2P24-+qH|7~3;ld|e5qRSyBDAz+p+-^DKD{c*d2r!r*5u|ri-)P;O z+mr+9zLO~h-~Kf!r2N?l(t8NIhEvxIj+YurV^&D%qyNIpcTiUg?n%fib4*U-?6SXx z5q9|)tL%$k=@z0%p`f@_a3Ou_bO+n3h#L{PG-<-@!Uucg~7lYmy?2|D(@ zH6Zq1lHEh$%U=O`fA@DhDX72AYW-?sjS4xHzCoGz>yCWS8k?wWByaFcOhZ7U%~HC( zm#0*!d#M$_GoMa`F_};N+LNTC4&4c3YbKA9sy#l1esKy%-Nsw2wJ%f&Ly33Ls6Cdj z&&Yot^63Bf+v8I5?OQ*cdFf4D;Gco{ps2$UnD!0LA9$Dqjg|gk!@2z(GrXG|;|>vD zu(d)U%KnV;{uKU8>&S#JtJWTzeM3A2uU@vCT$>jeTH{YK0onT$S%^Iqev11Jxu^b_ zF0pBM_wn|0dCCczT53b{jbjU`xy{bBS1uiu^ZSDJ?VLxbGMi{|rX#(~>p9D5|YCQk1q2HnX7v7tL-$jjSYuQFz8Q`}8Y;0U5Vem?*ybxs= zG<{nsbCoTi_0#56(ygUqrHdG356j+tELuvh-uL=}#aOhZlWhHtWyNxY@WJ2CPN-2QIzk^rBNZJ(O7(G-8_A&N% z(3st@PfUjS(`76LuRzG{ZVOPMIW1(-iN=>vyF$f z3kD%Rb4cKsUv1C!?oWy!-#i-H z!o@X&Md?PmpgkZq;CQqAxyLDe6?AIX?taviF8}9MmZH<~;zd)pKed|`s$N2v$D{%Q zVFQqf1e!pcFRZ|$&uJ5@B=?6^<>OGS&PVFsrzHh|N;N-g@5TAYs&Yl#^cCXkJt?m} zRQX=P`gg2=U&qjN5AOQ3vJD@eT>1=HF4dxk;9r?O2U+RTahI5w{zy+OHEwxYAgJT{ z7d63&cRZ;bxfds;=erOj9GPmJR2wfkH?p6xqw?jo5dU$&wln^N6x4i#W&oDXiBY6l zvPR2ky^j@Tmm3LQoI5qm0#@j)7O3giw{nqa)tCGDY}LG(N9BZu)#q|JZPUgaz2}Dh zX!x?brj+X2%{XVwGng>3@;O*>Z4eogRAAtR$m@J`kXRsfRjCarYv28Y`3TiASrVr( zTNhse=EnT}u6cI;vLj#JVNH0R)IEb=cKRDRjMN?XcWw3g%hl++#FTJoWgG6fS*eW` z-n_#1P|k_PAeBRpvwgf5b<9rIGSbC6u`HP$#{Um{Zygoo|Luz#NJuIwDJh|JOAeu= zfQW#AGDxeEY^A! zGtax{9ecm_e(ks01N^ZzW{0SogbQ1K6M{0$zgZ)I%D`=lYSkRPHW=vRh2o4NfKt!( zBB9OW+bj7HG@TDy$O>TxFhqm+)Ck~k)U5a%Mo+A^T7Vzk;2HMfq^C*dJvh*y<>z!4 zZza2tW-;%7$j^+M;JVduH(*jIHC@|(Z-4JQ*IH(<7%?vN#Bkp&o`xI_Sh%6@LjmAq z7RCoTMVH+kf9mTH0Z9db!xf1X3H(&qfXN1zEz!5T=I%d8rI=%vEzz)FA4P#istULen(J(Adm4?oCCiOhgc#nC;hhxPK3^xf75n z&QC_3@fM)%(GI(NIzt*+c3z*+o)9x;=6+*x#$eRx9{a8`GY;THth4U1HZX3eU|hVS?4d#3@#hz!^y%v9qCQvxpB zW$2kk-Q4Y$0~G*8sA$5~JN(@l85lG+5e1h4mM~V<4C&JttK~e2HOWM&cL1)eQc6yH zryyi13+oYOlJFI(wujt4#&p0~zlq~rE}@ujs@t6?|3u9njJxEVb3&owU<9%{Kc3It zt%K~Ktia`VtQ=vneB2?M+jzpoTu_oiYhHd_7BD}bWLMS@>Y3k&;ZRBClFP_amY1%4q?f$e#LkLkp#Wd(LvZQKfaRiHGr$4(&N#}S|v`${EX^H)de zvzmOBPR|acw!?91g#aJV+HGpT;m(U5bJdL4uS7{XYiksKi{I1bjxBt;F9BM?PzePP zabWbPI5?IBU`HkB?)+vKkGd`8`hs9r-Bf0XDXJ6t$CGG7J~tk& zof`Ws3dYfl16sJD!o42?gE3Us79aTBIY+c;V8&|#L+{c^;UNL7tv#(2?*)1{P)MjX z1SLDKGupQ+heyqysDc}j-0qLYp7EqqJRYI$_-n%2)8oVV`6iSVC7%j&W05^2h6t6R zF`jgUZNr>gYAk}l0o2V3ZSM|JCN`U&l*v%)-3B;9-c^}F5sx^Tj^mqlY6|reuNfX@ zW739xuW-5z2WnP12?Cy9>Nrg-Gcm#Mkp4PCUj6Eihj=V#E#u1kKFQH3dSs{!4m0&P zm14VXP)W$f07U6}!(O@5`cECib+r?n>tgwm9=9eF(KD2tb7g<`0JgXvgN~mmAka|)ucjwRurN@hr{ND_`S`XBVOa5 z6!G+MIGHoWEcafRu0aZeQ*xhDS? z-vK&5J8}0QF%qNV6n`^5Fd&Y$XmD&+EGU+}tO!=!6+?wDrJjwiHIH^27v~Yj_j=ik zS?iP;i|7bn%0hn$mz(WiLWj6aE*m^%I!#Rm(E0hPT(SwxZXcuQ$1FsGCZOFf9s z9s(dL-|$G=HSy7F=~+!CdEvaf{nXbA(=v~B@J2==4EXC;+3I4*J^gQbFC{EXBE9u7 zq0}bE0VkIPQUp$JE9~E;nL5X@Uvw}^d-w9@sQdUcsGQn17_CGFqTcb6W4n;4G{VA# z`dgIAF?R2x1kQFcz*maIBMJ$4?`0lWZV!RLE zgh$2I;F>B9BB>hTWj+Ta%TfDuC&$~q^S<3ZCVN+9$s}*tcEa)Ym?{axefvkP=76Ek zrS67#jIp^Lyt59K1&#Gz7ZGLj&K2jz=lSU>^5H25L0JVg3*JKP5F+qs?HG9A^9@U?^i@P>ZUOB$a- z8f%!!FV`F2jK6DEKjNSseWzVYpy1<4Sb5D^BrBTMpg$}T{4*qBd+ z(TAl;eT8K<8rs8YGwP4uvn8YNhUuY$;JN9A=2wKX+ZIJ!%~l|bu7tvX5s@M64N;o8 z!^bZrmdbZHQ1BIHyLPjx&UbwoC8a=MASk-UlUU-^Gid>o~)%s1i< zH-t$7p;!RLRS6%sxkmtgy@ z=N;nx035b#M_j&oUC2NNd3kqt8>C!xAc3AI7wl;Q=Ycnhux_@CZG!B0R$YhIbV|uuJ4tL0jIdU2m!=2kna6nhn10W^W@+dxE9<>j5GQNBhlXlO zh&-)32`kTVY?<(_x!JQNy$dB42*AqWZ`zFy@$ft58W`CddgP=FRxfNz)slHF2LS%4 zn?2p@8{NIn-{G%BSkv&B{TI(&jq9xPDfN*+PsX8YTstIJaXEth*N2 zXUEuaF8r9Wy-uuOr5&K-n(kY;5s?pZ(g)d1X~*eo-ALOwH)n{t&vdC(mAbL%ZYx(xTdSVLpt z)x0{%Z}ff5K=?~7%Qv(Z-s_XCb=#=Ytr|nR&g#3*S^3CFy6@V)toXqci%8)=rw{da zuRH#!vG%>Wn9<`ndw=;LmhXDwG=mqmv9GAKvGA#agwhWCOwES|@532~I2S6}5B@#N zZby%wjiHX6@>8)-JurF8-9@GRHFG}3lNPAVp61gnrR~P~OgW@;M~irH&?ilwBXWtk z$ECRp5BU*$E>bhg%kfH-w@){#Qr~n4IChCBb9<+F5w4>pz1(_;DKqic#C!{-NqV*#HF}Z4 z>-l6r!!F^C$)ozq9oMcQACYrIp?cGap2hC zykB`~Iw^_BVu{jGd?px!;Mv8jymDQ&Aqi(bd48hd-jom+CulFi{p;9!Q{6|Hpuu1u z^`i=-N4(VJXA&kr{iMfl5_<9w_VX?KT3BJ`^fxzdMwf?DYz4u-)UxJc8K`m zf#S{n7%Uu1J7Wk&Nlafjfc68f$#9 zU}#@=>ePU_d?!(JW9xwDldo^HaOO0&JB6ecAXHYSv;Y zBj1GE!6u6=V(t$!jLkjCAW8$B6=5nGb$LSv!{ya-9W9R^YJ=PFSVKLY?F^lx8O7 z`1l*}oBh%2qf^ppUr8q=k};kKV&lo9``rHc52>EL$jg)CKKIB)>W}1L;Ox@yZ+33| z6}H7xBDO5HtM``r)n>Xn-aYkmPI>^|9k$(s1hQgb2V#&rMRjwlA1{>f&jo899hVvT zXU?!Tb2U-0KX|5@QCfj_#iI_m`b^(-l$!&|S<2*Qx)5LkRkd~qEy*>~<}Na_;OxvA zXKo&f|5OZtUoW9q3KMH@G{-GYwOfUYn-`W}YVMnYw>)!;-X zgr*t(g0Ezs5;4IRynh78-sep8=8%xz;TGR9HGbHc6phHmLIY-FmJha1efzjUKKoD~ zxzq7l$AIqj>KZKcRrmyXg4$)c3JC452gNnUW|?RO9;;oWkFROznPr|o5s3emd%T`!X@N2;% zs@zHMn68SfC_f){rzV_v@9*2#9ay zreY)9Pe2b3ocsWB}{Rdx60a&pB0H@ zQFq9q(?HY-6wwPfHUu`D*vIA{M_K@R#S>ixJrDaqs74alJK-sVpik2Kuejz%ZWXiI zo_=A2;dfw(cb5t|Y+rUc)s_R6Kp#FGCvobO1#1`iUYwVyzlTjn%^yA}&wg%{O;&n( zdeG6W;h1rZftLkgLLMmcM-=r>x;~sWe}5EMmSZ44jic->G7F9UC0`D|agg9#i!V}$ zhPpG{YPBQYv%tDA;QH1IUVIN4p>==%F<*yy|-@)t(0zUB2@S?T)WE=mG*qh%9b z93Ro<{G16>94c&CYZI2l;xl31V(krc8f_|x!TdXt_d#pDVunXy!xc90=g?m1Un1zn zsJL26i7a*EgSVs;b5A{i(F@t@*`iArSm`}($w`=H!-Gr(hb-^!TD*yxg|VCo2dM`V z&)6O_N&?n5G%dNxV3s0Ev73<9W|8GYoWa%K*xDoC%+1f3)9`n1yEd0FTu8_;It(du z^aZ`$ttZj-W&OokBK=MhQPxe5TEe>|GXAx73#8{#r1HoT6kzxQW1afwQ31Fc&y$T6 z5jg;N_^b<QbNT@;50%re{4TOBu@n$7KcI?MJb)d#}om9Hm3><8r88 z;8`Eg^b81J9HkWp%)8r0IsNb`2G-T;tG@&S%8Y{x^c}gSbd7N3MOSB!1ccwexfj3f zj=cN6achle#NmG6!$Bi457Qqpgd0eJiS^I*884~6z);=?4_H|6&-qJS9+{^ejr5S4tP0`<6t%3>u5HspPR$ zC{-4`psYLkJcM8}S85?_b4JhIgy>t$$HH&KB;{)EU&%?1)Xq${TDe?`oo$5PYx(Ev zu9*HDrFFIkGkp)!EWGI0+5b!r<^DfX`($0wdLu;;gQi~am8<57>#rEfT@6OPZxTqn zDX9I@y;_;9PVuXcf9>=21%+d?1?~@Xc`5FM%hSnx(Lo@hHSk199>45Z_ zz_KJ@JTNRJ3>?Ls81Kr@EVZD!HKm9qTQz>q+PwNIaPf&M3f^r47pR(8fNf9!pdtmi z{n6M6_+dcLJN+KtTB2G*dm5*_bqZ}qVy$rQ!^liv+ZVmvJCEBPyH<63KU`a?{=S2* zIf>rY_JW}-;`3Zf-&bBd>Xvcd-%t6-aN*Ux&m;v&-al8@_%tO5&PiUO;mqp=Z&7lx zsb@W>N{}9}p2iiMH8cw;n7c8jDvBm z4BQ*BtS{R2rG6WCFPZEW#Q?zM6lt{1jE_>DBp@q34o;N5NtNpl2#>?Y zhEmqX*qzNZctzxv1e>hU5p3P5+d)grj(;B!7G`&7_w>)F? zBT9)r#)c8D)l7c&zVvpC_&~7AyIgWnga2hwhDKU&5|?#6e;&msAE==5nh+i)UtQ#U`FVg4Q-Tr6cIIdI5QN=^%^vjd5N|End=gA*Q;-(re zJa84Ac(V8ApRbSHK&5kCITiLU?jTCVd*~vJzXx<}M5j2Jyf3@F3x<*J6i&tP+?OF! z%p&|oq?>;iSY?OxIfNBp;JYHgNt^K)vvwOf9Hz3V4Y~oZy_U42PC94L>s^rOO1+Ly zX^L?Sc|Tjh)z`^?g0pPhXTyaze?<{x^OgVucWs~3LD2An{8IAjrZ-y?eNHtE z;};Kl>v&gOJ_U`@BENA>N@+@M(esVr#S&Q+iFO4KlR43Oef1p7h|RBr)zyvqA8We- zcEe;(SaHO!6Tn9Ofrrh3KD2fg%-LH$mDC$2z)!25(!zi5-hx)K`VD!2oY424lw2L~n)- zsq@*n!4I^xOgS+C|b)NX)_q zVqCZnsl$hD$X*it+TD9)r1d%*8qa{PL;NpDA<}p<-mBPz(QpWer*oZJB1!|OoRtbwoho~q^qJr5%en!a{1K_)vevNm4%(l@dz1U0t_*}N4mQaiK8Tn?gR zBX-m!ySEoY$oW%|{yKrkJ*t_Hv=K`r)rhgkj`d0(~8iD`+ zM&P}H*=h{cVUIhLmSb~5pp)Q|3L33R;nfFH?M(bz-V3nAw9YdRwFI&6v^?q^eLpQ` zxA;2ejjFj{mtzm#vSHRIg}N@Rouhf?!MJS*=hWo@wh-f~2kbew2^n4KgCd(R+SvbN zL8&b=uuc@!Xw}WNNJ#PKNHdr-RldMpvfqHz&vxNkl{#hTVIxo*I_S_3mvjvBq#+Io z@n$2CI9KytH+x%w{t~!ySRCu^g7WyJIAh7GSznW9o_8<~vgSa$D|j%pijEfYEpDWl za>8=zmLE}-2m?tiLOP~{_Ei~QgeJ}$GLO|Ano{*Of~=FllWP9yrBD-HJKl+M;LJg@ zVs4hk%84l+m-rnc9+OYaTk0-#q82In%pqMKkX|pDA0cdM z=x=BvJ-Rj}(JZ7frB!7UY#Ox<>Aso;c`V%dW0aqhcMT%tBk5p>*1k7u4hpv#4$iXX zxY;ArJRO%@teo|O0Ng5#Nev-;gnli4cM)_e?;9W-HMz%cwIRB1PVjkUMEr@)O#6a( z@FJZk3vZc)UkOQ9q;~W&^>YO-)mt}_@6Z46=0n3VsH|IJKS*2kl3Ffh#{TjmBsa(D z5c-Lq`LKfioj4VrASbfYoI6hk)+S=D243wnrhq4?_91)|GDPiX_VOmjDW%o(Z%eiI zl35BDThK;_^MCwe)wOqGzPVouC6&54y-P;liC3cAnd}6SrK7A>1P|y&e@7-DGc;gS z!8_k5muq_*k@Zo4xsG;Yn$P}&@WRdSJfg(i9>?kDd~SyE>Ipg;bA|ruExRHTumahj ztWfya{suMwW0soLYisQh*G(Qma^g0-qcIH18gu}0yFQgR0MzEcbRvlo>|)ca5-a|D zEPy`q;L|vc4@`GsA&aMY?aAfu<{aTf1Gq#E~bYhaxCbbZR8$jT+DO%CQ{ev3{3uGbG&gC zv2Ee?*Am|L1Q*wzy)|1ZhN#~kgBIOT(5zD2{b%9>m4eO_yHU1J1^V1`OJA;#ee!$} zn^1x0zHSIBF(MEfz1)^ABOY}AfWKGBWsEtGZKF&t>itKfY_ESdgYm-q4|Pi(Hg=h@(>~m8 zVPv<$>D);%f}ubU%nU1hNr@kc{AGx(Nwun?N$Xb%@q#pY<9%-m8GYa?L*)-&5tmM= z#+btkkWET3`4pU(x~!_1*6y7+iKJ^7e2gadJN-ZLVn{Ef`HJF@XaWz|u)GRI zup2fxKGmz#!A)I@)p?JOK_&$&DNbdp>L)#mu7gHwscg8(+b>J_R`#mTZWVGVWkrtLk9BtVYt;I2a|pK!BOtuO=V)Mjq0!thr3}47h7o^Ofn50M+ZLE z8o|~^&+|jQ+lNiNgx`A@BPVeSossVxBIH*f=s4!ka=f|agt^cHS9EXMCag-ozPEDa zx+{$sg!|9L#;00)zbs1adME43z7iEQaoXAjbD^MTFsfr1t>^+5*$+wS;f3Il zY#m(&nKR4AGS*e(`}^~d7sSZPG(zTFikNp(3tgC0aBG66vl5aYlPG!h_lq90xLc2m z5Nh`$PLHtCzN3BnixmFJ+@7~zlIX~RR|vaf>n~rxu3yI82;m8X39^+^(YjjfUWm3e zm1bi7RsmiaNu(PV8P2SJCWAhvd&Fo6^R&R1Ou$s$8GTt)(X=v2ho$R-+syb{B-M=P zSP`(wN0kkzBHyh;e7=(&GCLX$%?Ssr!2J7RhA^ok!J<`cGaV8kGOr<__@qK~fr0by zJ#%9Zk$J8mhO9W>H=0vh;BlLyap6{;$@j^dGSy$??N32Un9|cmv_|jK73S2vH(%m2 z&Kv?oQ&)jaNK)8ZZ$hjxB zc3?vLZ_W{Qz9MeP0S-#UukxyIRIws&F#eV7uL1dMhWw{%VLZ74WWt{C1pM4dz55_9 z&)?vaaxFH+ixH9X9?vSKHd{U?YAA8bI4WnUEM|jyd8~w8_3Y&8T5S?Ggvs0%68rgp z9uy})z6~;AZQKxxrIfhK<82$^ed6%04N|gre#TSL4-`i7q26bY>ZGRVO)-C1##Eb>AfYJEM2vZIv5V1XLZQo zJGmgaaWSOaJJI1g?ygn9Mfdzn$3-c@hmEX@J-3JRzYnEiYI;a|;sT2yYN0*hqnbp7 zuO*g1u~r2lc>3n^UKc(Qrvgi3gM8}b2 zZ+v9_GtaGSt8VEMH)*-&;!&Wsu!505f+tzuM%-4T0t9r7>S%AmKe=7jPK!kBJ(GcT z1%`4TOX)P9ex<@_!f@gtk|VXpBI`8OJ5+O*aiO>T!zXzUX!3tr^e&3XS+Jp@c0u>X z=6(7Q*Y|9ro$*!oZ21?jwV7M$|N1g#9$chtbAU2a0h_=u9vC=87Uw@L(Vb~0;f5by z%SNs>ICfbD0 zt=*SNo1tfAx+Of4>(e;@ z`TXb1KhxVh}%9EkgV_a~$+mv0*C58)cqTU{lg8>^LQ7I5$m4P}pzx zH@}2`cIPYVS@p*m1sH3e1ZOAtWf!yHfZN=#cGdZX&-wu2)H)L8&8;o`{`thm#|3`q zR`$v6>3pJ3!-UI(M0ZSat#*V+M?)|OI^or0;hK9*j>p-7!_!<={f&={Y^X~ z9*($mF|7xyD`k{l5USX6^|5B6RJ5M5&=+zxbDWxDLLDpem>@bH6Gwu^$iFF!X4{}# z`|^%WsUPt~%RiRafWQyB>HVSgiN!TTm}=Z|5}6?=fF_;iA-~A|=8o@aE`?dLPA$s> z=aq8&ExOL9r!2w%>%|n75sI!Ke&-$~>zLzMWmWC**mO_HXdj-Wvtqb*d{k0f7l?$udDFO6nhxvhi=A=J*j}Z=YZ;D_|+U4L^Eg^7)b8Tp&hE^Z|ljkb`a_%_e72gm>#-qz8G(H_k6pxZkCW?ff4u7jQ^iXQ* z5xg7Yz<;sD=DV$DSTvNYH1EMVVFJ3QLNTb4thP+>G@URQL&0b8haJ)N3v2#g`^KsK z;(yZ3^v8p41E~k$Yo=F42!C=gL+0+q z_cVU0@{mHqXmfgHur%1n)?;^FCtfxqOpl+pox`VVK zc<_|Zt-w~GJnS3V!e7zhuR~B{Obw3D4rgqN-o4eAdS9I<*(fTx-n+!__7f!`cpvW3qJY5u9WttDjaLY< zZ|Jp2Z2+xFMF+o{hABgkE(djglN8-2p@kI! zM^UYB-q1U5K!)|1=IHk$1(#n%WJ5N^xD@`Z`F%XcZ>^EMb0!E)in%Uz zF)k2Hd!{*p#*IC!QVdHOP$H{tHnQ>-1uZ0%UIe8c6WG#0cvblMg_GBemou{usnZ^q zuIQP-mJbZh9yDS>jrghJQUrg~;g}0f({rNj3Y2|!IpNR~jKYs^lcP%+#0+gku|VK* z$sL!?vH*ez=p~1cXQHtYrqramPs+5TpELXG@?F35 zvtO-`pG88_YSUK_wgGH~YtOvDRTU%Ab|d4P4akh^@!kAWO7aDhTMiK_=k(~LG ztE(Ep6E||F)kP)y6jY$}->X?>_5Z5k|NVg~;i;MZQktQy9U1|1`9(;z1YJkpHM!RF zi~MlIAAj{6nF4Xkyy_6tdU~PTG?o_|bG12}9JWWUn3vFbEJu?DtG~~=5vLx68d5r( zY_@O8>${W5TWrc?yVfc7?-Q=_GNyn^zz0C2RLxMX2Pp+^<(+tykl%B&_ej9!NYJg3 zoAiu67Q?3Kc$dYj1?B~Z>rYEC*150t3& zS5q;K_M^Jh3P@UJ-FZ__t=~x(ih(D3B~tC{QN8PM29~pgETBuD0E&53KK;s-IFSJn zSG*b_=cA$DH7++93IlR9hA@9Z&T^3#-6uI@swPieKnxtCVgp)OCtQu)_g&)-NVY@N zlwZ$ElGA@K5$iE0sA11C?4$k&!bI_nwM(?3py@z#85`$Xs;80(Re0dV^+5RESq1WA z^ZvQ`fXbDA7YwD-m%3ay#D7w2o?<=qsd++NCgPQoIA-JdyH_P_#ED>-D}IJZbRwdD ztZb(!F=UQ3yMor$u(2{bdfp`ygEH+p*+9()G&tybWP@z`b zJ?G!Sw!OY7b)%UYB*e(vE^_6O*HV}ceDyhi)L${>JD_NOI~Y^*gOAoee)D{o{U(!l zSjU3Sbk8w(5J1wXhDGlAzB)RuWGWsrBqBp7f`Wqf2EZFX93VK$S`MsITK_U4^A5Tv zaWl`#i_G%xCI?Gkne2gQ=Na3WYm9K6;HuTIj!#&}^S`TU=(5A$HHw5YKC(SM3U23E z+w|0b*1;n)w}$uSFPG)^(0Y2qY4}5d94G3$aq5yUqtzL5&#Oyvln0n-`llDm+-&&F z+?hUKN8eg>O-ZKJ6FvmSd8Ta7o+O=yz3e38S2*OMJ_(SLC5i?d`fe#SWI^ZPh)*g|io#!7!~+(XDb zw7e^&yvbC;_1XXFM`dsQCe9BHEN|5`ZnBt~eoiA>{Y?IJ+WLYU5G+<54HaQ;DIf9Y z&#>Q~{aCLR!q`|T}b?PjBfz^I771(qxGR(^529xFb~ z?WKsyL4rThVR+plDy{F0_gcjt}O$yl5jZaIhs z{?V16pNyn|rgyb7v(V# zBbv^5zWf%yQ#3}6%6E-a(h&8*6_E^XmbSN@Ux z?S>fZlZctI5w)=BvV6KOmSuLdQ=Y>0l{du{bV0x)0sp&n~B zUb_=bMwaDj{>nkO0pDPL@Xn<>m7foa-CCc5t)5#72#G{HtwMGu4vw)=_eZpqI8P|8 zNO0lit1xgk&=&i=iqYO6-6)3ie{YfoqnnImEstvZKldImnf_sxkmcfe2x+)tYHiRw zTs*d_?QaEbiJS*4ah-ggjQTc-up1gEnERnD=dZv_H_2uTeyAF^&=#2p<< zkELulHdhqaE%&?d{E*&S3SOKi@8}59NaYxps#6HczhU*6Gw2s~+5A@<+bZX4i^ni* zAsPOeOq`YY4W=UP#0ZZAD{L=-E5cXLm>N!6_AFa~vG%p81` zeSJ!a3ZiZyJvaaK11@}6l;3^{75n6UG*azDWihGE51B45c8om^zKKmcV;*d+fT4K< zCLF>`y1{e0l+k^Mf4Kls?JH@mU4Q;3(-y2}tg8erqcJt~k!U;4gzC%qG=uTr!UkF9 zo#5}{XJL{+c{Qvzs*F^qcJ%kx>}_XX7bDL8GGH@;e$baC`3F~>Hajz?+8^9){D-1b z`{KBH!MHECjNP-4jOHwI(%*F>tMZOo&Lv-EJN_8K<1UV~2vZiIP5(^OqV&8vPh(`I zBla%v#3vx>A3$bn*Q~d>~h=t32H5 z|HN-}iZXm9;#;GFP$=_#Dk1u!MXMlcj1G1@v9evgM!oJHCjz_)j7$PSq(}CdpoI_W zIR#p{D{|&$LUliMH)ngzE}l)k+ZU-h&gaxyXP)sX4(F!?2PJGw%z+rmD`L1!utQK5J^GoQNrEQH4{AC4DSw9$3S^3hj95^Ya?FZ2V8qa4aO#Vjs zkV#dCN7g1{L}4kF{H_5Cqath?b6x&&xV|@DK{=@Rj{>&{EBZPNBGL(*tobH}U6XAV zoJhnYj&}@QdRZ_I_IIQ;E7zPI_plpphMu3fYk({i8NgO0-cn7l404Ov#U~k5>_&9M z;I}bo#F%orbf=c)4brqnmE9YZsY!(Bli*SaHwm`>=AEm2+`$?7k?(BRq9QtW*_47l zcp#W&Zd7V*1TLs(FACn`W{173V2y((4yXqXr@$drFPc&w>MGEMQ*QkUa$^0#9QdOD z)q(wVdqT#FH#?uuf>E%RZ_N;va#_oGZ2pOi$nOk9WR4m>WAMD7;S})pBxE$l$m56Y z=Yyx;WF1%)EL2+HV%kK^NW`uuIe%TK&b7iB-nr{w2s7L5eWIv&>Hk8J9+YGAfEE?j*O1_Wr$ulL8-K zDyuZI?K>V43VT!jn*eA5>>3WfQE+@>)~j(QL}ZiY-to#CePq|38Y`5PgzG?x-nw%d z2UbS*r!o-fBe7u7`^Hm}VkFY+7M-2D2?_Yfsxt}m)2}p-XBeYJpSgN!b6+gDY+_S2 z@@_ZJjEn=UMua@F8^2ibfg^b4bNk!h&ZdfVs(L%>MR{Y<0yoXLZ=c4&ZB!p0GQ+R) z(fuJdf?E%Dw|rrcfe~MorQaH@l3KbC0Lsh7d9$9LA0GA{^~~%ZG)l@wTZPg@<(L=} zeHikRHFFHP|Bx1WS%40TUeJ)dRrn85ofTfp*br7_TPbCJ^K#zx(SPvu%<*EBl0Y79 zuCikG$bS4=A&C|?Zm`hQ-)Q;&DQ+F>hW2X(+gsPvH7O(MT-ka5(D!}=5X#H;pA99n>)?FVTjbZZh@Yr4Z-1`iH|NOK>JI4DjRorm+tHQqz@Lxmv&uQ}4r1_Uc@-OQ!5R7$-C6h;d zy(9v86)HIQ;(U$K?4seqtNm&F36Pg%N8n3%>C~(1I1N@9S`10Q{MOC+P(FBMa=5II z=c}kna14jQ83d`rw}h=Ih(~KnUzEB(@M!;DWlJp>{ z>wkMaaQnlJl65;f^ku=4D|;v5E;_!Y=D+Qg@3pTXj}a)oTfakfdF zfYPlj47_8(BXXl~6CofGKo2kfM>{NahM*Z&3%|Mo~m0A2I2D)`QtTN?Q98Mg37*9?yrfB|Zu&mo!Z%xs0? zXlmt~5{rFs$Q~*ViwR!o{0N+Cd$Zkp+y0UEtv%TsF=wCe9Y6e~5cS1Zf6=G@8iBt? z;I9$*Pevdj9dG*|$X*tnIa<-gUkV`;!U3MCUH7gAt5tMxDpYo3k@EnJZOO_Xs@D=f zLa^(`!%CmGED`!=r$OH=jL}E4r0{vqZ&(<40axw0w)vun#mM4!0Gk>(S7ErTW*&j@ znMMr;N?Gd?u^F9gO~9BO_>O z-^}E5=ojRf_+1Rh5!236vr9i?ouS~G+gNt(5NkN}bl~M|j5u+u*+e4q&Uqx{S$kYd z%E#O@^3}!0uqzrb*>4hr<2u**SKaLYmhbNlN`Lab!G()_e(v(Lni07GAmfGWA_p-0yquZ=>Adb%taY8I&IO_Oxp z-agWshadgy8_4kQ&vdm~ncJ3dwUTM^Nl{;PqK6G1r?*3ys5iepSH7mubB*312c;92 zyGz9WJSPFX;tT(AS0V->!#NT7E&5YX%5BjpWn>Q13t0_Z!lJe%>pjc&O5<(%{RJPJ z1a)&5@AxRBf06g`?8Qbl4JV!YdeQAitD5b3_NadbUb*zCFUg%nYp7c+~ znhW15c%#Bq?{E&4yFZqgH<~Pc^~J(aCMowVm{(_Z3Bthlk(2;g&dbDB@aL;*fPLj# zekz%sa<7P7Q#L+h6?a{1#h_`u{0?u=Pu4fDBP;E1j%w~Am7~`Fz4W%f3j43e%!XP9 zLDjOOxKGQ|rnd3M`s#GwdQRnAJt4X4pM*mNv;&fUp8;_~ZiUKcb)!Ukir;t6r1uHO1>%$ulK99^*M{F- z%~C&mA#ea0R+3r2GX3Iz{?#^e3sy^IN>{BQa%s&tSH-?4dgqA}Owj#K0u_m;;A=;# zE0=2USoNn66fxFt5f(%al#bL z7TEvlcH5RwHFr0a*>w#Q{9-32WJ-PHAz9iFy9QywvE$P?h=}E)S4`xMQk@fM5yW81 zya0dLhuH?NLMpKmodw*0)|^{az&<{04&o1sAXK?Ebn58?w6`bV@v1Ob?*C%%Eu*4* z+kRn{?rvd3q)U*l5d@J&KpF-_x{;C^=>`!A=?h29aa8iXXZb_jzY;8a>6U0l1$rcA%fqn3;E zE1!vduvioOm(*tc5hunq8tbWeM!=1ZDhpYoBxcv;)p8yZym^* z%b-zFJ_j9#LG1;!KWiVnzb53NgkbtHB@ri)h$hbYNVYZCtczN#20yHg_DF`tg>^JB zmQX`uV&g+xg`?~~h0z(CbybLM)kf3V{!}HZZxNSQYzU)k#~pKc!jkFho?2P|G}E6- zQBTdc+wp&Wpf4-7cf}X!QH7|uXhA*!?oUp#wq7Cn?f{06YX!rP*1Y_aJI3Vlvy|p# zUjOT#{qHCAKVSUsS@8ex@&5uou7{Jis>*tl&y_i9Fo+AM3Tup3YX2PXqUa4IpfKI3 z{RPqIE=FXEDwXgPIC!w#@-~4{JJN2+Z>egj|82yv>!0mF!F zZ!Kf|jkUL@mVFb2=jh~BpvE2HEng_zK=MXWW^<4`9D7<2yZD*>HRu9;n1UD;hB~_aSK@cPu^YB(xkT zMyIX9?CM|qRq<9pUw4ciVn(Xx2uYNbTtP^ckX5n4suOGHNDUb93(`u=*#X@@{hR{> z8g^Z|Ii@+V7-bKmoEeT&hU?mk-(~;tNNj#hd~_uILbG4^BlK8U?2%jmH#$fH4u=o% z%%W|^%)5N}G3}>M3R~V-8a;Oa%28Wvy(dXpxEgY#@I_QwJ2)ts-OVa z6kxlqfUo+>r<@DS@YAG+a^%O^RrMd_MU!^bs_1{!0;nMW*w&Pqbh8F61i~SDI!ImQ z^sSa3&>Jj$#b)J)F4?WVmHZB_ll_QBZ)m6cQu|%8nq!FkaV9Pco&NWq4(J=ugMTDm z@s%L@TOUmL-J=eu2ba1`U2o(MNt)3YC%OBmv&2APj5(e{T>MHp)Y{{jDDm^~k}MsB z^TR#v5^WJ@0ZQJhW@Wv#$MiHA9;(BzzHYSWR|?%S#=8;p4#@T@Wxb_;J#xrJMoMs( zeApD(!jgH*Vi5PEFJoY2ME01XuHX%Q9HE9}F*P(gG(P#cdcFfT{p&LLSu4v+=Uxjv zyAkg4z(1hPqI8AmPv4bZZ?jxQ{bs@~RM6Gr?uTrCScKSd#&FNz<8b|@<(XZ32?+M( z)c44kVN@~L1EYzl+}F8H_LiU0R?mOV^)$(_Wl*+YF`~O{@{_LWk=7=80n1}5$yXka z`?R-qy<`hG{`E-b79%wWbUp>LjA;8;A5gp!`)BGO7xAj^K1nS&JkyR?^fyZ^tFwH} zBeMNzMh+wCYpJbsBZX&H5BwBUNJ3xcbC(ufVuWT~G1slkr~FIvdA2W3|IC%Wfy^As zhEM6|Za#6t6=tH=|25H5#>ZCNBXVTcWgYVuQ9S>er^-?2{CftqmzVFjo*i{ynELbI zOa)=Yv|&u$#4`qm6AbAi{~`T9T>pD8{tw$xIqY0l4-*x)>2U@pehXEq z<5_9v5$omgr#&vWewqcsG4B>4{4wJB76HLYu`ART~sXk4SBwEwCO2YmkeI<9xnYNx^i>S~WswTO@F7&_ z#gSHTVZO#mE=EeiIpe|fcflgQig*Ng-;g2o!pw2O?giEb3J%cw#PO!h6x`^S*a7eB zj~`?(}|uN4ZsnjQ}p$0*qRl^2w-pv!nnbL3jGM)A-bpW^s+*Lf%Jn`jE4_1q^Nwx@>JPg_&$UxE7haEfX;g{V8Th@=&J z%#vijEC~BtCz}78BJn6XxOq`UMbT0f-GT~VXs&sXXKDE=7Lam$_1>As1($}WVrQ^y zFKA@@Hp{i64al+Q3&aWiASC)SokCe^7z*dAeZ(n7>}>J*&ew>ZIEj7`8~JOh8mBD7 zk5o+0V_?LdpS$eCsBQYxagDm_{P>2WN!a?q{ooF$ZCgBONnMNkiulR5;w;IC61 zzOtJ>z!4?Z(fP<~-Pf~pg5a?U#&>`J0v&kv0zNpfUbvANt*nkkIrG@m{|}XnOQYQ@ z2k7)Qk(Dw2OQSDgX}OEg-#}-7DH@{+1D~g2a?{Fz>Q)pKmpMK-`x_67b>HyvQ+blY zxZQ~~2<&-(BKTqYa#UXgEi$b$l2m z;xc@J{WJYauxJ>s_!m&k0Pu^ik)wkL-<8FGA*yaX~vjxraw6%G}hscla&KTMo5fVj(SyTVNBru>1L(V74Z(*CvtZw4rU)p{r zkPld}PbTgJl7fLc5xzHh5RiK$?y+Z8)({xAT>;bnol17z{(wE1PYq5_$&T|FlKlvP z{zObuFi5+!wbxG!zB%R4>d4iliWa(e zpN{H&qTi!_P;VaHSWy?Y`XSQ%tvYF zEJa>!qX=4IiAjU+^)XpuW{`+>(%r_;c(K(o3#2{AX~X>5`#}~ciGFDlIt@P!Lim0KIQpvwCyT zD`sL4fkj$|rOf=3Tx|6Xl}}1zguA;^Hvb?jSLKf%3w(+=>(w++XFZyyv2=m%^t4xZsi2+t)YqAfpBleU*-WHZZ%$wL#gK)vOxFPt2eT%nOw(eY-nG9=oB4PR zU-oy>4Epb7O}6xOk3xvWt7EeKb)#q_KUv74awPZ{p{OAVW1-l(X0a311-9_1@m1FU`P3GR1UFiY zwj5>6ru{$)#}GphwuAtO1k1$`;RVPXSJEfwKu%7qibY37hg-B=dJ1Iv5|z0-#^kc_O!XO`f^} z& z#8$Dd(`s^rxUP8RyXG=ko&;X<-8@ti0|Uq>rmNSC=~5S79z80kX%FHrK&#=LStuGu z`lvp6T3g#2rJ`1CY$=qJO5dxXuWvOA2P6bu>@QYw4no)8cXnpmkx-+}4qOjt*77&O zZx+%GGvAw##9{>qL+`d9J4?#GZ07QalDWrx2Q*lt3jr&68D?k;-5~zLrB^GJ#f|!i`kjFEzfR?7!O8KN{}!l)@kdvnVws#6A2=W~6@a=9ka^ z^Pw;cH4E#HTQXF-EnQacrNsSFv=Y>zN@>`c|I=ps3IDsEu+qFyua&|}E$7SfXfpY5 zQG>yd7C0O7EmF7ktIlogLHWx9ga8Z;vs|(dI2=B`n1}S{N8ZPl^*2?Ez)2Qtxqp$y z%$mBP5H*4`YEHp%ovTE|ngwM9uFVxMJPn35o}O+ez*Z$0!r=z7+nMp$DbJ6<*MsyH zWoT0P#0l3n(=$?ceznE>bGe!Hj*F^@4D1)2u8Rr*~iRgSLu zUVMwu;Qv|;U$F}1EPUUe7d}#DJ~m>3r}BpSIx7BEZGq|A#7ma>C-eyOkAHm$H6%q> zP-k59yP_2v_WTp0sG?mhKXlPk#F406{mg`>@yVh;Ok!@#M7<$Ku z#6dsJ*cdbaF%NVLK!qP874y+qz=TG3R%>=_NgZ~J3}$C_ZTiqUm!iur{?gr*yW zeL!h$P;ju%GESi~_`x?b84&F}r1N}@>7?F~cPGb0?^!c7Cj%I<&bG{cr*z(JE^14C zKBO?c4>AIYPZ)f<`l~cIbfZ_BL1FGoAcQ**>lMeo8)I9_SK^HxRc?IEpI$`sv0I znKE@96T1<{p={Ol=K{LZvYUUlZH7YGGNru?u$Oi+0+fL`WMkl5wDR53k2S*st&{d(J$3Pqz?YeVxV&~+|S$a&J+rozzgo!X} z_VV0D=p2Vwr8n1O^tby&YG^|AySzU+7SF^?dD$g^wZ~m56C~KgiPtdU&!JrF#tFvV)dxzZ7dGoO&;{P zF;|F^8=#hA{ip^7m|ML&SU5C-QZMX&d<{ZL)!=A)jAu)Oa-e8-h9h^pP@C_X@6`l4 zyBG%Z+R@j7Do`U9_h|yDu^+|x>TJwyHV&^&p>TGCo>)Q6ZD$}i@J8ruigC4$@4?YN z;sS+ZdL&=~Nq}fTkYjvnfa!$W+dBvIk>iYZ-y_LH@>r?c%7_7(Tw;Vb21qwRY z8R&7Q|JZev^AM&Ko4kQMTU0ybR`!7eT(IBwno(JW4#tk}hLit9OniPqrYW~g9CXdz zb~Y|c#F?mdVV#5?WB9f{Cbs)-^{8ou`1Z)a?7llraS#OBft``NnBgPM)lbm#cCjJ+ z$%M@JJ(SNe7*Elq4@8N%{0Y;`VY|BvBX=Zjmt)uC#aC@+)64@1dDb_-93tl7o4o7A zX(e^zE^S9~v1D#H(J@2CI(D;vJSFP8gSl$0c)C7pTy?!i`&{3`dP$egG@m+FcF=;T zy%kh8 zq#V?s#)wtARmIBW+DNbrcA$5vhvSw}{mym9Y%~PeX@RRbu2yO%ZyxXsFU8)Zel(nz4UQ={v zRdyk$_G9tV99sxuYeSctp!}TIX_{Z)LtUor4_gLargAbw+5p z*RMrgMkr7^utq6U5E67Z_9KY1Ecn9$$xteY;R6dgHfH$or=que)hJssu{A8tO24Z^ z+{~?q_!@6_#=~Q!%vd3AR>5S;;CqcLHjcE83||~AHB&9$3~8I+4Yo#2T}+sL^V$hZ zeU%DmrkQTgDaeEpu@d$Jl}&3KR`_LwJ{QsoQEZo1*_B0rso97HwHupr$@{LlkuOk& zV-J!aspZ~dybo$Bz|-Jd$;9z5$6p5T45g&ZLpig{1|r;SMyKOKOUlL;BVUCs*BNo+dEv9zEDGekV4JPoRX(sfcS&xWHcGi*;q7_^9r4mqCA!d-G z#3jBzCS$%gQ~S(j9lz;#ZV9(b_G)>MDk#&nMUv&4JGerV>YV@yvl!(K*@rq(nHrY! zbLv@fj=)4pt|hso&-i^i?~%`|RgP)AdGMsj+gq){t2o9$(6ZkW^C8S-#W*0h zZX)-&a!%LagL>y_%EfHL6DCP&?*(`1%V(eYbwB@I zO1=Z=jZ+hwqRVE>)9c0$anKclp_|eYRgvu=Rm#tvVf2C$5APc&X*21Y`SE8WXA}dJ z8T%VcbNp~;z|Fz+{>F#zd$CB@(%)?K%|n9j8bGF^>1%e)XVyr)$(bd0ykPKdZU;m-GTL)!~&yqHBN`h+{u+rgaJFjK9%}F*tr83gOG|?nm z1v3^uN<4sVr_$sv%8BOvmb+bV{zg=hKz7FjTAqvG-+{sllurBll-Dc8%|oFuG>=o= zaEbO?K&obzVO&5bPsv@Q@>NU6FTFO>oLpsCh!g0h5 zdW86Vqm9tf-Fxb($<`RgT@T{BsS{!k)afAI+pnu?;nv>ut~;Nz`&2?- zLa|sue9OuNzSp=kjH>-+kqN;TND$ZJBjMDvBDSjIy!Kg)YO%ghutRMlW<0G6KDa@9 z5S~TT{AiYUCpUYldj5D&bgTV6*+JLl_?J5e;C&dI0R20ARc~ed7Ow9Y6H2OnkN~fs z&2)t!alkGtEox>h4;`M-2NgyG5I}_Wd1CshQt7hjd@H%(;-)5B@9&v?)pVHMUDNq( zo`t|fvsx#;F0_y07L^+-_7VQedp^W_ShxCx%&fw$P}4UhT`8wpkQH&~7^-a|_az@> zHT&_Z8@k2$C#M1BC~$MkS1V1AZ&vZHmAt&N&RyO8-WtCB zF8YdC*8eiNb_-^vB+LKkBi z{6xnw-*UC1=9Zp1PKd2I=`L6`nF(orNA*y5TpnIb&a6LLzPs^VytF%R|J(Y?)#|RX zew7}@7yT71P3Z=P!`eZY@v-@=gA8V<5%)9z$~~nP&^$;uR?9!L&R!3rN{AnMSWxfD zF!N>l&M05-4c<)fYKQ9(q>4JBMe};2Asr6I7I4^~cYQDqU~~^9>42K@HlN*Ws8IXm z4bv|gbKheEbCH7aAmj$8L{az4ig%+LD{#3POWj44&HCx3&B5c*_264K_*n+++^C(ahodXi&+J+I$|gjNZQCh6Ev{y?+x6b|48W+QwV8eK|q=8Y7e=n>`rW zy*2<*L%Gfa6Mw*tJN}b(Uj8nH7!!lg)GbK5ompbsI%?& zY}*s1?`|NJzj)evMrZA{B7T=|Qwr2`;V{6B5+bgMLBz7Idm}q$)om0RVwg(Hra&P? zGSxD%7>8iUEKGUie$Z)9-26f{Eisd1YHVluF4%JKgS29Fjkz- z@Mt^Z^&riIp`rrS8uT~Y4m@X*Tw=)PL-GU2s7$>)TXU@|)X?^*;pMnK*AG8@{#JR8 z3uUS4#y){d*R2y&axQoeJ>4*+5cT1gRA5fa^EqDI+q4LB8I=zt{NYx|n_7g!Pyr|C z9D>uQXYE}JroJXOT4ZSP(+#*W+DV)1=?@=;GR%1{efhrFItu^npPNFg;U7D5ON-t{ zHkDbM-x)4~_P{0#dn5~e#3iToPYBcm1l%*y9NfVsi|PDMeP8?Nj-$IR#;G^}A&8my z$1elxLW~lz9)6+PADWq3nSC33`8`AVPNl*6zZAOjMpX!r0tgaxEgDDvPOwcHH!--( z^qu4KAC!jgQ3JHs{~P$d>{Z3R+u1VG+f4(wV@2>1%<2Z?2KF_%6n86dM~7S^*!M5B z+vb9_VdiE8ktSlpvrhvLfY=GS&_TC{@ZLnZh>4mk4Y8ltiH{Z-8AYA$NT0N`rA@%9 zn{TMLFaYMg4CZZ0eYmvu~e;+{GVZ=}#eJAN_c}z#N#rRjuiCk1L4XI@_*-)5h9Sg{zYY2<3>@@F)pQD z{+eCleEp`z^`gUl)j~Ap0Vfj_HJsh32tBMNIPH$~1<3*T#MY1?ZATcR8)AdR@~B}h zOd5|QI5!AWf#P=6Z88{dFGXnPQW;XD_4$u*JMy<W#-nUs`QKvqcb0egcoz?a*^$kRKKK;nz4>mwS!k2 z=JxP!LeRVkKv!^JzMtq%3WaTBX#VIfw5LzS?Wkeiio#dPFolx^6d7n~rTd1v{m*Y$ zey>uRhu7sA6x@6S=`b`m2Rw7>#vxrtP?N*AnH#lu8^=+O?srZPzfJU78+cl~GaoKB zUDB*Qg1iKt*mM$A8t3+YZ#G|9T;3fA!`N<1J_8+oIsiRg>8*v4_G^FY`XG|QrgYsyxZ1HS?MWoC>-^6{_f zSdNTVcTa#(_~I7CO;x6nj8M6L+r>Ukj;&)5Q4N$otYOZCh{yRA1F0nS;OqO+`lTwS z>dPVp{sLLKK?4iweGBWGg%e9P+;x^3$AY-pfJC=BD)|$E3w`M!;wgK*A{EbPsINA=aI3my`ZjfBC~hv(gUEoqKg? zrB8|AqxEO@TH^4mi)soA|72U_M4v}9FkK|u+C9(gB3LmnuhRIa>%~jJoP<3pHtWlV zogRazC;55vhOze?jnATkx2hTow1FNx{=jOgAbj%l1F8jhRc*u+5%2eYg&5{fuI_uz zY9N;yzm1Lw+(r4UDN$qMHFk4mv$Bwd(s~EeuH;TpgFou+XR}ZThEH!mP{ds%qW7vy z|K5^o6IKQ6E{oE$h;#5Fi|>nP61zyE&n!Z39-sdX;y?Ituh#iAFbZ1@iXzzwL{bC* z(^sZY4`UjiI(ivT5vQ8&hyXJw^c0RE;2C(f6F{ty2&N1|Y)E%@^1QkVVZ5D>XflVA ztiFp(xcjknuF{8`xYfjaR+|N~K-dT411LGh;4G>w`Do}2iW7KsT1Kn#E3(~&vbLoP z=gp&TVT=JlcA12<4H3-Of|qutEcpx4^7IcT@XSd5K=eMtCMy@N`tz9aVeghZBa~h2J}(_bx5jvI zFP|(_UHe|f->8>=LSNX}6n40KdwFg5QEMch8;g;a6Oj91*IQC(FGfgE!18dppC_F* zZIlZ{u}@!w;(4-UCd%r`g24pzO0yrB0HcZVm^~idf(bbztB(AXOkdnpHS5$+map#x zE!1*!`1ypw5j2;d%BzQ5>&Fv36Z>)S=S{sN1!R2j7IOpde&;G6y-pj((~+&%=ypSa z+tz8%!?ED&&5`Q^Os?CHrzo*iD^#A`eF1`Q3Qb=BNZ3)f(GM2CZjK>+nkjR2yuxhv z`Vh{UGjv_rBhY$kn&sxq6OlfRt%Sm2f_wduEd(7TxuOyo-NglZ7J>yM5(n~bHnzRG z3x#YtZsnH2HusI!QZ}7>PYN|ZLM#{3Wm&D-83k;5suRM_{DU&UggZEua zF8capvmnFAMmNm7wg2GC0@RT5C5{h|| zMQ%>lI2f*xi*W!3L?nN21V}*cc*hTFc?Tmh@15GaRjNNxrRp_koV#%T-Um zsR#vPuHJqXliT&RsvSE)x>4v>VcQh>Inqc>hBNmEp+T?Z`^AIZ!IE3WeDeMDLA7M_VpJPga2tA(7|#z^%LGz~$0ZpWTa65!Zgy z`2vUXraq8Xw?5w8YcaW=U&Ath*e_-26=GVy3=XwecpN92`UH^>R3k2UJ~E%nYmIb7 zUJu|lv1AHa(PqtW=pf*wAPF044r%m{z;@JSCY+`6#90n;%4T~0KJZ@h3>b{QY~PSF zb#nU<7DBCoj4rCL+X7mev8E4zAgZM~fytXOS~sIzfg~WQS>lZ?#)+nB&vzU<_)*3U zg9@I2s-G>bt;*0|4b=Mbw>(HYkS$)wg31l-41(P5<;JG?NrdB)kPdkJaaT00ws!h5 z0eAy)#2qe&Y{d?!c%aeQWCQWzK2Jr9jXYpr7RW5fSiqGC^%c=u^!WNB5x+y9fAxmb zsPGRKq0LS>V(e$)Xn}eU)o&=7z|P*!LSCY(>)m*_ zKf|T5Rc-RsFf^g(v8NoLdHaWJIK;ez_mDs>KY0Q@i>6Xm4< zw>2{Wwy&#Wq(8k-zt;Kb^=3kG=%Lwbs!%3W?irdwhA0)OcK`gc1W|gKb^{_)$mi9j zgEK4Ms2RNzDN$5h<>9oM&teCtFHPV75gPM&m>f0aK$*Me&uxk{oq*9wIL z9V9O$g?wbk|CLe*GsWYc*?MjMhLWO|<)x&M(2q3;b(jd+PWNg0DwG?aH?=^HhT`3A zmc#|@FVIUTJpvpfOhT6Gx3q@E;AQLdHbZVsyzK1xvG@&!)M>AuCFhQX(ioXkm2DYZ z3&IHLyxOydi3BC^nu5Sa%#u*!nz~S+sRV=PUDBOCd2_}uK4``$x9by!a+rS)>b$+X z_thnEUjp82wI1xASR-(BuXdX@vvjM{ z^1Iz^3u)v>I1w`A;>dp5C^ANp2sR`4RpVq6)N19p%~HN$Zi-#HB@h0$0$H- z6{bnS?qM!1Ltyjku&q z^ZAv{J(NSMQ19wwtS>i^`5N>*D2$qm#5;XfP?AIbnTN1hP6dmgURQH%>@z zy^qc2W+J=kI7g;S2-R1gF8u{fk!ZEug}W*5qL2y~xsv{OH6NrP1ml#}XcZ)iwZ(ba zqbCzGX+GZLSftqe>e{(^L)H~eJ`4ZqWCG<|d1QjW@oD5zOWGazjp?{%T|GD5!aMZA z+h4k<6UI2m&DI;y{`Ah*Rl)P_!`o(-jF)u&z{}6^2`&NHEY_10iM@uSY0lN-H1P(z z%|@);7B`4q$;rcWeN(7T%h8-Ua#oJU*bbSr@PXZ4_v6h(RyYysVpi<-hwP%QL}}V_ zm$jH%rfg2ILj+`+O^6L!IkNw7hd<0qi!0bhY9JgQAjGJ-I1y=_jG& z#LRLr8V)ndbaN0NX5Zs$?uzNXDBQ`T)~_uZ4aM$vkBl26XvQV0`7^$98qgCO?4Xmc zWn|3P<7jQW$z%kkLejtIj~usk2{uPr@Eq6W2{>#iuG6F|*qts}tL%PhVM@F6DZa@L5bNH2-+B$&+AVJqR_%ho8)^Vw}q+ctL15CpQJt zn-m`Z2Pn3L@{YXM{ruOhH|HJ9&)39ptJA8YUSn%FY4XQGah6~1YqalxuF><=CPXeR zEqJ5sA3sjNJ)EI+hOcfsAt*jre;wIz^(AJBKBZ?AK_eFrD{47vOo2;;$p_pIjtA5P zHNq3pJTKAv=;ox9zLxZYK}%Y%`sw$`Bn4Cr>Za^kcF|=I;Wf3*Kaf;pAKuFTc?egRb*H&^k2T zST0dKY2~Q(Y`M>a?cp7GIojD+ zJhEI+PU}(o<+zifPokdU}P%5Fa2}_sWp&^PL2Icl8vqD@vHhbiVPat z|5G|JMNlW{p_9q1FnlNnU-d@alfs61EOpah^1GHR*4fT?+mu`1ub0lDt%h{p-{E1K z;^*6gv$zgs5B$(N>Ar%Uk8z~TJVbAlZ9Pd4R_9>%&5Dl)q*WPo&zX#-)xoyBH|wo$^V%ZbqW0BRN;$zXu+iy$mDc^8 zpwljTqY5|YdESlFh{&Gb2y6CYSJ-VTok~E+711*StHFf6$~oTX{Lv)lO=WC$z95XX z-;5*pM_2PCXC+TF8|7wjCkrv4s2r8GwDEfNVK(W2?_n+8Iw*5E3G^rzW^p%bwIDm! zx9!&^(FT4N{>uBtje&Z*sn>f^$=^XiGV`}!tciqOW>(XSRQ}#@_IXpXWDfA?h3mqp zMOMJcuTjI8HfCZB1cyu3%2eHg-MAJc-FMrK+suxLDS3TS8ZAm_{AzhI!|P$cwjYJJ zwjrrEBFXnY$&uds{RFg&GCtJ5`25ce{R88B^JYFcjcpqX6JU9>D_s^Ioo{S`s-Dq!Gu3#qt&qrAm!ghZ3--D-_|0NY zAnRC{oLag0k+B5piY}pTf+_QEi1574NDd|rXR8cP8 zLPp0sr6{>#m64ZoG9HbuN`ckXJ$QT0$dc`$wiYCF znH<9x;y5tBGn=F}Xf^pzgb`c;thjYk@t^05c`|AaO&3%%3sv>H{|MBO6)1^=QoXzRh&)+$enME5r~Zm9<8yDciunLc{8OhWWW4M_#;#NN}@&SUo<`0o%--j)k!o zbzx=6EZ9joc$6lYFd>KHa)`JDQMcfa&p_Al8y{`~@0!UsUzt8GMen~zrqZ;#_qAG{ z$b(B|U(k|I+I;5c6)e-GueP}{uD=LAn+DkwpckQ?u>Ly8!n~CTc{p&j78qG8Nw*Uy zoV#t?C`FR!Aeo#?^#))+4)GvZeIk__eFKQjn-UJ**O*X*0|G2-QDw%>VQ#V2p-}!+$$v{@qKaTH|bY#$)wqF&FT!gpas=D%U)} zbQE1YtS5@X$zSMsDO=H}2)}HwWyh2qHV;Enfa(6^NN+8_S@WU!tBJxGhzhHOVcD zV$-qEoN75|3Zz%R%6|AOoZRa96HGSIR=(c_%20Kd1878F5%)?hPo`{}xf{fm)PKd{ z5SX5YVNa0#bi8tYWXk35KWAzf>g~g|nR|G<=KUm~?G1rb{k}~zIib&ot~V&K5d38` zBII%mb~xgg&wk7(-#<03-y2D+0Qh=pjEYTO|AyWmfQYRbfKQmQ0i&@mNsD4cQlS=+?((lty zaoo@|E^W=YJbY;`KD^k&=)6yxg6=Qiy8~U$j~uuJWbk8ZLVG-F{@&*QN&(*b|M-c1 z(q$wODot?x-k~Y01?9Iglm%>o*DaK2 zd)7W9UutaBddDzF=KAH>RkIR#H&{bo_GUrRJIFM-aASm5V0<>0R%$W?@5{jqck;HH z3t#f@wJI~b7T>bBpG@Ec86S9?aN$* zhgx71@!$sb6Ag>$mdgpbGYLpxJXkAi!=PSo;F}gWwGH?6Pyzv6!I7|`E$YHzIo;nv zclqZ7RrK$m58Ok-Ja7MWWlk*{Z%x~~pY^4I!}8|uQ$ZPSq?0Swm{@j6(= z#5mI5N;N{i09aR~kw=Y79Ih+^_3w$p7tl7FkB%9ff7ucLu3%Fp4l#4f*Avsojg~H3 zFM7<*bD3Y;tTg?UzvjPc0YKTCj-=kQo3!ugN?amzB@U@K%XM>83$3#>=N;R66%Uz2 z6hTWxLLe;5TNv#Hv!+6I)9MXQ;wi!G$Q8H_xW`$>1PY{V0&tu0%LXsZ8W!$MK_RB} zVh%I(RM1u;z1EVa(=VTU7Eu(}Aq9JGe40-w4I|o?$8xojdtX2GDq5j1&V45}N5FYV zR1YgwgGPS-X4B2&+TO1$br|cMkhjnKOrjIqcKE{S{ zo7$NlBG=ySk|Tv#=;HDREF(8aSr$0H?Jv2)!jn(SlGu;AGURtTd&v6uo3)h&m3Fc(clnn1!uM4 z^S*!v(^70oytp`d`&O&WpgL91k^J~l*zT0P#AM@P)Z3NUW!jZG2)l6^2^_0u_E#(3 z!5h7AHq-4ES@$cON?)e0CrG=52f7=8a35hA4Hz{}N7H|^x8Dfc8x#F9zSQnc7Nb391Y2~0{ zd*vt=(@0+fqL0H3Dk#TSOC&z8uX7eo=hQLMrmYeYmN5Vun3@A005=C!VgAabR-n*` zRlJ4+<}R-ycs+arZ+$aY&`=CrTk0-<=)%YJ#O9IdVB3pNPeUV=yDFQ=c6br!wv&yr z-h)~a2HEq4C%$oWRT#$##`#vbvG`SRdqhOy@P%t(nt+$$m-|<_BV3M_q~Vz(rLpty z$YCd1>Ti@HDF~~(JLuh6LU)DQVQ35hoLpxvV)8mSu66C|htK}zYhqGB3xkq!VEfmZ zIWS?`U%6E0E*s{b&U((#v9;Yp#aF=j6`5FQK_J)KTlFT@zm^2XoG1vyq#eeP@%{4_ z^v|twaG}uhbQ}|CBfQPU2$h-}bfe8@cUPg2NV1+%( zST>7W@)Vamrbdr^=Fs{t#}1`w|EzX zlo&3~Ba1iKoD82{TIHpz>kxQ}`sr4h% ztf8%7wAa26q0z&*WPG7_=fM6V5l@g=Dz?X_ono;l|=q2D~7+j~Lk8^0MUoWn+lWA6)c ziN9VB@tDtR5cSN=9x**8fM*ClnM{r*%Nm|W8nG@cK2PCDjtxZZdS$Mb2!~r>?bULB z=zf1G2RJ8y@tstTQ%b|ud#1SDRi^vU7mB&34_g}0GskJT%cM%TIc&vv=<3Vogr0JGOr|8DRW z`{E>qN#(B}d~3Hg7G9Drs41+Ylp_|N)c1K&b z?}J?ZQ%k%H)(zzAWWV&LbFsu}eRkC<-N%Cj(e$nC`TgxTIPCCSiGI{v*C*Xf5t%rg zi=On*Nl5AojrA|+-n38IN2|#{HlJ>xl)c!etfmw4489A)Ip^PGS6Tbb@rIl;_`zu_ zs`cmXiOq7T(7W7NJ41!AT65GBes?d7Jyn_Hvi0|DiPl!Fk258;6$~$=FolYeLVF5E zR`(QE?>u5!uQ5Jd|f7E=lj5v32RK7VanBb?>3s(bZMrp8D ztt!!76V!&TX7`k#9~`|BXE{IJ3vksh zlL3s8mH8`3v4Iwa-A~68j>?zK-zVHYFMlhJvT^ibDATL5wC7PeZ9_sMZc;MA3x^TU z+z#2k9rb)z{B+49?y$70C+oZRv~#1%L!^T4;Pm5KuGc91HN)hX)lDO!ZnP_k zuXM4tx1YpPlr&yr@fkF*TMJm>tlm@`1>Rzu{<*5gr8xK?yKy8G*+CQVb*qR85`Ozs zsZ1bxgR7U|!u%6{U$*Acb50Tn`?Of9cNSWrr}^G}{~2AWBwK=ZxC;4c7|YbT@Jxk? zy`z?(h^^E>SoG2CC)U7I1O2*puNnRta0zA_eMJ2A;^~gM3S(cmkF{5!$}@eG8)vkR zY<|6ZJTmjk3(Y7U)vU7_hmJzYxkg|4Ks&k3W23|W_M7Cb*44z@ddDI-KT&qwv71=I zqCX?FWQ@H=KD;E@*LLp&O+a?agpSKIFx_EnCW@~4JEv^zf5K_zT)zEji`%zEyo)8@ zl_OFKMH<-&`Xu1raUI_F%KYKTpLjJbuPcxIRl_bR*H^!Mb^WmvSs$w~_np593RTwk z11lcN?8bDj%{x^cIY!=}dcm)oSC_jKtUT^2KU?fKe=CW>Gd@bhu~SR>a_ju6-+Cf# z(V~#;D1jmry`#cZepj|^jcxH|?vL0U0aZ%9ZQSHI!>~rz(*5+{sFeL6lrVF9i2MKv zvAf~dfcfOdoomjckXK9_(aIfyhhhmq7XC^uX})@Sp&LQmP+JUbltc}drnFguZ z{GHsRrP*cH#_yw@jljN_9xB$=4$Ooi`;ygPai58ZwgO@C-l*&KMo*D2NwLQ}AxYLK zKFWJ=4+h9p_KVYvloa=;-@6YWNxvLc(&3M5lHpo+x|N>R>V8^qWgYBi$a=r}{LCh} zcw(JVuh5gmZT3oqI}7VVGTWk(;j14EpQt$#+6v!VK~o^Xk~0JlY)NUCW9&**&5iS} zS(@LofKjL$l~gZUhg6pIqhSM!-ds!mH-@p9y@xj$1sIq)5>N#0i!iaCz{g5) zQG1#M{6ncu;NmM4>%}qsee;ocyB|;AO26%6;7F)}JdJ$31?s|SuEvlxj5A#!*{6|| zT-(>`2ww3o`uV1JG6eve>|B39k}Tck)Kg$GSDfL}K&oi%OxV)sdGNQuYgdGZOw{6_@nucc2Ku7M1}aWWsitWJkU zc=(aa7Dria#S4VhEquQXkS9K63PmgxxU+%iJ}pXp94smTXvpB-{=FdkInz1p@NBc! zj?^`~Ip|@#xX*18qro@bJWRzsXZo6p$QhBi2s(zW&?!90pVI!r^wPNJS>#K730tW* z8MpQ4UeT2ry;t6U%_CO2+xJw3bl{!@J-)^$Fcib?P)Me~^lkI8%@aKv8l_yTDCQcT zgul6EtaWTfZ%GFvk3#R~Galc-2)uA6jX03}JDMwmpfWIuT{AL!PN3jAgaa zBysxt^K7!Rqt;Y{aiUJKg8sSIjVA`*=wv2dQPRa-&q`9XimLcr*6x;?E= zQ*e?a1Sd&LtT&S^1ixLdT@E$!Be8>WRYpx`onH`5^T;%w1TvNc1`%I2$NzeaqwBcw z-GBe;taqKdF(mQYw(l#zM*8mr|HMnK<|2^zkEW>jduub(CHc(^8nSDW%{YAJBPi@248Q zV^Yo2KT)aHlF|>tOzm`KSzxF!r;xy7FaLYz4YE$bdleGvn4?kCq}}@5og|ser?E4e zM1C|&V<^S{IK^)-l%AvRNU~g(@CRRw*~+pLjihSO^+@LtRsT7zH~hVAHAJ5=%F*OX z+#8SHpM~Se{`LJcYR!dVctssgJS z?OzTiGVK8-F1C5~u+Arj3H_RKRC{jKVP>%`{E8LK&u!ng$&gCmlXJ4&TF{%Ws!8CM z65A;PTXywtRd44_6U6)_qHZ&KC#zMTedE5Z9uT+7get6sxyrz&2@!e>T~WaohvMKx@!GU>(-;n(^&=naul8h_?{>iXDoKH!gNWbgef_&yp)Sj#YDBIDool6 zzCUco$Py9@gv;+H7#lCW2%<_Zf)dG+uHx z(zAHw!7<6swM~hu9_osh`wHOR8fyj|ye!$()_8J=hfQ0ahkQXmq`yo&gAsstndnZN z^Wx*K{bhYIaPuq4vyxHB)vZ+P1F|Q0+#o4)!rr<$ait;2 z-uZIh11TxX60ywJGof${ybIH|7z#Vb?whmw&ihChU=Es!NSUy*{@4V=xvxU+_FNhx z-WR~S(oLPa&H!7GWuj!V8XTNhZNGH1y}i4Rp%dCsvOko{qOTV1^8NqO<=M zm|e;+feU7lJI_Jlzy@*p-!QN&xCRByUXErxCr@-VN^(OMe~4(y(JBiUFX*@R2_%b> zWQYgOy_R&?iN1K@Y?om3?hy&7*v5A~6qKv3&3+N|mM*GGGCG#@-n2g)yj2fl(EfJ9 zaz9_kOc>DbdF?=0iGj>d>g~U!oLq6t@9ddhv}x;c0jlZr_DTHt&zc9{|L5?ncCt^U z42DB$|6bkv4*h=)M~FRBENZs0__}#x-a76v)uHFN{~Rt=6~^_Xm+|E5Q@$|{UB&nA z;O_q%J`_MrrOjXY4g5jsUr#uqjg9v|hmSbDi}{axxxcvi>_3NlSzLehpZBsV^xs?m zKkccKCXD4#jVp@vn(#+84t)&b=P5c`i}uP@Z#(hWTjey~IUW?+ zP`a)oU1Kl;HUB`%ORy%=B!C$BVD7cld=JRi6>o*Cv3@mMJMe$o^NbW0Ch)B)#0-ls zeFkh2ut!D-olVL7r!Z?WM}O0b428@5b8<qop_ zR}^inWZ2X*U93(sE0Y3MPZVtr>%}ko()NaoXDWwE{-UG=ewOP^JRn~YSGB5|3D!t9 zV~ViOXUSE4&D-JJPh9^p{hHJy$$Nn+C1d{6g9S<^g?$y1Zx0E;^~jx=zJ`9b-bo zJ8=%|ik(-GUB84IE_1tod25!j4N1JioM`!QGP3_4B*&$?@?lz`m~JWVejq=0yOMM| zEol4)%MJdU#JDouDF(SBhTC9IX%@Is_TNI$7Yk3zH+=@npl3kWMV>KszAw#$Z*pQJ ze5rn1c{@)lW1mIZ%$@&j$eE83_1VR2h+p=f{iJI`FBv2au{uVi)b>(CqWcCn4ID%s zx}**pFO7AKtI?V)R*!BxuwNS`)?BcEY-LcI4&i(w`rs==UHI*9uk-Ied+?e;@rI)3 zy|jl?LXkhA7nrC!Sy**Yw{mqeIP*pq0DATsQ_V1X zF#%2ocQ|)?Zl)QkVi#iM<7@as$f7$WmV=+GD=#QEo4VF$8$;xsL>x&wsaL0|uS$)Z zXyOEBgItI!xUHFi_4tm8PZO;iA*b3V39pbXY7=t%?^?kam&ctK@JpXj2;9`dNAf=W_@VLC{m73nR# zibi?}&yGh;gjm|K!{_JQ7OD%eC80^Y3fm_)X5^zRR07NfcKL|K3mKAfKYKmAX^xU{^H9t8$a^jT`dL^Q{;l?n}gg z1kGiw^d8}~ZbX1m5V!S=aEUG$c>3Dr)5yx5pa-2B-r;+rh##Xg!o;@V3rl-}y2;Fg1~URNp&&omxj~sUzU#w=MhX znhn7dK*q?qo%+>Rye4st^!8sI4-Ws``Oj^RP>a_#{X?)b=fXk~sqX(z-@TxJ_1)XA z9FSl3#Py@1=M@rx(~O?D@no*Ve|6nk$};@ukVwX=_W%6+D$oD)4s`oh??8E?meB4u z0b|VQeGsg#WWsWgocLgOo~$d6ck(AsyIBKHRFl{|!k?C~EnB%1GAegE@qzNv7JdEH zZ-d`vQhmB`r#9~#lEZ0lsAD|0!zsCX?sdw}tsHpH8u zv1*^XcWiQqQL^i(INEk939uY;@wtr>g%AMpCD$fd>aeoS+0-D9$x)Ez#*%M0wM6=v z_-yt!c>Tj;lg;P2Yu_8otMaTDadme=G}6k1p~&yi%`PSMT#0n%zyvxFW+v2F_EaGu zG47bSa%$yYH!N>nJkfus3Jp(JWfCKPrBU6NRF7;<hPPNxdac{kCm15?$t=Fhkl1SNi(o z&eRidEKoG#$|z&tcK0S;*uQUuaNbmVtTJ8P&j?CJv$`n)lqAOY?hbfY5()MBeNu>Q z6+WQG%wf09=+aK6YHz2nThOHlB?Xk^P!KrKJ#XkV;3vv-c}@>hOeig=h$yDj#hy5 zBii@|i(usXR0#x|tsk83oy`*fEofPi6sI@FvZ|mL=s^Oq#kj4ene_51f?$Zws%LE@ zy2`(IaL`W!*f}pbOn(6s>W}VRyj`A7PD*xT06Ii0&8{>1RtyLA?TBjcJFR@dfp$KI z3{D_Jn3AIxfa^3%An)Um2+@F-hHVaXv{^+a$Tp|sY%FU;fP=nVcqt;4dClm-uN%nqK=Ub{Tu6AV=r5IWk(jt42Em=^O8#^^Lg z(ZnB`Zib;s0t)T!iBbcY(^$T_(ppy{@Vq%?@O?C=e%9o-#9q<VtIPZPf7M%q&5 z;njHEir_vMCj^bC!B(c%on63l`df`Uu26j9@%YqC@(FfK1PQ<%)U}~i&VYjR15Gh> z!tl#1hxX!Yl*2$vpM16tB||X;za@21x^T}&0$pS1Bmw}zwPfs@S9|YjjFj%6Dy(Vr z&3?@&(;#dnU-hx#+Fm>=+Dj_!v~8zOaqubL_lbnXJ!5B*kE0oRpAM=Xc^|B4&87~Yv;NS8Ze1{bLTod_ies}ELTu8+8DM^g2B|I8 z$sq&0%@K4%i{P;`A=y}~wWjto-k(Am0u=A_nP!y8N6$RorVE8$;5bWyrb`^IO>TnC zpWq~*KI5LJw@T8CZ8L3t<5s-k)HV%i@~>^Yv+S0^sV9Ke{L1}jY{cS~B`pK}yhP@f z_wKXn2Cof2zOx|i1QGhrB^E=2omgyt-QH3AfE^?O!*2Od&>wcw))99is>9(MsoyCe z84ti(o!{`;OzWCu2)D zz0-LPpKXj2#PsBmzyM;#GB)Wa1szKUKUr`PThF_R6+evIIL^-^S(&VhDk^;`wA%SC zpoFM6SXzgrcMAFGjGq%UkLP^6F%U$-3+pJ>h+Kt_P2EfP@p1ftoQR_(XFJl54U)tw z5M1iZB9MhYx8rCpqj8*5v9xCMRn^t!ndRV$CPJ!@PPW8Gz^UMg+{L`5#TDnegOY(v zP6X413C#8sb4T9QqQUCsrJ0h1Jm;w}?7O0X0vnG!(Shnmr0)XhGQhUa@(C}YPYG3& zqYdpm@+WA2iG|ZT(WB3k@pcJO$6tckn5G!H(7AVtHLZ`T9HPmXQp4J_Lh+p|Or2(- zFQE)uNKaCd%!o~k4LD=#3~_Ag+@g+|s;Wws&G!DCym@vi5TyN(IatqnvoFh4Xs=R@ zp6T_%7kOxP03H_}Od0xv=4*~c%^J37Y+N8DZle{)oG>ie z?u?7yv9$1M*g(Th^S^+)1mDQeY7NGa!R@(m(U05(>i{(f5xo~d^9RG}D;dJlZ6G`@tz{vqOI81ZF$6JGHwf;;`KZz( zh~bp>VlfElyG#UVL<*6PmnSm**i5VPHcG8wj-Vu|h)11-|k zf9<)Z(}!%P(3CfF!wc@nI(U*bbO+dT509^0^7gmLTn$$3z4ujLm&zz?&*ARxOVOHG z2@8ky8zyw&63>!}GDuHI-vc5*2x|Yq&?Gz^r4nFFXH}e`+z7n2kB}^7icQJ^Nsv$x?VSt0_E3t;}dv2PC#b2y5 zT_R)@gbaadjmTXD$AX5&qtl|8@->;hggn9Dz=czWntaD$R|fa%pw;bI^GheMJ8{RJ zSM-hjI@IlzqD*_ddu@RHy0+h5y8FR|o0eTmJf+m1ezQrRvlolA9y9}dS6i>@?Bm-c z)ShQLjY(F}8xfA87X~t&+#a~>ZWr9)rv$XGzQc`Z@9aKA8Y>S~g`NovI+U>4MTf&- zXHa-z+lOm3^vl@qMFU{yYXSY)E0zP|K93;A_EEP9g>(aIQN{PGCC#77!GTF`(92CR zn{z2!KS*DUm`9=Dp3xAw*F>yJ`ptX(?8ZwkQ+(mW^-n(i#Qmb@nlG&9bFhKo|Q;EA(em2``h|!Z^bB4W=Cf8CLr7ViDUBXM>jEu zz2==yq|#GDZHfbHIKL%pV(ql_9!(!$lhY=JT3)*njd>LKr5*vgc32AwwQ+e8adKRu z@V-!p|HbX~Zb!50CJkkm4pd!_O^a&nIj?=2df}dB^~=BD$~XIqFMZ@)RCG6*_{q2f zUR`zU4e!1#&bp5#p3%h8&|2{_C$$3p|Fj4(5x;@+kc(q zTMVUx9_SRF`-H`gol)h3Y()kv82jy=)CgKLaJ#wXw^opy!$m zd@Ps+-R5?qgL-T~zLRHphf@>4i~-<)xULMF5vG$TFJDKi|Pj3{@gCDV*tMYm0E+#qRZP^Adn z`k#W$-rs&ZSr>q;B#U3oCo7-QjiCE>hOhq&f(R)h-Km5@1>z6d#D0fX4>L-srpRD|mA}aT)xl1&YKA{LwkXg9j>x`b)lR-@#qJ*IW5pJAS!0R`o@q z79E6q1uzHsclOM?%#5a`8JaBj>Z50^lhQX0&0ZPadN3Kd_fyryt!|$C4d%SxE;Ztg zyxyNZUA(DtCmqHl*tgmj)eBC|@txN_uG{zI{0XH1TTRY3wB8uMgBXQAv&|xkeya6J zii;RF2ch}W;i4J;_;)43&EI)SJD>^kZRate{j}w+9S5;6$m8;{CoG_lqbeO(A8Uo7 z_?$mJRLORH;wRy|g+f)sG?^~}D2c5XkEHA%bz2x3edGz~$NbQyz zOABMa_2!G;c;RP#c?E!%RKIses7G(_I%nJ{Jy*5)u_aLG`LHMt<7A985v!{??nn(v z)2A-{J#q$-_IXk(rCKu8<-x%?b>$ zT?K|=9Rs)}nLU3O@GzJQno*6+7Zp4&_%{d}C^|J7j1e`Z1&wV!+4Av-8K(d%)+ z+(gJsBgt=0Qxod=Y?UyMi0FJ>zO}7pbMyfEM!+gtS-|>8_@H*Oag(R~=R=_%X}+eD z&BGAUbu3ItlE$ zAxoeT5hqLBN!2xxnfqvQ?pia~=exZS;%a!g2(y_W-YL>Fcsh;waFZUAFJ4XFLEDK0 z(2U`|6OW@VkFlz)C872$`i}@|meQn*`Bdw{&(9kh!_dKRNgI}b9L#ck8MhTRI3(*( zT4x@NDzbs)oPTlZIA}CY6PqzgxF0B_Lvz5pK&*mdgqVp;CRYR$yu)eA0#El9a87P5 z5s5Lx5^(`#vX=It)TXr$xp%I!g1^AT&Uc7|v9NKwN0Lc}$d(JH0ob%z)0CPx|I>7x z!}gQJl89r(=chRA{4#13Dq!%RO#iu5cMuX?j{;$_i z;O@gtfeMP3kdyT*Xi+lV2BLu4og`Y@QcjsRr=Bi3B zOn#W64E>4U*RKjzmr9g>E{ez&HIB1_AKlU!@+Ghl7m*Ni-^D~eL}HqRP`wuB#HA@s zg(E~UhRNc1Pz0%Fk-t-6gTamBNn|e7Dl=p_CG-alH4S7Sm{Ga`TQ;7Um`4q0-IY|E zjH{ydStkYQkPyy?TC=ER_lI(Z!@#FjcVujuL<}@WC~i$$Ds&~kDOaQYXE*0>4xo7^ zm%Kg@#^>ws+PwcbTd%qirF42K@#3~e?suJoyVrtFyxsm0+k+_J39#&@gOh{Hr!3=Y zn}2*d_^5YM=eFE*k|%B$tGP@(!Pxas+&yeaqjwG<4rASxK`N);x$4e2&METE30TD3 z1(Ne}K`_aAc3!D_MGhaqP{;O)Xs;omUlTxH_Ixf|a~u%fH0L_wxd{OAFBh#~T?4p8 zB5>SWGwcC*7cJ8a4%{Atz<(KJ?Ryyx@Fkn41!iY8qf=>x#IyaW#L-1f0 z)6*5{E?k*4(+K;L2EI;5Poq8IT3#^z@wwN8;q@zN(4Y#{p$X>+RLz0NhX zT+eXc0>mYwHKkCc$E_Gko(6PI&%Cn$e?#1+y<2~*~&;_94^ryVm3UKA4iI?t1+@Vm(p{&6J{pkcg`dh%@Q*#74{n!5F5IW zjee|E${>rGc7i4VgKmYndT|5*J=bC!?Zw2`3xVlJNQ?<*=xkTL!k?@qt|Tz_5UYln zW!W1CtnZ{ydYeTD!v$<&dzo_dux@siWTEf(k3WokWH@6v28bh%UQ(Qt-Ig`}IBLnO z;B63T?`;_S^16b|!DnPT$eJBvq(rlO^5+d;wN_;=4`DttZui>gA1QDlict zXdiH6wd&8HkKl}d(@JOwt`^$`m47hf$DjGl>w)^1168YHp{zzqS>voD*0bA3;x#tQ zC*63kDN(Zdi0{_?mYSFor_}eC*P{$0$26Bn9n!1_o{KdqyIAS67~-$bCrz=mci(;H zRWO^)wsMjI(yi-UiuS#&{R`q>^o71IcQp&eFnSVJWKK4YCoon-*ctJ3S|(ipK#a;J z-V@cfzn(cpFX87t&NbgKV__-2h}QK+!)>PY4f$nICDcD-!c!c6kIg_mN;iV1^bHF8 zZ!YK<2WF_uWHW<;aBemW?7l*V_+!T(bs_TM`V|qDi^ObRSJeHJJerQG{f-%-oPJaI zW-Qo~ka~+?VWwAPWQ)X-X)!=W+PVN2HNjQV^*b7XRnvlQ(vYM6C zAS1${PZCpDpme)nLZ}TlP&+Ixqsk~-83L|ch_^VsHergGwOueDusJoRKev1aSD4?`(43t@N`c}UTa66E2y`raybC(qk*bFX2y zOdvJKZ?W=H4KrW}eOVrm&EMHzUsN>e+z^nlCM8=_l|xh#?SD_6x$!GwL-nC77ecCs zPPqtm`wdQ&e>w4oKqy+eN7!@5s-b$=mpx=4rXkAmLg&X-yypD`ajhV43l;h&-oG9^ zY1{3?CwcLh3SMJ1#auNRs)vWd;K(M;Rn;3oHBI|3%WHn3P(DTe3m&T6IvsvXO7vXI zZIL}j-l#_dsCMq27_=V_qiHio)BY;aw!dik6-je2eHE&TXU!aY zflytL74=w4o$R#S`VOvykgBTBbKTpc0iM!^D1W$>`T8uTa2ty-e~aH9sFje@JwETU zkvF@8+tQvUw6sQZ=7}JU!+GV8KE&#bYp9=YvdBrl4T+DS#W022fZEQbLYTINwWhoY7%(!aa4H=Vj?Ey)E}$)wkk}0 z+uIrT-2TCWWg{sn_m|9_uOGz+gRp^42t0m&{Ik3-^ghu`v(KQYSZKe``~%SZ>(dW! zkFH0sYBOm3?{paFKMN;9r3hQ-EO^!DTcPjVdCGp@%1J!%C!?kqbs`R-N}ki@KOfV! z#}&-5yF>-PCKcz;wtc@WiQf#pkUJM-!fjYFYhjREtgiJ!_)9Nko;M+EsaLEm*1v() zaEplJi!?m%(6eWCGoaRd^~kYSG|h0ZGS1=i=wykoWax$N)qzz_>)>)WKT<&U@uqAB zMVElWc3+AV`jI?wA{~P?vJy6N4LK8$zz-ZH69WoytL>a%uMte%7eq1mC5+R{Kf`*2 zN!Q#&h7-;!Y8(Maj-=4rD^WSej9!k*(ybp^Q;Z8kFb5)>9TYAL{!+y7_yH1tD**eG z@=(6<((#xaHDzeodmP0mg4X}@{gfQTXo#-Xdm)|`$NZTTTt$0pW*UGiKs7+hoaCT$ zU3!AV=>^;5V%*V-r%@q64jGoKVwrD8WAiY zPspE~L3lt9T@ymco(_iiHykrvrpZHybkXb&A>qjrLRUbSAFKGXmKA1Jb3{?UT8hf} zwq^FpgFjSU#uGhEZdpatqWbncc1v0u%;B}+{o)HqZXYi!2rF~1geiX^9o+uG;)nGU zv3yby@*-!Il%m5t)h8ww_d8zT9gUsGn_48{$1UM5jSEG%btc2PGhik!TL)&CQtG=x z&rG9UmBq!4*j;rFFTt6WBN>vyxaaw{3WVPyg`aRbOkyIhnk4DMJV2R&v54NeL9D3d=*`bGkEq*M7&6OyfqYEKsjI$6tX-*`~?7Y zw(l(=f8~ACYdoBLTv~>ki%T=i(|@#G2dJB*B%C;GUV&5O$1=AM^p@2R+)P_@`i&Tc zaD2;22SdY-J=c1P`lK))Z~%Q0XW03Z&38NOeG%IoA2`yUyZ=(wLlq9qHUJyrt;^F5 zJ9Zgst$L7dEe+Yh^BJ2jOXy@ursr4GNndL?(}zVQgLb!tUmVd2}#9i7V#o%h&` z66J!qkq4uGc~1L{=1qxi<@Y;T3IQ_w4v!Pu*t9#nrsq7Vz}lU5g~8Z_BMz=*&I=L|Y)azIXY4F*Fj9@(Y(Ut@Oz6PV6O6pzSb7E>+Vs8JcW<8L9dbm5kg zC-HXA+Ss;q@qe8}5kg~brWK|Ob5;$Hk%94+b61|-0UWLmXb!jk=-o-H3&SUc$Od9?c{6%1)L7u`S(FW=JwtNB(Y?ha&F!4pdL0g|T=yjVO*otnuVjnfJsz?S5L_7w$Ewj)^xk*uIlyC)Ti4O=RP zxvG9p#^tVPcHQNRFq;G1MX`vTQAS1S(1^_w^*$q~v$O%98N71hK5N5U3Hd~Jlrh3O zYx>NN@H>UbQZ= zC)*%*@Lou6wM4+8<24=9ME5$pU)`h27su`W@O0G&q?uPGPF9A~x3Bk~@Ftn^hW&H7 z#UYS{X+F)v(JWclj2r)&_MEun94r4t*6q02=I-kbdaqx@xc`3_g5WVE`?WyxHK=Ht z81t84B3<^k8t-8ei0wdP-Lc)Bgj*T4y$ySu{ZcmQ?uKHIcHBpKb>WNbcJ2rQol`!# z@!B=KSWwcEZ$1-ou(6!WzC9QjgqTo_srn)wWpG7O%fi4XskvhNmw-YrIQ@7FsoI22 z8uNtVcH$RYvGg59d_qm$ z_cFHD=`%bhu5`a`g~^G^*Pej!XEHnb>Xn}R?^*z7HZ$gp0Em$teQgrh2Z%w{PL+r= z?I)r3kr2c472=@POdZ!_R?azwSmL<;P93MrgdNcRHuXnmo8YDK*x&HY)+{9NO!HG0 zYNw6bPeYQQUS7|!8t>dcE>DBXzYtK+GLO~{vOINhW86>jC?5?@XrXT&`kQ6v)yFw99g7^c4}5ZK)JLf@=zSKyH{ zupq=?2Ffi^1D*#yGYch*^*#P`ek*c=wS!LuWoxD;u@hjLr*_|cG`2zWD)VOu_zbmS z+C1~waLD;`#nbk&@Trog4m!41?GXThFV6KOhlh2g`bvm2!kzm}ZOP|iNz~z;V40rv zv0_Z)+I;C>MlNq$+vz$dIK%Gyc&Rj5NY==U1Sa_=l%cBZX^|^ zmb{q5#*1S1f)zY)li|Uqx`UzE18w=!t_#22iOa^K*cZTp*sFCTm+hV?P0)kvodjh6 z6r)bzK0=&*z+Gjv+#DVDP}Rt zD}pJoy|#yo3ROke>PU8d$JCrXcEHR^K4kU?4pAO&{wgGM!;iq0nj_NgK*XNkQUL?@ zo0ypSFKRP?w?6orO=)~&PNFv$O0BBZ{mCaeITwX&hVuy^EJ+zD=1|l;RF5QC%&(6$ zf^!PHl;!P~Q>)1xIiu z(;m>BP_TZYDkMuB6fI`6kWqHXynCgwrgkiASw}-gm+uk&qN?f%#3%(g{7L}Yj_%!T zr^GxLulpiy5Q@zzx3Rho4yLQP>$|KeR1maAIUokTv@y056nd^~v-KEw$$y44{;qPV z_rxn9bp6 z*Ai`rg9OC?*D2VQLlEidEL)&~nI`d~tEM);lEZ+r`fuF7DgYEXN-U+Ihz^qNA%(u) z!S_V-PBiE?A3*bVh#%&2m*q|D*Tt^pZkzhR4zBI0bBXMSt+2 zBt-W5CqM^BPR%dV3{wNqx?EYh^8U4b96^VA2I!+&F`|y(f#|9xptYG~hA6m?(5y3Z zrJH33lZao?qETixb^7Q2JAOtUrSU??27$4SO2+TPZVnliSG-)uOunD*19)S=3y5*R zLdbV?$rn@SMpa{vUYo(&0-L^Fy%<3d%eF${QZsk9}1CRp`IBCLR7Z54}=3$AbtKH z`4q-TEQmidgZc68E&4h%-cw1H=7-G@Np?Tkj-omSuq#B4^?J&)9=K-erUCk~U;^=* zkwlT@Z#TvA7SXHEq3?!?tmynegZQjDHxPbpbf-IKV-6BYyk2>b8 zs_F+>9P$z}3Z%&wF^(O9+yj0&Pr9Y$eMPS`M@d)4*UB7(M-BwC?#9u&>WZYpqHIiU)z3)wAp zRqKhW$H=A?53u!Tu>N)m^PuM~m5Kk`74vvwIcVxs~ZjSxn%O-6^#I37xcz zhGg=7K8p8-C{_9HA4(Dk7bW)Gef+MyEWVD|EMh}dQJT(lioTbL=Q;-2K4=jITQJ^v z&LB;vPz8;wt|l|vpvVxeK!FA;8jBdYLd|Uvv9!Q^#w(>?I6-&}P$LBQ@p`8+{Bc6B zD-K?2>e?xs&^?&GNy1GEHf#K!XQoaknw=0gR=%gIKHmOW2)NtwV-gugiaP-B-FcqCShQKqrk6jA~Wz) zjLJR9?<+>Yg9R9A>ax-hcI-yol!0Z|GZ>FHB{!)s56CTms1r}&H{N>>0D~Nxuj^a! z5!n53HBYgfezz~!(W0O1T@VUik{5sytRXE>a&>vxJ()|K_r#ACLAMZA^+5txy& z%O*{FmTSJIAl+s;IlFc`_L-cT!>wfOm=}XV{A?s|MyT%s`=FyhNbaIH9Qg;RY;y-N zC{!|PY4-61DxrQ?4qu;As3CaL5-1z|!uvrE4w!Q?b1sQLaML3qtkV=#b@n`BJ^Y!N znL*oxf{cQXaO^|vaq#{6fqGIVg`s1p}M31fADAlLRB|MJZ+4yonTj*&%Mi{ zRUpH_EJYw?O2IV~p#j8Xs>m*3Bou?|BK8%u35rGGF2F%C_B3pc^`X|kQm!X{4kr9T zB>n4`v|?meSSs#ThO}mMMR3V)FOXH|$t94YE4*Q&-$`+fbkIb81kA*vvo_8D|(^pnZurV}KRhH9O@^jM3F?|dHLghEf`$)>HzTII>qV+ahyXmKd z_aKs}HEm(X^WzJjLbm&2as&cIv?S=HTfX-x$G$P4y9O&Z zPHmzFWKAmC6Lh!Y;{$qqExNRIKf9`;(O*wbx@g7_Ce!ty_eTpi3v4=jn<5H-vUwk^ zZ7%RZgo^8+ez!y3SXum*{MvUT@JnbIh%e!0-SBz4$f&GWi*=Gi7mBJEp~-#JQ^0Ib z6>wH=sn5rUE-iph=Jmcf`_*bYjV#ia<|qK4R^@6^3_t7kB9H6SAsv8*KzdC%j9$y$ z_qLtqvPtP6EzV4^=d%l0uZvyf;V1azGVUws^Q5C7Yg#REJjzB4$e*ZaS~56<60fqv zTbfyDlt&D`zGzt9S`XsPg5+bzmr_rNd5doYMpBPk4WX?=M~et8;FtnFfBYCtubCQj z*l8%ABBE@KRNKlZ8B(QpE*=~7Ua(58l?mb9g^6akq?3#^AYsk8<9wUPFHR?Ie4=*w z%iGA@Bg!=txxQb!pyZAH*J@$s*H>xy<2t?4q4cW3C<9Z$gnm#!b zXyg`mDVVSL0}hmgv$h&>S926(JxDTDa&|EjF)?9vq&Um^tfZXzQg`RVAo7Zlqmwr4 zv2#~VOiP>XHtEjeXs`V5J0f{c*l&i)ylBOg?%KN_6-q9D>Tbfgw+=J&%1?s?6s|mN zXej-^*n97&sJdleR0Ii1R8ewPR75gJY_cFAS#nMyQ8EZLK|z!#NphA95+%0?lA*~+ z7MhGmXi`ImyBhrV{`NiZjrYbG`<{2s8~(Ef^qR9~%~~_mtg2s467Sj{y6rPYd~Wgn zPI80+d9`N~lkVMzM!S%*;q6jFoKK_U*@8=xK^7FQp8bQ`C(V@1f63PQzWFa;{yv6$ zX2JWSVeoD$+U826T;J^3EdRsYAIbf<7;}S-{F7^{Ir}>M4bQJ}=m~LI%6;sE?ut z5Ut);5EO*1BhBOc$CBEq9;P?GAEy}o&H9uKK(VOp!|Cm8ldJHfq5R>iKMr&@%H|sq z@-13H^(gU!(b2tC(7f@l`Xh#u<&&S)$(@GPm90NLI5D4LAk7KJ2xp(g5rU0g;MTrJ z!VM5)urV+65UJN&yng9GnXmtjOaN-iI}_C@5m=zYf(CpS&U)VQHEUJ0QSsV3dWAo$ zM{1`)&!Ti}TsYC)6O6mANa(H!yNP* zc6M>ssW_cBrb|S$#$LX$5=K4_eTYx(e!j4TG zet5YA+`0?oD!(gG)^5sr(_9gVk58)JMZkS8?^V3JJIe`kJwdy}xvsf>J?Nxd5tP<3 zn!>a96K>wh;CO%gw&-XZ51|b*nPBPlt<~G`j4kNrFo^+l=mKj7`1UCh8vtLm&=Lm& z)QCNF3X~CnjE9<_Y#umuua^6whrul?a2pBmI4GgcMiKkTPQvAK6wxTw42Vo)7Z{9G zLY)S$N*#w@Y?HY;mR_*IQOxj&t7Y~{pHrsCjeLVIq-*L;%rK=$zsL9eez|8ONRS50 zm{m|?wmrN)ZMjb;S2feuu@Rb}XPp#=X3%h2b(;d$9n@AX$QumvZbgms7sXv$*Fj?a zBn8UN3wm=RU-Fd2=XRjB;E7q^P%V0ih`_d;h4vK^OzJVAJGGyLY08#o0wsQefg|-v z`_~6;LIS;$Ai#dissL`l^sX{4N+SS(Er8*pM7u%Z8A1kncAO}-h>z{;Y~|oc2!F@P z?LdE-oN`96dzZ6p;FHfT^n*EGG7!{O%Y^^_dejwLmWlhzsjdUjhtp{8Up<%IeAr70 z#e2N!BX3LZ)D9xKhFpKX_%6ByhoBQgbDKyj4dpSqq2;WfB;@CJs8_@MT(0)*w(^Jc zy*9lpnEk`OC9axbVsB@^&D%TcGHoi)ze(T+b)d8bq!9p0IXMu9Rg=|)g+>A}izBFrQb z{NlT(#b?R<&ym;EqZUbo(W}Q9Fih3@He)G#1;w=u_Qv#{GDZ-3^a`puJaNK(BrE<_ zXbA<{#$b$(Fmw4l=B}$CqEph>EsMGrwO7TRH00G_I8tv#e~!XXAtadre1uwQM@?3~ z{lTprmQ(bWCcx1VpOhS^UvnRFs{g;>X zrw{Z)P}vUS$<=W_Ko3C`$SJA z$+Dl67EX85rel`Vzz7#U;u}rf9FS%yak2lry^lgIl}f@3?V3Hzp>$HhG#mgF=cS%U z($Tx#Y#_cu-v^k~ z+~?pSd(@C+B0>$m<)e*V|2F(Dp7?=9@bu4pkd*~c9%|P{Y~0WeSFhA8YS!~U$58IW zS$$EQAlZ;)t*9f~vVcxIG^{g-*LdRTZHZeu>7Q+DKq$7W6_zWw^YwLXC|FR3NqWM) zSgNl6@w>=(F3Hzh`39Cdmo1mTA)f|beE)Xv>FGqk;K_H@_^?o9<@l?(TOyP(ejWLE z=*?9y09Zpv8K^f`-hT$Wk*h;Xs4-)f&#*0If8kQ9ROUw0stPObb1^1`!wwa3tcV^z z43-@8h8lECh*_cy{>i4`h1%a=@pMGY^3-k%kMJt>bB(h)zr~QSr3#PUDzCZ5q+nT~ zc;E#w!!;E>r&bG?*lHo;PXd@?vTl!I2SvaZ@!3$BMDvqPqW>n3|5FXc+Jb>F_Uj%8 zN)ftzZ?C&jlgm%LZv~5lYs)VLjXvj-Fw$-==`w62=R61s515Iu=geNYk^8|*_oX}L z$`Yom@z;YC`@nb-qVWBU#AII9@Hr;qK+TUb8`7m_$35=#^fA7 zEV9`^^7+%>yHDYRfS+heyCBE10uF;Mv>fiCTHalZXL7hgQqpq=zk{1a`4Kw9Ytd;L z2wY+#cqpV2lEVAC69e}5P5L5v@SysFA5BgpNrx-jE{CGd#bJx3-HetXp491l0rc<{ zzd{Xb`BC^PM+c7{IYY4oTPVyL2}U5f_(3&~9Q1ukmwiSexj=%u!CF?=aox$yL{2hZ zNsciyTz|hvP}p;aS7JE0TD%mk`r2oLmeLAcg?e!+iTjS8Y#dD`o&FOu945a)Xw*kI z#$C{+Yjs^1%`Bdv$qQhy4j)l}`e=3`BDbf^Pc5{f=MIpYM)8$B_&u>@nbDg*a96-B zLWfYxZExb-dpTW)q5Dh~2xJQO@H*Y9^~g&;*fbh>3rud1~lQlC0q3k!m`=-FIKNWm^$tzME9)&WXa zYwgS0C9n|hQHro^UyhNZE4nt*@GE$nUEX+E((dNHo{2U)3C|`0Nw{rvczOTgWGd#8 zEeoE>=fU*-y-DM;oW_|AXZ+O6_&3CzKe>HJhwkt0&kRKG<_n|O1b*esi_U?!nnC!?g_ueV;Df+WG)t6&c%!$#8YmNx6=3fD?lsHkaB_pKSuvfE zCq5ngF>O10T$2*Zbp<&9Ilnh z9{F^bJ7hCSF35Z_BxW8{mP16G3Vpq%DPIWyb_c0HT+n9Q-bcUOWZdS60wFw4I;j{F zraGUQo4ZV8xH&$mrQphd7(LlT$Pkd*G0_Jc%2~f2_@Y(7;@$bt z9xRB~kf_8cRt?e%#L$5aQ@XIyL>@)aGKr8M-Q?wP!~ZBv+1-d8l|mVyJw!16MfB%S zml*FB-UY8~0*R?Hbcy~Kr zcx^2Wj-?*Q+I%`PzF^^ta_x+D0 zmzXw!+-hWFN9f%4yQP3K&%^$`to+r$^GX)H(vP18FK*pDF6(k@JH?zR)E}WktriHp zuXTX^vM6bm7)fgq$TKi5uOWk`-2^Qr+}#dycyzby^aHQ4jzw`1_X;v29~>%983@r64WJ=6^E)Y!c|wo5|u z=34Oc`2J0ED!Lug54;jql6#BqEe0i5GKSf>{EL=6Mk?F%J!ye=xpCjqMlx~Ujoqio zNK{xY<*a#dZ%eFd3SW7VqS2Lx-?T=c*Ax#AdYn)ZruiQ6Nb?0}ZzfK!b(Q5QyxzIA zyaihPrnagI`QfF{q4f4pp(;BcEm%Dh!k;3%AarBNVwQ zy=~r5elWroQc+Q;AzgQ%Lu{CAx6nV4f1{Ej+61476=wG&CKMcjgz}DrFAH#G6dQN> zSd~svXKqHpH3}WF7pCx1CBwp07AcEhwEWS#chy_`Ud-uxu)Ry04e6SNhXI?P#^#L|dU75&Ag~w?R@}uMLg5oBpEpr4+Ico!#5bC6 z_wRzRYJ}|}#Ljk+CO?c_I+I;0Tj(Iqh99{!k5PAoYzFQf1AZ#B(Cd5F+Ye_6r&oFF zYI*eA0*(8sG6)ZNza1~OYfwDA=%1vTFi8NnfvD zUgk>55j(2q(@psjA9Zyisgxl&9tNJn?9DS`!Z1Jz2&Pl;A?7D$62n7NZPR!7DuDgl zN?R-*TbkeTIj11E_zlu+FHOJP(C#2I98#(NR4I$p};ue!$ z0{#PBF{n^$Dd*|@QV$%87E!N8m|{{sq$-)HtNd!|WyVh3r2~)KFEc399ZmCyERly~ z2ED~>U6rGI4!3bf(p*)mhw;!OaPStVXU~;_OUo&60X~-dN=e{-Po*%N`I3*c2DTS5 z>swq@8=osV*iZ=fNC`->@TC`MIBd#eP;9*T=}EZSys*H5B)U3}9ow7y=4GUF*wsPmi_ ziNiE+r!OGk-;%vMsC%wtfb6_?*+8M{8m`Ei;t*lGnrMsiN5VcYzhS{jLiHls?SGp)5)4QAV^i|pT8d!ip#t@ zc>fbzH*fHmnCZpYyK`q3S%c~pHA_h%*6~GFgR^mKoQ*hhL5$Njk4P+~W1b?T!+AAg zDBjJ5b-)I3>2LK%b4SFuWQSEBq$jJo!f=ZZ#Poqn|knyjlkw>Adq+I zmL0v){4Y4q&l*E>g??iPx{@&frx5VoJa~)DamHp)>gTU4c1x&NSKM_9v%Z)QQ#0SAkhPy;r zDUu~k!v&x3UByTN3*Cz7+Sl;0yzwej=)wtx2~(P3c?!Ng1zwrQUu?pluFPQEn^wZ? z;0NV8&EJZ?xWDc@Ew{X|9?-W+_V}Gd_Uds86of#+(DlhsK$8U_^Qz_~n%5!{=WLHC z8;1&R-pk$HLqHOt=gBf&tAFEYMlYrbmVK85zM2g{h+ifW(tHTm4zZIaM1AZZ?{ka` zqC0wb^An-J71;25#_I<+x2s=#!%wCIKg3la$fZt4?0VY!-iz@1wXKTwx>VKZK`83) z;Z~boZn0LNp>K~%>a@t^Y3YlsNbOj8GM9CdTC?P$6tukKYqL7FG`7`W}%VbVk%0lSQoX1pg{bkWu*??#T3KmdpGq&@lX$ zden3lGfYdJ;evJi(ooe06(kRv)i zr7}Kx2vfqx*LaVZ$o(!cZ2~@2K7>$Ii8s>sY%;83=ZTeRrs9`^2UFO8q9i&eq=KhO zYTmU@j?V%y(NT8VxPX?Ne0|#H{PYna9*#Xa2yKHZRNss@XZg&+^xeM19hs=S-GZZ2 zj^>*%9Tm5?0jDznru%u#8U>o#w-o?AvGUK^SQ ztl!vjM-MuXrl_pj{FB<$OR6D~h7sD=2$sLhD5*^B6zS_+%T`LnM#8^ zr}Uqv?5cE9J?`1A>4XVi)e+i#;9=66b2~JTXvm;A>f@l2H^!AE$@N zE+50HvQ_ZUNMU!QYsrDtm*;Hl3LQFx=q>Kt?PQ!Ei7uc6`#!DiW)dplSvlJnr1_$s zwu(A%*7P5Lv>?6(5P3;+H69iPeJe=46e7^kbhhX`!ymrqm0y}yOFi!vo&}uVeN|<$ zU68waL$`xxK6QNfj2*>9{gV2ZwySGK1z{?Kl-Y0lRu- zQ7aVxNUKelvi2R}33;Es1tTj3bOO@(e%UO+`C0iilSHA%WXpOB{fh-Uhk*tBb5Yzv zU-{MUKrcH{o4|jhxB!TjF7PX_>-xW}dGzgd>t!VjN9YX9nWf z|9@ARt|~#T1M%ixz7AEkI_w`1BU&yK8B2T}XjPYQeY!RHlS8M7A`Q3PUWU;C<{^s=Pu{DmrwMCj*n^%Jx&dSG=M3}4+2RJ9oOXNt(!b)HBn znD5HH?3UlUSi>I{bB%-7Uj=1)kv;V@aA1Pbj`>!h6k$C8vYL#9E0|RoyJtUcqq3*> z#!$Q4Ef|o^8-F7C$c0UMl@$_$T?#e$s2ErZUc9jwOaZ)v9z>+!BS-4=*TZHSVP%K21y2w;Fq$NPb zEG1Y-TE{HDXv<^ZUoR)!pe%^B7~0o z+9dJ{(JBC;uE@rsfz3aJ{>bRhIQlb1{>{rs(PtofOE5Qn12-@H_My0u(g+ET$xpArp;a!*{v%B%Pvij8$YCX@)=SOPzXUQ*Ef=cxM zR@QdtMDlNhP@k;T|5-LyZu3v0f5iLOp!+kB&ZgIYcFHgTsT(IQ?9&=@!!O={wM%lP zZfqmLCJ+~!eHutHJx*AQf9ce#_c#gs{K_P{gd=n0+Z>R9`lYHTHV3pYjs1OZtnV*s zO8OAAd3h4!X8A>dqUM>l$uu^HbVT$KxJQoO^%lpO@`PgRoFC_`QyRSSi0oN(&-&jI zRRfl_--)U-!2cT!(;OOr1FTQ*`4wTbu1?qPqemeReI$dmp8So8e|?W1eqH_D(}Nmp zn(T2x1X8BHz@p6ZR_8n&xG-bsc)H<|C(+d68qU9_(mtIBOJithGk_#U9nQN4!(>~b z)Ssj~-ivjb+bh#vWflXyYI<(R@L=1H_AD2x+6O=zh8{jjGf&0(Kj%QM$gG8{P;Ftf z#!=TPBRlh)nCR3SQF|b-^4U>)1(kRL9JS#HAeihYX)IPjmWz;@3KkO~27!(rMVsN5 zM7Q8YG$4>M*mq}-crd0L0nxIj!G(o6Mel%pMjeULDl)@BqMhiA#%&+&3vRDzi)W2g&_go=fgq-x$u8ukxVp>YHJEkebj*m;;y5RTX^-P(?cv6-vyaP zd~A>Pu${RMdOrLhz!%ECmpZuqJ%l5zb@6;W0P`y zh3jLD7k^9i^Y$-(mX2kxjP43yw>DQ~JWnebv7@Z^!}D(7EO>8a2&3JAq+<9Ym&Kp2 z(0xFEnV~+&Jj=Ebv8}>D+Zy1*zCu+``Xhp~piqAQc2tC^B#^TqJazXjrC@Q|rzHm_ z@42NHy=>7yxqxY>QVqwy=ZN6*|JU>nF>>GWxy`%`?*8xS^oWf%j^lifY3J#LhJ*>YF6y{}*KR5S3 zbEu;Y$#|Z9@uZsQ6tPxU$JY>6hcBO}g$FFKj<2|%eIcXz7jQP9*KnO?Y%=4M9Fxj; z#iiNqNIf4aC?rWg_mR~zm=6YQbN?4q`GT?77QG;N_ign{DK)d!3v_qxF%Vw8E=TnC zz3Th5v=8c)<{~&mL3-p`Y@BbIGLKUDs8r=B$Oo^*-%%%eASFpI8`M4vkp^jxiNhc4 z_^=lUd@@qi79SJPbn=Ay&Wp|~r*gkyKZB)*3`dZ=c3n+BHTB2sp|dr>Z~0W%-l6!| zkLNOj&BCmJ?7Zr zV_69?n@(jA-&Xz4*3QxIS22cQ7gRr-jPsH=`Ws7krQV(3sYwfkZ=9@9h&Q?)?qm!O z=OnGxSUS)#1}|eDLmJT&CcEZE&2RU5D+U;3Iudj*_iaWsp}RJtD!OAP7`;()e5~c5 zy_2&?@00hwWou1*y)H%OH$#L3JMpK|#C79y{F9EB(U4CzPuQAt(f?WA2Rt*4INJ zqXilzvuD9v<&Xj@4PfQ%*(`5DKQ9;Xa$GuiWDwhg-r$Iy$nZubVIOHA@Dgx*hd)AD zsT@G6w3Xs;?#q#n)R} zx+*@TrgTF^o@ALH5;)~F$XSMq`l`_tA)r&n;D0`9@<}9GSI+mNoBdZBEqQ^?0)(Ud5djjJvNFctl>-~> zgPrpRMhSwUX`;z7a(tftEbjF^DgX_|>D1yhfE%P`Z9jGm3zT8R0%a0D_m#U7+L(*7 zhxP<&n!i;H++ zm+Q4u_h|($cyI$iECb-0GFy58HSrL@AiXv$Vm~3Fy&!ttvM{=uR2c1>dO<2%`oVeg z^ykgff%QY_z!Ct0N1ZuwBMggjA_Y)RuDu44pi-Gg5F@)}bV0Pzfh-pFLvY3y;20lg z?#ze+@IYE!d1tJB`pp_lbu$_U?Ia>+ySJnvJ_O*7zPAEUDo4OCpYPtay9xu)MU*au z>1zN^>8B}x#`+96&`18w-GSuq=9hPT3B4&{B79wp?-hUv`qKJza{7@wRk6LCLXbq* z7wG*gk{Hr^1YZFtOA!EN;gG(%FZHUA>zm|qC0dKrWPL-D+3Zr$M|Jv+dj>qi1Qaev zMJe@qskB`pD(21k8~4X?<%%jPfdCE$T20F?!~|)6i~LiLi!Y3RdS_$l0Vf@?r<%M= z$G{7=Ch2Y$tIf=iTQhWuBT4JpM(3=vlCJqOA2WfXJ;zI5{10XhWS;`D>?_$-X z_(@aEwhOlvhP8V`nBL6^yE`m=}GW#2W+C zvBQ0AjL}dGiQ2oO-G9J7kzokNzd~S5xD+6Xeus|!`3$^;mFw43^B}pK1m9*H+nrGQtfVeM9z;JA69{0t{@UWN~eR{hRMg@HKC95 zThN5%9aM~r{x^vHgUy(UO7p@sV`+1y4VSb^ou zpJTKy%Gx&hVPQyQ*0)9h;99JSj3#vVW`=c4#h95F=v%v-)f$z)G$i03-?ScWDrav6 zd2`rM5eii5B7GAF0xtvM0&pEPa`~OKB#LEtQ=VQVOT`P@_=@U+>4?6dcDL}wP&*i{DmoETNd!TS&L9vVAymRl6ks;kMl03hI1 z6D*NoX~}o@6A1LE++K9SRnx&Q9%tc5vsx~dYb|===yhrcWoN!!x(x++qr0)MpD~}6 za;Ms{l@bz>TY^G(1)hr+FafIk8r9?avQJquN{_ieQ5PvV{?^6;l^m$FNoK%cWj6Ya z2MR&JLH@b_3B}2{;g+M> z9(-_0)=ZHt3f?uY`Ivc0*Awg$*uo^ET6*^x4*rQ7xt~;svA*WuMdJN+rjsDz=4zl2 z)!K;E{v~Q3TNSA*+=KbSYgc&phm(VDm}aUH4BfO`%M-Z7`9(5=G@GkyP|5DHen6lE zy{t)eR^s^e>I=AjB5!~Oxc)ToM@0XVMp2A?2BFz(pjildfY6grV26a}Q_8&=-g?ok zhrD)06tQ0I3|PE?|Gn$80aorm8ob?gH$PKszfsISd!hT_vn5*hUCT+%SkiT-!yo+5 zm^M`}4eZWG-eaV18=BxP25SU-4<5+`)GuMQ3wnrZhk9snfjGP`6|4~$^S(~}A<$w& z3byBJt``4O-(oQr!)k#*!&+GzdA!r)6I0OH+d8e7Tm%Ld{5SA8k(%g6DaMmDQYkb@*BV zuv3_HwjC2D`7-l$bav4kKI|9(3?aa3ZwL-4zBEozLi4v8u7H|-w%fUhQ<*UDo!AU> zRd#H=j(67`;_>)vU)gr9`63dejr)G+{7vb~CDs0LCF}j9EU&$Z++_ zHBFUVwC9bBq2T%Odv)GJ=4`eeUyi|Ui^syDk1lr*u?^gop{Aw?PQv~shBp9myNMU| zWNL$nl7hg#njpPhY^THL_Fxkk8(fpewm$x%UVPWniX>vOoyC_+_!v2&CCzySH^!`)W!OG1Cr? z;=9|?aA2<)04ZmP@X3C^-;D@`H^;YMxO^0lD|fByTp-+j8-3(vRcu(fJtH2xU%_m4 z0eAJRGIpb_N1LCFCNY1tCKAp`s~-yee#!-~fz>L6G2EVuVpV#J@P1`{^5Zj-2;c*( zGJaG|qh_&BSVFcT<{q10c>PjxIGYHoKaq`R5CN({{mf5%(s_xYIXN4dzTj`Np2$J6 z_X-6$g3j#3Fq~lG7eB1gB|vhBhbdpfajqwwe^WT}nrgK!Q+DY$Tzu+1Z>>Fz=y-PIb+p|*a=)lL7)hQNcS387Z zvAsmNp!#;f#Wx?Zc(C=O^owQw%H@xXKw(Id@ zlQ`{OpgHXeS7SZ+T zH>}Cn?w(C>uhuu4LFHm^@mmH43$L=(Qas{cK9^)YdMAit;*ybj6a5)8ndi&^XrL1d z)mMYel%W?4vKcBWX*~s)_}bWGM4U*&98Ut($VLKz}x}+e4oHUF*sMg=ht$gIG2wCWa$E42Cuo z0EXIhFdR8uCU9o7O$Sd4GwXw;!+hE?UaO4t6fAQG+3Xq;gAG1CyLJ?H%Osmc1_tjc zr8xpe!$~E26s}zRb<%@0iqGpB?y}OrD%_&eZuV>T?;fsZXb1FutpY^Mp@@g&kR1wn zp}jn*?yjfdZWM3TE`Bg^V`Btyy+S`XUh=sMib(Fohx0+abdtjnbUy*l6&3H(byqGK zi6~F!T~tm|hkljt_)%(kgEzOJ8}4-HZ5#H40G$4Hg)A#FyJJ=v^_Z7NSyj@(8}F$f zJx&L^**~*oDf2$Go^TEMto3j0?g^5*KOTop0PV^0fEzR z(_zrZtyaCeLUdx+?)QIq9%uIDi-R0=*Cy{rfHt0ap;g>o1i>u%?Ms%Dj?&xFuLTrVJ#iFt(C8J7|S+3 z@yyeGI`GrW4-6t93qO)fZ9BC7pV>VWq671-3`USUNKD3`tiO&bNzMVl0;y{9)%bmGZ25iM=!BI@cz(Q`m%tk^YhTFDF}-^byx|w}3E;Z%M z+OtB7+oaeC|A~x;BWeYPU~_G^u1rB}gg4!XG=|Y(oOWFFU$bkMdj# z#YXsVs;1iB(JBK~+!L`>JB#qg4$yw?X!X{J$OIAV#X%s#A0Wa<^1A1M{i$3i@$)ts zi@CG)k{X})Ufs};MyE2JNQWA5)O+zUORXN=UbGf1<)CZPXK=P$w@J!h5)#qh_z)%o zz#)7J%0c_GZ-lE)7oJ?FfujW1kA3FYn!{{f3-#t0+tOwa*QJ?yeD%w`olZH&3mIo7 zUH+&xreYp6NpuvLd|U!~%F$^;FCZe4>wy23tcb{(eTLxqqTT}MX1RM8f-6|6LxE52 zxwnEcx9Ea|+BE=iaBf$!5)@oSBtW@q@!- ztTRXVqCfnj6XzDMZqsO>4x1wyE> zmMHdrPiMs2J2F~mf;~$n4Fq3B%%wAL>oB)QMSZd$j8hzJq;EXECo9ZD#nFe<1N%b& zoIolVyGVr$co@FZtJAi2GrmV+0}iF$^!>OKE>oH5vGc&8tb4F}dNP~8+>#*N*bIdCo9 z+?EhF!-cO^#eIER1@&9RFiVI~e0eO>N^PdTVVSMWk?MesR^1Y*6GB&yUi`_IrQnT@ z`MLxcNw_#!ayAvvNX;vJ`f1pjHokK^Nx*vUjh4G4pBQzf>CjMlqv9t__=!6b32EpS zsSZ{S2ujOg@xVfD4F0hsY8$I>=sw-dV=uR}sEbz>nIGMXiKHm5M;M$@*fN zCY+$@a=iO$=1t!jE@;g?%FV@yM%V;kK(0vqmr*ZpQX!_h@1M>xiUO~LS z6%DoR&;BQ!;YyOge-`aB)35p)oof3(P5u$=pW*YLoFtO_vV{KlrZYc+k{G{8Q*D0= zFeqKvz3(j9AwiD~?|<^iM(tD7=RV+W?h3&B`SIdyBhiq zD*hWT=t-?EL_P=Z)3;CUN;lx+O&672rPDEmH{AQpZ-o_q*|{RLL%IwkND0^m;&C|Siff)8c-vtS3;@Z3|94EFsaNL1>s{C6 z-%ua#9ON+Cbpqgk+8E!cZ{gG;(S!>pS%t-sE4#~tKk1J!W+bWNg<}K&_A<2b~1k%z&v* zKvThFX>gM=$bwiH5sfm1praB3q zC?W&MsJ;samx0X+zh0#LTdfI*A;tyOdqB1szJ20#%TK-ZiG3T?H zk5tdPS!q6WU9r_7|5M;UF9&iV)EJ)9H2=p4d;8$~H$-r}Oo9q38r5amYlLRi=TP6S z>?`@ApQrd|Co8p6yM0dnwJ^iWI9qe8u~(vD;p?wwOa2Oa<|{$VGSd<&KC|1!H{&fZ ztItt|uTt&GcE0b036 z>eZ7BCrD$-(SRm@+@@4D*LM9=J+t+s=dt5aa^wPF)lO(=<|DNzn3ExR0Njye6Q2V@ z6mp|ia%cuPMI9jydaeg!NxV@iN2h~&jGQ-7E1&z1VY@HeJ3;!}$s-SvElQgOYY7&P zF;hrJ;hjO3$>qe&RfV+D`tc2`(5+hfQoYzs#--!U$5x#f(*cMR-BBr!_JF->svG8n zMyzs$g6$LhZs>v0)zz2pJl2ebv>}evXu!UaKHQz)73j(8aogJf$^omYacx(N-h-&O zoi+ofjkX6LINt!-V}#MSBQmYa#+b*yW6im}2dn4@ExPWnGd8(Y&W@FdPb9q2)F#r& zt`2$pwZCn9uvnYXqADPkzMwk;FwykGp=*|f5br}_3phR`b^z(8~eZb2T5oHGEb3i@8KIMG&>v zjg>z2yHT@wm&{kB;fb1{>K3==p+;3sp*f$MeCv!9is>)bLPq7bOmzJ$6x+-QXoqq_ z1QhLuhCHWbNm5(MMGBp3j8vIGTYQ^tNG?Oa?#g+)r!gP4GhP^ZudWWnCJzxPqBT6e zuXQh%8r;8mVo7zfC00sv2f$#fyH^B!QCp*8ez6l+Yr*+hlfUjFr zH@xVa%1*E=tN&O6Wb|e;_NQpgV8@**OZKy^qhN6Z!j^Y(1fOE2ogmGI&aJQY1tT-* zjXZ#>;yNV`E3SgJZ|^$}2E3AYxR24r*nymyc~9SRY#p1N40HCHRguzUh0KxAe6T@R z4Lp2jjcE3PU*}2G_1&%Pi%l#Po|2HiO6GmTT=JoMBcyXaYJq?clm7CTQOogi`Q$OI z_2of)B5H&Vvoux3?%RM*qVQ}K%>crPp}n=4u>UWus#3lg>)PeYpEwo6eAWicmh~6S z+^G4_d`V>>e*EKAGGJHhKS%_V##2@r-F6Sq6;;izNQTF~rXn{UbpgB{y?`f9b^KKw z_bW=d1+lb1dO&ViGdV!`+-m_?i3OM+5Sz(qKUB3bCBWhg-s%5k`;RIidSOP$(KFwB zGBQgzWb|xE{YT=1V2k2JOSl-CJXg%-ic8H-1bO+xA8ySC(XsELGcRgm)Mq!`pWM9y zLYggCla;gUkzux#dh`AFMO%>`bE{?h-}iQf#Dd+#S;DGJvlOqXP>A9xG{aW{-dVh; zWzvbDQVGwf*^EjV^LRIwc#km}a6cwYZ>MUGPoA<{MW)8wA-F`>IN{pk5@qoH1b5KC z*;A@4Xhnd%_sz7|&Oi#xZCThLx>!E^;~Ol90S>?#7~WM~s(;@8>|z2fvxhe=zA+!# z|8OKD&MJLh_8lW`D7}Z5@Q+NHJ5T20`cZojL_z&tj~6RmQBgA!MmNLskgkPj@lr|? z_p3h646&1f%5`g6B{YEr614428`oR@!J!i~oY<1vm+by&?#eJH_pTQUDS=j&PpjUE zV($i5NU>QbeJ#i7FSzj)yU7|KLctqFMIjVN0m4p^BaHVDz@?$|ZmjJ(4#?fvNq^RM z5PBCx1I7|&iHducEQr6DVKCu5YaNh#1B%6I?hp!bfg;*5ebzuZr8 zoI=kzI%ikZdhx9jh28AC=H&onW3?YgXmegiX+LIBPP5$@xW#iI1=n#LQl7BJ`VAn{ z{9bY+O^9Ho1Z=`N^yuwP6^fU)fO|ciNbB@4E&AC}*SV5e4j*4UBVC2|tC3~AYYa3N z58U+GB>ck~b^1I^LZj)~+wUAixpUsYO`j)6V^{rhy@sw==m2+r0-rYJVEez0p*c^~ zmi(J;`r+ccYXD9(u?u~=q^KVIv&mvdYGc6IWy@iCnNh+BiR=X*Zge0Jc~mD_1Q+)M z2>h+^U01qHM&KO$x+#b^q4Ao_@^9*wBO6!aoRCm~DAkY?`-HS;E=4sR9E6b{9GjpkIeSZF5I|O|cCZ6FFQd+W z*7ld{lgSsITfHsYN3_gEv3R^vMfqc?{YZkBNR-pcyalwmClRtIKnwQu^##Ui?=Gea zjP^!Stw&=F;UEy$_g6IFzqvH^{F#bc5~d#>W%Hb`R)6K_GSb2bytEn>LmH-cqdWvP zvg)&pJcVFTGN-ndsOF1jZXVzVG|Hw7h_r&whafgmRxwzEDLXdwipWMG7=JNH(d+#g z{N!0N06#hRZN8>9AC&wjZle~sP7q=_xbS$cyy#hsFW~A7ImP^f#g3(hNLi($fhmxExThjL9UUU3o56f>p)TGW*kQsfOXkM31e1}y@>n?%m;<7 z`+$1~>ud6Mbc0_Uxdjx!24WC{G1+ael=iaV! z2P+3eWI=COnN;I*0P)&OH3?)7P{IdigoF zhpt64NarSv@@83+m+;Sn{p5EN>RXZh8Hinb?^%4Ve%Cj3OF0b29{#(U3MmGTOniYJ@D^waU80_|)HjH)6TnWM1t--QG&&%HF&9h^Iy+z}-@vafr>a5tYxg z+WtPRjJ>J@kSxQ;susGA>q*Pr9Gu2zzy8iKuDa01Z>O$Man~L&pwA!>azb&%Xs<{0 z2azv(HKP2z^kN)0yt-W(O%n8ioPK<=iaS)^ss%<-uw5CN3?>K{J|-7An+JEe3`+>xaAPmdjM`JPW3@YECZKKsiB?W zY0HXA_qE2odU9+*>0joxdqa?^*H{DT6EO?5EGuv8 zP>nA87UWldjR|jbMJ009X6AE`avoNXJ)KU7RTYnCU}J`IQFI@SCJ*GXOaB<7;wg#) z%_8&nwwzF&!rMrA52cO~X9i|i2~<|n(owa%PWtXa!?UX13FDUz!Y6C02_QqTjPS3N z`E25Y;9S2c)8K=i%c^<_9j)Pe2|`<13A&3W$vMrdb1!>$K@VF}-4E-R-*S}Q5t`f2 zuk7Phz0XlvcNJxjC3fTu%|jicom1DA(qFE|T~igSK(2+d$4%-O>oLH;cP7|~!>O0Q zaZP25{d%FKjyzd@49wouRgosGbV8}}j!%(PeVjAUUC=S}R;TbjUfAUF#}u?-dQ;!E z9!(wniW1~#e9x3!xtwcX&dQ*s8mZV4a04{GXF^UCB5uD^dkOlhu(w=o+yqSD{b|xV zC0?M=QQypA`=cQ!&O#!e0j?5fmsGj;8-DgzCsHg6>k`iRXV zm#K@(^aW>}gZKJuB$`t_HZXv=PF~DTP+J9Fx^ZXQw{zN0=y@j?(M!K9I*)R!U;Fy5 zmr}=A8|?*S?1d%x7>)8Uat0sVEarnbwkg0ee5k^e}4KSi9ciFzwcD= zgWRL_%aEDp61+>HGDCIm;c+`hgWI4Vk8Gq5dt5#p%S@i=UC=xskLN&hHRFlZxDTK} zJ}DlLd`KWAexVoAp9Q%CNk`fAtIq%8YUv7Eesn5fVm{D-RJ96i8~8-O02v1z(nIey z`fdDl`E~#vD%&9#X`k|{$?L(HE;D@4v^T!D5e!z8V}PD{g|1rKa1Y|@-21#D_# zJ&U3#krtNk<=gwrI}ne@yG{Fwx%pU+leSR8w2~_PZ4oEC`4SN{N7q zNQsDw)F`0XBO)R-Dk4agUPDws6oe=O5m6!{qEbTd5Cx#3)Yi4E6x$b$-`}$qkqc4f}ld#DSp%zty;Ar%Lt$ft%eV8gP zn9)<*W4ol=a~E-*qS(dcQ<0U~oR!SYQ&Y;BZ>{|YkT~y!Vv?D5XqM5CRPg$(G|#fm zC*&7Guu1K!O;?&e2jbI`8d8-rUqNqAZ$z<%0x$tpbb|tDFi*dvT0ljzDq9#N z1R`#=-mJh;Z9rQ>GMuZ7g7lGBfBZ*?jBZBM#&}2r6dE*|xQ1GYT?G+e9R|}SXT6!5` z?a=vjNt@~$kBTw>DRTZT`c<ADItYw*Eml}*P`;EtW1lH*ly@Q;M<%Xwz>alaw?(hPUPIHBcX$zX09yLvSs9n zy$Wqk_4B6r_ckgw0(rIM0Md~C;wR<59;m0pULUS@G9YV`UjgiFj*gB4fV00@!z>&j z9U8(2R&_+Flh`be~`=r7%f;j^G#a1LmH-86*HCWqP2b=l$ir`w>_tNNfQ+N!wtKtq%sZozP zm|o>a(Y`qPC6j;MBjOvWdB^<&Sr2I_pc2dsea$+DR(^M>ykr=3W}g@fK5A~5r2!~v zNgWj4%urMMMi<5_LN&29u}7`|!p@j3C> zH0H-wD5J(IzCPW7N6$J}LtmI^pF9wA20^`?}5Z)K-1N2X*b@+Z1M>KAE9Y^Bad( zT%O~OHR9kA&Rs-R;Jos?>-NSDzCU@CfjvhA!`$J3B<=b7Vq9c=-D?~FK0h>#;ea1I zZ#s(yqxB@^@adQISaB_ar^ZJa4`<3Mojd4+zdF3U$O?p*%r{~`y|cOZ^YYF{6re}@ zCAP=87lQUMQ!5SpaGS$%wR1qYTX$_raBkui>~4sUsO{6eA0{Nm;Sq>f!_UHAd;-Ub z@575^bo8`s-*%|;#oB7LgE;PWu6OB+L%1JZriqSAQ2bRl+w*AMfxW-8?QF~(sF+1L z;ZaR){;kRblWJ3>XQp1sXHWKvHkaBOcrMg2e12`eo?aIcr&V zL4G?d99)vuRogq6reAvfNBzkzE~h`-m$=7_wQ?dW4jCq;dOxT&Bw~t}WrO0^4~cwtx>np4t)EtBdS9?BXFPe`&^>UN3v}ylw%M z2Bytp_lQ9)1I{S^?$6cn{ zTN?(|QqSE-1I;ne>w-|O!OGW{dg`!FLfs5Qy0NQETfSNxHe^(o20b@bobp>>Yw|}D zd|B(Lx4iiNkb%nvonoPC$lI0l+!dE?vo~RN<&GJNH$LF6;GYr>G`yRRVX|tdLq88t z0D>G!B`c@oY&p4Sz!4SbrdB$SPr3-LtXjnS`**wXT|27yO+9hhMRB%cmXFEy2F^e{&t)2pdVzOm|!U&_*ybmDLDc zWZV$R3H^~jmm z9omR;5BP|4IE69N%fTRuoMT&YkHiGTv&_u<>Sr?I&T?bR%Y|Z!2f5p(`pr~-wPOw? z*SLK3ym+zJn~@kv&s|@en|-x5)93}?xSVmRn!M2Qr|6)}x2N?;ja8?2n9^-a>>^Rtxkc9^X9r+9@FmSC#OgN~}KXhwY%B4u1uappIZ(Fwzwq z5lE$_>)SwKT>hg<erpz2$DC z)zXI_rIP$dN!=}@Cn2&QU6&KU=1UWO^J5mfo zn!Pzcw0}w}u5PWb=+w@<#ODmVCOTrQZ*qp`3Mm*!Y6g0QWLn>H|BmC*RlG|m4O>&fSU!+ z#E%1EHaHVpL*UyDZd!AezgTTM(7dgNZehV28_fyP@S8=ls3|}4#Y}rEkLn3~oiO$d z?9ZC}g^q+PDZH#n{M08s!W8!>rt{a<@{c2A`O*hEryJoet z$Cpd?z4Jb|FqPyGXIS7?Gjs4Gsp{9jd1dT1dv5U(kq~lsP;ZvLe)5sc8bpLt8BFb&VZ zE}K@wy(Lno)^xWt0A`fmD;r(SRL0U?73`u4OIa|>6Ij(OJI72Cs6_=gzNf#4xx!G@ z-Uc2^@1@yBwyE3R+xb+kNG7>9jKmFi+AxP$)mPq^y$XA*d~2!mfnl(9J$J;y-c&pP z#SM@2lp8(vP6q6wi1jK!>zR8=F)Eg^FQgShh|$ll%Kh%icX~^aPrgTLd}_rvrc&RN z%t9kSFjj;3mGOw!?|cRlJxOgm6t#dKF?1ZrDNV}vJzPCLX<_4j5ozY+$J3nfK}sRiwG9C*|AAlN&7iqHR%EOCJvS$ z9N7kzr-2H?mj8`6;>|xDbhRJ#={I#``(D3W&-zcDg@AaG@4_mnkMyLcUZP@$X3jnh znV!4D`5A{NSUDvg0Ba5{I*S+5sqQKRv@FegbXNuEbV=Hsm}yA`X|Cvow^-c_`J~{L zIs$712)#$}AJq=CsabucTI3l$2D^YVG+d z8mB8kivw^C)~wxbTJ`8fFgX`Al4WUhvbmg$E*&%%EEr^pe?+F8LF44g(0(`UZ3BrQ zG{svzT61w$q%E7Zk4 z->%r1Vl{n;Z^(d$CltZ%C#5V0%>1BWO!a9m$x?WpMV~jp@|r&%ZMtafnrk1Y$IKFu zV$TpmbF1bIsD;aodf>+M>*I5`XhijZAwTqDW2|;kiomz9>a4@7%l5ap-~D>s1Nzap zj<5(0f|f#WQMwNcbZD1MEpt2LmIfUN=*^ukM1wocZ!4))S-eMvxRjYd&#D>tO3`-R zsmmw6;65m9YQql=pDnKu_|3eUYxBYglH%AB=!7@%y1lRKY#mj196wg;b%(K`PQL-d zbf}`dKE5L5tz{w@8mS3jZ!wT~>}S%FrMYM-Kwtyx`$7w)%(E9IP*c#b<=x~7U!}Ok zlquMFQ#wKT{#)1W7mVAjqGV05+$7q^1hQp^Ovno?YZ9DeKFA!9|8ccsE3~SNH_(tW z6K1ZDL&c~?D;tU95WmT7OGZqMI1e>RAMQ4P?0NK}zEHrCyI>BE5!HV3+YzIE z>0-UexY6*PYp4F6KUV8}HJ|NSe?RW8LCT@BjnPh{+n@ZYLSS??4^D3 zZ*P9G?Ew%r|K8=dJeTJ>MOS~a=5|yr z9u8EjKO&>%E%|MiujF4c&J&hqyr=f0Zv%apPSFhz?yhR)9Yb%`v9=VbjXi!DAC0|C z`Dw0DLMC0wGXm(cL!gR%`isOxm8gEn_VV0$_6&Vm*tRO-)>)mv#!QT8YK;kdf$FJ_ zJGtabAfC=LWScn_ljYTk_py4A>c{C*0I%6{ItzB!@?Jt|bzpfx+Y`dM)b8oCB9oMf zk;nESkCctxo`IM2j-@-DV8iklElii^?)Sh<2R=(X{G4YIk(*<_+a~aI7SL8YWY>ct zsrWuL`3#!Fk?zPclDhYg$C|!90LPC`nDR>#k*}iq%O`) z4T@A_wS&@bg?^%$JZ+nPCf*x}s${b$HUe9X>d6A{ABmQolIwF1J7GhvumvnMNn~6J z29vmR&|uH_+_hJw&x9I@xEHBRPdL}Xp8c)avw zgRork0nD{rRTYwjC8m)0!68X`mowkbaA(k#O|Zy2WfHilC{O1{%1v)j^Q)2F0YB$@ zx;r$Bq^-WmgGoOq@|j13$Q*i5MB+YD*#e_kp%-f=_%^r79hZXH^w>Db#oQx8aw~K7 zUHvLHN5l4>=qM2~NShGi*5F!G4N_8%6`Xzr22S=ihGjs_g~^gBE?OO7AI83D9e$od zMBNTKepV%5(96lngT3p=qva?faK^^Xes$L#-u^_VoDyrRz}q$F54rt9zy#qWT1w6$ zdS=rafvRacSc#9_v=FWdIEqiL6-KV%p8^){D1R30@0pW)R%f1Rrt~+9<2S@0H#&~X zC?Un__-<1_>woGakFAWu(r0R^Mr+rR#ajionQ4}vf5o=0A@F&*F z+dAa1W<4O}zFH!v=WnTIT2hCU7fMs-w~)+QC#{{R zuL$k|9hObUVUP(k-)z~{c(Hf(VXP<)M`$r&{N&XQx}(TUpe%9X^V=@5!Bh5(@1d7l z(!_XlN>O?WxiNo(knkzKDxIFC>Ho>nq3H&CVO|Rk4H)*av~qP9>?o6mbL(bQ#m`sypeU+w;b&u0<(RXpVG-@+x6y`XfK7tIyKXh zpVm%%Z$z|0E6vcdvK;uLU1(s-n4`Qo*N@EYvP> z*U=`}V5T+7wV6ER6#_;#d}_|-lM+r{q|wlcGS5US2>RWmU z#P7I0`0K8@^tRUU!|^gF49X@@0pJ(F;8%`+iP~OQPM%eTVvrO3T`4XfUpx}NIu!U; zHgGA;+t$sIMFc22gWhdCt$Wlxxn28HUdvePfLmcKL3yTmzth{G69#9-9WM*`tbt6o z(uEVXXf|tj?j6|&!Q0|Au0hrsB_-VAHkoc$i9*glxaPD-r{_M}#ikwB z@Is#19r^v6+GjEcGF}u?^ELeYoEg3ewYcDm!()maVR^$;cln31ck65w{J-20ys*G#+ti4uT zH91wY+h#?=SF4Gh(CXfXZ@14(u%T8A&~WFqjg~G$WD94wa8=T9s4xH9d-e&3nvikCybCB@ZsZ2<9uirGUQ{zH z>GNo$O+c{wUxtdvc=8^5^TbfsLw-if`uvjcRjU0&Zi34i!y{Jrv8V5VkOGvY9oUQx z6hwbiX(jp*{MSjYvk4jt+~mW!Gw{UN6aA;kq`+rr|4`Y;Iq7Ji;s#C649nY9VVR`~ z=2!G$<2#2VmK)`MOrY5)A4Bk|p^}M+Q*^0LFFnSjWJ>{|Q)+amvTmu&!7+WUFI(eL~@MDG?jy!+#E|7&5gFps8FhmndA0r?Z#>y(WKy$Lyvnc7w5 zZ@p*lTkqLlj-L2?OeeqDqIr%-ItQZkI4-~Y166zQcQI@YuXt(|S2JF~Jq|E|CDRs( zs4i*pcLLyyXxEv;I4=K?l9@y`xVR?Bc$Ar)|K*W4T(Pnt5sv9XEyom)FCw}pVM`Ci zFgYc`XS#$TQz0Xja5fHL?Xdw?pNZ=W_P^!@j3Bj#>V3)vo9e#%VWfN7)Ss_BdCzP< zw7Whcuh?<>ztFyaxrYC*q8}B%Xd7*-Sf_OI?4|KtYb?53h_4lA@Okq!A#XrCBoR%D zycf4p}-SxVC+0Y{rpq0c5=OQ>iW) zcW~Mw7E-Fh01`4*B)GgGRhrg$^d&M_Bx@A3LO2t2d=vMJq@e(m9{$9NoNmnLs|6oF z+k^*PXP(4$Lrf)n2q&ThUwOeN3?x1<@zO)vyp5{&Y&hYaNTKp2gB9xywmHIj-aF{e zwh?zAv%*nkV4=}&0*o#}$1G@DpXKaaFL$mLeV3=*j~lv`TrgU<%1~NZ_L6n`+4z3X za@_0vm*&6U?|4Y|CI}IT@Q7YVr?BHs!Y&M^22Byc6c0)T#_4?K$d&W|DC?FH8{fp5 z-O$^Bd%4Oecl!BCbN3|C<*Vw-Gx0`Q`WKo2$-+&XTC~yNE|kKP z;odIz;DD1JnO{te<=peebXP3d@c1z3Nx&#bF`{PW3~OdO9jylaXz5Tt0h`Q2Cxwf> zIiTs*=%c*4b?!LHIz78++?;@GKUpYi@7exswXRFT&=j|^k1I!gDfFEJ6yw73v-xi+ z(@}B-&0TvRi0nr&!7ybLxB(r~2!C{PY1AqS>uy^v+GB%eI<$c`tf~oG&M?C(h;NM? zgb94pXur#w@|6vb$%n2z&M3i++#V<(8dAg0d&?P>Z~tU#l*MqWl9!|VsF2K6NXZFv z4iH%Us{UiYiA?b&^CKT$xo9bzNj!UbljyWYJV{->q-LARz2kAO>y_5{jNfPlj_@!r zwgKzk$5w^GLS2yog}yNdLpI?2JnU4`xzWW)p>al<+})joXu1v@o_sty;BGR4DT zmkoL>Yj}?27siH0+V!?Z6Mhp10gcM4;wq$Aa9gx{Kg)jrU&EV@fW#y=j?~7qezg4X z)>UoYU3^mN3Gdox%9vMh!$|v#p#z|77 zExKEe`PaU4aWTF0^|67bmuh$a9zErQ@oWe6t9}@zVF~jd?BRWWn}29J?`wo4ZU#Yl z2eJe&sOzzcuMhFP4N-4X53aVidW*t{L^Z(HuX z{YvBE8d!4uZ=mHGh#B;zXn06`x;yHbVJ$+AY9Qg3juaExc&OO+c1UmkmkD=}? z&!zrpK>dD&J7QPXJa5RWAx*^JY77I($N1KsebomAlbEVqDa8dJej>ykq5u2U4;AI4DT9FC!Aw zV3d9z0-11QZdR)2P0BzJ1Ss^+NICWNcsPx|jQbQ*i{A)=C@B zKJ{?|o@H~!TINnO$1HW~-93T~!J9Dks4s~LcsG03pc;wC_OYi2hF7k~KsvhAU!caK zh=?ovB~HALJ%hEa3h`#dG&Y1fx0?J+exGvR9b8=FhrtjO4fW15qBqea;(hLe{Z2n6 z6_P%Ju?Uj-wtzEBOv8uaQ*|RPSwV(BM>sv&N!7zOnfrP5W~R+qn#U>^!DYIw(QGI= z1mIT}bfpN)Yvw7YJUX+`9DbOfACxTY%L9Wb);D$#58|_;+%n~>6k$mN3Rwq6E95K^ zDF-&3lTK7n*r#~x(7_!$@+#M@v$?xNJaNzdvwI?rY5g2}Jf!|=i;>9a!+rarw;kR3 zc!&7uO2>|eN2NEtRCyt;5Rta|MHQ*ig=Agq->t(sKoWU0{|f4atM2(~4&Z^Wx?oZM zFni%V1m+b*uBI}SlM>hgR$LO(vshWzmfc~@*0@q6Bb-Y6l^L~cSrh+Z@Zr)EeBgxl z2-om^bqTG8rNP3FAd>(-KJ3Q>Fs57ZL@b74LUhdpZ`_fIG77Vj3eVMX6A)mT?_U>% zub?$9;=>5%3298-ymt@AwJ@2fOGQ@!Z>4(2dB4D21WV0OY+nc;_1z;PFtl1?{r0&z ze`ab9bcET*EnA_L;C1hp(-Ot#I(KU~GZ|uVWHgc=?jBZTK!A1EY`={-Q)eczwY27o zvF4y25g0d8tykY}`dqVwbAape+*>I^o?(t%m8wDcO`IGR%rj8-*w1Ex570raP-r7; zG%T-YH3=U)=Zy;i^cxXhCY2z|9b^eHRFij)6~Z=bsi~l3RD_#Ux4p83)?NxQyhk4i z$Mfg+IH`fNKDL!a8lhPna^xlElr~VV&s6B~3$b>B!3Ij#mB0q?C+!zyP|%Q>7>vwF zlSj`Ovn>bUxfBBYcL2$7?sy#J{$CGvU(>u~1!Mz}T#i)wZZp#YZ|P3Wug03TIszXa zWfgw};Kf+Qyr$!^&BX_AcHX%jb*F4iOb=aC)rT6~L@4kwPjo+&$bZvnCKo-{`bXRI zo7#5$7BaGxQOeV>b`^R)o$ln0+x}x|ja>-px0>l_oba4#{h3?*97L>{YsZDF;Yr5q zJJ;J{0>YSX?%xCl52Gr6g-w6u4=ug)SE|=3xkc)%2qg1G{dkzf zIIV$=J-6H~9TrdHcP;uPAdfffn#-zaa{$27o>pA3*&w4%v76_xok@7PQ>Sc80*;OnJPvpoRLWY=O(=cTn(_%lyHWlcQNl2}o z>OS_h8sJ!eO;EHk>$}sCgFaqmd;JNrS{qQ#uS};6nRqXrq** zS0nBShNV#MAzM%|`V zn|m4l1RM1eO!@Yp%GZ(2$sm+Y+2Q;`)Vqy>7^dH0lEHXzPbE9L+l}n1IlM~2O~k4q z__KWkgGELm^X{gQy>USgdP(?2I3_(e;O=E=V5452x#6(g2x7=oX;>-*L_?Ty20@3fVHE`t;9|Cp&J+POuQ6b z+beOjSjvfgzW3yXOV?^nTF{dyPQ;$yuYJODR9`y%dErN*_O%Vpfi;RYGEM(*iBt9* zfAE`2oO(dv)L6UaU00z$n<8SL;D3&RIURKDx|9R5J2pt4q^K4YKl*K4!jS69Yy%e<;Ylsa{Dd?6c8-i4xbYr~`0#1FJ626UiQjY}raTt74uUSd3M* z5Ug4Oz6T+%10yXyZx21*V9(96VrwsIb5DaaI9I;d0cbQF@>su$@s@nZLe%V?_{c04 zr?Ouo-6N41CNp&x^P&3Z)AGohA}hOP6fWElE9A9@$5{yq4b;=z$b3A#4vUaq(qjr6 zgjfjoB4%6OIf7*tru~p6_a`vmBU+ufT8NHdp~^4H73q(bjFj3kD!1n%Y?d26`4I-O zV}rr11*%)?R8j1+1eSd8xgQ*`Z}Ladz@{3YKl6dQ#`!1PLkc392&{;i$A>&2xsb=* zqmoYfDAeHw^i47AA;_R^=P>XIs&4VfA!_ zt9blo|8S#)41Kw=YXl!GJ%k|Y@qkb6%1kZMA0uIls+MDwlNW7*UKXa+_x`f!2v)J0q2ISMwJ`DOl@NL6M}3 zw=g$-wVB~pb|aOx#3cqXy;n3%)v@dqrz8ZIp$tXc#tHFBU#&(mLr0MWM-88I?sva* z&)gsg!&W3<=M?6PhsXS3w^5&gMe=vCpsUDWVXg}Ue?5fQDC)Dio>Gh+y;Ztl1Is%0qg<+i@;_rp>cLf94q)#|LN*0t(F(wc5xi z)PO%z8R*6dstI1O05tibkVXmbOYF$2g@eL!C{sDVUo;M>x+0jccm^8OOdFABOzV0a z5o|#;jDk^aRTy$p18R(Lqe6GG0Ap{svJL>Z0ImcRyx$@ZT<+sd4429VO^T_D=?c~n zigCyVayUfLK`U!C^kP3px}QxxFOBjvoDpTr-B`LZx9)~N`L(mTqmsr`PKae!XQt&5 zodO^mFM95Iv*#2W+K9K<_s1)xTu`Ltmy7q;a8Xvm-*~CI``cb%0R~Y1L=$am6eBQ& zOT?mh>-Yb$y~Fq0=8fVni%ESH#GK~-ND~O)HYe>zCUzu!mH1mX(Z8*L{bCND6$xUZ z?*7=2y*%K+C&!9+5xP~?Q$=-O^X!i9JlvW1Y?GPwwoKI-u>X2_u+u#Tcv+hL_)DAi zj2niu)Q&{qA`fXBRduE|Tn&50N=5gJZXg~)#CCE)>28@_kfOAXjw=<2Cz!n-iO9HEi8ipm)1AFAO9 z&njXZn1W@2rwf9+{G2OCMp}=U!g$a=lurEuxF^I-Lh*X72wu#)TZh2bfg~rUT4O&c zyoxn}`070aL}T*z>JPho^N>rBQ2>uFQP%3Sg?lIF1}?CYSgHB?BDaAGIiXt5h(msu?*Tg3p9 zdGd)KPy~i~U09c4B*6i~G6|6*W`Sk}Su2wC&-}&bR_=;0}g? zE8c#)ln?wwmC7jCuPDo+viM?HAjdO^Kn^1EtNQ^GUcew5viLv1d4!!MM}ZjvuJ-gd zge(O6XvpK{0Pe{W2dt~Mz4n`{nqlWbFSik0r_$kJ@jzX|NBs*X+>Xj`wGl(O+|*NI3CxN+c!GX5rzdPlXzdn4ESsrJ}2aWI%l zwNDkfP0cyZD-MC=4>C6~_ir57!gvWsm4o@V?nYqL={RRdxL;BscLE-9sD@@DGALr! zpJ2L(y#+tLY8JBB$lz%)d)^9Rvk2Hw?G61KET0_ZLh#_6uhj8!BqW*4f`o>X-^a+E zqB0!_V z9OwjnOe|!Y)?{kv%YKaHH>rCfxnwQuGAxy3IRR~c6Brv;%`(79^@bddI#l@+h=K== zTuYVj%$`14e_rOPLXNv?sp28O(`bNWA_B&T1^0nKz?Fet$nh-JCxKe6IbCiR!fw$6 zF2t_H7iMD%a2RZQA{G_)TU401(U`PR zLtpe#|EX>F-7U&@o&NHtH~}n7D!4UW(UBzgKmY9?Hv#kA+w7#umW~~{FQoag*n)gx zL&o2ef-S1$aoU`bjlc9k_kB-_O0w2E;y>&txYZF~yV2UNZy!bLU-aBaw2?@t_?!(3 zRg55+U%V>awyRRFDb`3PV4#Ng${*6``wO3%GrXY19Ak?@?!zNak^sLDc6c9(ou;Y* zS4UJH>30>olB8@{MM-z+5fC8t+pBp8Fxot7%Js&|SRm4=KcH92wQs&ypIxSev5~hB zO=6rKv^t6(5my4aYG9BTF6RZ$d3tdftMK$LiBk zHA)ixL=v#D8c@;MorEYKU|AZY3L?1|0l4nsQ*sgsRwU0cB=RcBLl7MTu+Jl@P6L(K zJ=zea_60x-S_YB|YiOcOv(#X-)UYwAI3(3z-RLWXbr@9?Vk6)PIjvq~VJ6=V2)1ii zwRn#V*gBMRc8P7Kj@aKAYzcWOs5~i~C-;M4rsW^GekOha`f!=`hE(IPBUp{P8I@7% zcceE~+!K)-dImHB4)Fw6*zMi}1H)cAd;}bqidbb&Bt;ocu66)a7)vY(!S8O2Bm%$S zyux3#2nGcfFhzSyF$@Umj6vK%P4cT)orb_qV8IhLK$fDSu;l4EOs4pq!5a3rbpna0?)KcEqR>VzD zlh4IPIHLT+j+Vzri5D^-0rD9&K$W2pKz4wO216k~W- zXS~8xjb+G8CBT7Sa@EuV;Dil|7s++%8ZiliFj2s{H-yrzA8>o|`hcNgfoYol_0&BA1la<)+}zN@I2j*E@+OkcweQYjX=GXoS3 zjJQxkBQs3DoXG{~(#>EgnMQpLSE6rz3263}k7y?XEmrVbalCTC-j&ab)&^pb^mVrxRzGE04Q~C*9c`5_mB^ULN^ylw67J__!3# zkKy9lwku?YfUg2tGhv0Y&hR}tyrnD+OvNt+jV1wsxiiun2F@t1BPX5MVx)=&?i05bkFp{Xy+s7shAaM{lLW7?ag&X>H5f2T5lj7ncOA z#Q|4Dq8CU;IxU#o32eKVWdOdzcuVANTyR?fE?bo;G_)%>Fp>-z=4(7}U1DQgxwLw8 z*A+da4n4atDGNnpsaaOej@i@YI8d(ccE~?000X;(b{Lr-XHx^jv@;r4`!M=2fX9O# zCXMI_C|f3f^IZ|BD6^?1Ho$Jg*?Gw(I|cFY|HxAe6&CQqZH9SW8W7(w!BJX>6^%|@ z#?n!5_D25g9|3)KOAfz?u^sj;1R0=~B z5B^51^3(DsN|G*n<2!XiZ=7l8VAgp=HZjn~Y0qP1Q5jn(_qUpB?DwIczXuxBur$Tbc)N#an^)G-_v5Kzo{?CATBDFGb$< zIMS>Jn&~8cNC3@r^aD@4KJv-vsP^l-yA2v47tLBgFCBS(nM=~<3du5;j>e=;pfe7w zS?P$SiXMFa+UD%fn9iX%=qRbj}4=$Dv$=#n!DX_1nRy10B>8Uc@c zU(1x{OrUFW^oyY9`+Ct?evs!Ls$9_u8D_WY;AzNy7BsA z#mNKR?ptvsN0F9l3()K2Wr?=1>a05mc zVTc+;C8tC9m|(*%PHD7;dHweeRaYBfOHvpFCnE|f1)Cl}odVyf)dg1#5+qY=5`!5= zoBMA4ZL4$N{f%-<>&ku5*C`h^(FM6%wem>uZupwJ&2JOmlC#sr%T-rfFClKw{um0o z3FZftTUz!X)%?dW9Id`D#kHx*y9sOYwRmKb-C9*5tp-8jM&JF$j#?=E)m zTUUOn2kX%oY~$XeXAfWBbB8nKtZubCN!l`I~@ z;n#d9NmItDD9(otv&zTRh!2W)Y}661?g~VhjFQ@)Z(VG0*KZvdrnI%ZelZ7aH5fIeuTm#@90Wp9vXc}A5qA8nflo2r{D-^Lm!wA~zczXA zYkFF=(P+n`rL$ih_etEo=ezFc_`cHX*Z+_GpeT#n@YH)^;*qd?na2;Z*qePnMMu}) zHTita?LeE6B(zm{l5H8R7_k(|*$G_d-|IyKq%TzY{7Ta_~>j9y}>&Dqn z6qCQ6`jp-sEO39D_;N-^;xEOJlt(rtv4uyE8Yr(n^|tcBM3VbN_VY``XMc(J4Q%`G ziQ|LndrIA8oE+~4U)k`mY53mge@~=%G?zIJoK#in@=^TDgn2^fzbBpyxY(dR&|tME zIaPAqzJk&{|2?t3+~%l9---5?rj@rMf4!`3`}W@x+lS)4{@dbt_f7vj(Q7g3`F~q{ z*Yn@6_V2Iue?o_R0ag*~ho8|t_nwe`e%r*J;1}-_8_iFh`sLt%sd)Xpp>L>Mo1y|o zzzQX^RY!1g*O8g=`O{CP3!Mhda~>x5eoMSrvL+^TQ=8;XfMz+AHM5-8XL^cjGOgDY zdNk4T-5+wwix01bZm#tGq!B~)mV`X@T=^#PA+5zPH@;nR8@-_R+i&Lt=(po_c#?s} zZM&&*XSWrJlj^duwc=5hb!SV`S|A9Xz#qHb#Avj9QWm_=*q2xa-a{+@k!rr%S}lfy zg8~V11>7hN1n4<^WVzPvfny{XS zeBE_KQl@MNxGbZ7I07)|2VAv{=D$Z#A^iTZp>?}8OVn65=T$&*wSub%Nh~eb@C|8T zuCqt(mPB!+-z)wanQP76LYXwOmI9K(2>X{m#H!Lbb-QRJxPV`uy3Q4{>rqS}8C|NB_}?GFFH8U~-eE5#m1mp)S$(q`0t zl6eowQXE+JC`#O&hWjL}!DUrmzTr}OC5RDygYcbc9lA^dS;AyF=!Bptgr`u8e4 z8=h*>;{<X3wrFkw~ z4y%rA-)Z?juT(Y-?x(1;Cvc#Bh6FBvSKJ2}sGpFNvUCwImx2L0ka=hzxek#PLH zoTToNyCz_cY*%mo|6=bwprUHFbx{Qc6p$ntBqxz18HJW4C=!(%TC#wEBuQcmC^<`z z*kq6>NiwZS20^mqoFz7~>F`#A|Ni&c=ZrVTz2m<7?mpMS7;ETSRkLbUud13g=l9Ji zp~bgLM*ak9g+1A0SM$7*D|Lb$A@eVkG$#S+z@Bq6{qGDk#dd!DMCF-MlbYA7j|r|6 zs8{^MFImUA+RV)RumqHYbB9W)fI~*kZ+-Ch>HPaa_5Yw)LT41M!&@3EsSU4JxGym1J4>tAZiKqdDX%Xq$OLb3arsqS6=`zK`6J0dU!+mlI zzm2-b6*kA$^fR5sYw&|4KF2vM?Y2C@71!qfeHE(cSq|yg`h3#WW_#m&TxUtdzSAhE zj8kXLI#HoseEkXL0>5yN;Qri$_W9a_7`^)TYcvqo09x#{WXJxTJGNc&fR8BF2%>k* z&!pg@q7qhTizgiU{O+sigES1*2qxYK`g|Qwv_dU{O*3L$XR983>yKUml&|Fz@lwzT z6}}RKIV8i0?%>w%lkym)rwG;Y`|-f-*V#G7?4IU0|yY-UE|6 zTJEi7SC*phZ)qMqH@m>U;#JD{v3~yN+dXBrqkL~Mp$iEvjiV7m#!k=WJhP*{hoqBf z-gMVa+bOM=NQh1xe@5%ixAkWx{!c6r?{lUJd?6f+ zbqaQH+rbdULfh}%n1+Ot0etc8k`x0?VoSAn0TiQjNgV7IZV zoJl?$X6pk`r{Cd@sZ@6@$$^~%D48X|K&DE?@jJ=W*{;G?3Y)jdN_h%D--5cAFAF3R z0G*AOTNmPI>fj0`_e3R*LeDOr^^ESpFiA~xZ2aQIOdK0>918E!5`4xGb{jIx3hwLE zl*7SSW~npf`nsE*kHJP|dt2^usVqIUEgL00$V#}N`ZoUuyj*~O+#1uUb}z_;XR1C^ zO6Vd|?#Zg>SOVY1wp+*UX!{jX)|*3Fyaf~#U--`DJ0m?AoskDlIB$cl9;}9}w_JKb zsF|^12?jjwCV>nPpOgzMnR3!~SYeaDg|$ORS=zx&T=#>ugOq`-AxlvyIcD z?(c>^Sas~`hWd6Lkg#qr-TZ=M`b#gR7hkZ7M*cibBlOH8Slx@KMvU_)hDzzRDE^ok zQ7tUjNeTe$A7HIJ$@>@4Gvfz=;Bc1rCNuLp1KO+s)~~rLk5B69lbIC``xNtZi*=ve z%yDit-gqXWZ5i{f12|<(WR{xavt7~@oh@;@L|k_B{VjzE81|?sXiOs{Ps&5EYM{ib zs~7ixiuGJsU8tPfPPNE=?u8g0x9Hpe^L8S+K_6{@N2TLq_`nkM{%cT)n+T%dcBkAK zC>-vXB9>x!`>~j`6ot~`Uf5mC%0cA!tEdHb>xA9kEQ+>4JZt4NNI;JK&0)L2=nhIi zRm9Hbs*h1CV0}7^MnD4$-9HEf_)3W5Rco^TE0)Zn4pz^$zC1d8u5CM$J?xpj%WQs) zNq|DRNYI$A3w@sTqO}l*pJb3VW~1-L#dliY-zCy|aQyaAW9^;1p_yNt$QWG=tWD2k zd7@H55MV`{tCll;{WizOMeBQW&;B>^GxK37WDmi0>$VZ&@+prPb)5bOT1oz=fBlev z@l%h?oPoMuD9@Y9Dq#6qPb>(s^m}a_roJq@zS_%A`I5IpF7D6sU>VJk`#dM_`xPcb0_>3= z%!Id8Ih&lyy0%>t*a!kn_VX<<96anpI)ec~86o;T3T4mxm9e0NEEerW1=`BdqN+ zdcJY%MH-UmBAhCIEe1Ki6o^i413Jvkfr)WplJ^ALX#82DN*g`4Bztm0W2=-m0VdE; zow5_bm2$LBZVJY!_n^OjS(ku!{i=5Ie`;Cq0FfP1DW;RN#|nglnCZ2^7!dO1El|3> zE13S>dAX$%@!nb)spWp^RMi<<4NtNwSI)9cpIDox_XP#5(B}81K&o(fIo2A2-d-y5 zwq8a|gp+z7ZC0#k&R)^5ZNtBGt!(E@&`xhZqY~)XcL2LaJ=;~V2Q%RV1G&@L`!s;aapZLG3!mL9p7y9pmrv&K-@Az-I1OodPk?C2PN z@r|axrdDPo>=z{Osy$e_MEgmh;rd1~VIfUP5k}k`bzp0aI@Rmh4HSxA*q*^4@T+=v zt6!rMR%TM~13OxGet!kEV5Y9)dEkNrr4mdndIhnu@fC43`kW`#UwbhusA7#_ID@A5 z%trECjs5rqaW!$2$rDA^j@NdDwKvxVh?^h*M<$<}QbtGp4=CqZU!cqCnY+BJi{sMq z_yYIl3+;PPw^jpDmYe=cVj5e)66s<0yss?547TX#_^n}W+hz4EU8>}vQ$L>$juf|A z8JczzlkIqA{~#)2oI`&+UIREX^WccwJ(Gy#p210e)3}|{bFcbhNYh{Zrg&p_Tl~MCp-wo9LGR&WXbD%1Yd(R5uxPN$}^N?UZu*z?0T6Yu8= z_CVn9)}?mPm#tWCqp7aBE;i0XI&SrtPdYx$iSa1#vvo`}#>*JfGu|}4VFq3BJVkcn zhxg5x9V1l>BFV>QR+#FJxUwt&10%c=4d|6v&YUFdhDL8iEgI384V=sXHY!XE@6a1K zgfJNZ2e1m;#RF>~70`k8apF{be;gD8N8ACThMrwkB9SM&5Ofa|c5sAw$(Rbm05n!O z5M~OAQh^{o&uQgqppl6n$Z{X_1fF+`m^vN`i$s#>ek@%_PD4o1Xh-u29Vt)uC6Tc- zf;o^{NWSzt&a_A9Sy`o^&=~^LwI(lrzeE+wrOWRY;u1{7g@A#nmARbR5O2zh-V+I? z>`ZBeyg`9W-`aK~ddo3{#whSH81m`03=+93JEpV(g>@d*Qr3CA;;sI6yaML_q*|nQ z+W+&os&8h|>p4T|%V*Os>mMD0H&#S%!utk`Ky9JJ-|m}Z6&$ok7S?FbXXoc|pgV|F z6ibP(!kWHVwl=-gH+VfaJ1ShVg0&CMJ#aq=iy4J^qQDSz6-SHOC(F2w!_yF(j5$NQ!6o~?39kb{?sKCaw+I3)PQg6bKFb4sFNR)i7^WI4`4AMCR zTigae=bu$@VnLw>$p98BN+sdQE(BX@efg5q4j4@42GL@15=;-4y;QwJ;MwlU@|>H zZ9=)V^T3e^So%AmumM^2F<7Bk9o-T8#&q40eek*XtNL28ggp?0$qH@{g8?7R&XqBig0-D1i>2c-s`1%whR7@PQn7k57^ zePn_eHSn;vEpD#uNUSS;R{{9+vbh=mDLf9rH~n1xQa4@Q(fR&|O9!yg+|g^pPPtol z59||Gn0Our{yu+wau{lD=2Yt5*wb>K8QUo3!`UqKLnKcL4`m9_PMlE}tYQc?@7U*6 zbqX?>TgbhS3hP}{_ffOJEXnUMEge3F)n>}89u2+*2o48*h!tRE3(QHsbz4H5x&g{p z!~;P5)ts@1rR9@$&WCB3+Uv2FY=D(zck*d-65ao)oPz(7`Y=QO2 zbAIEoMY90r`yb%_tekLKMk&`Co>8V$8*YH|Xh6wyJ72Z)D!(Ci)ZU)a1x}vXnBNb) z#^}&>pkz&VHEttPr!|ns_A!>SfZaw-X@)d4U&AA9J}z5ZBxcjau|G?N=S?VjR3RXHXrAb56nk7v19j1=s|E z5Gmd#&RhZECr%SykSs@D5&-ZocDP_Wg`YLi_1b?c0G0lu2>|M&8?Q;l%4Z}!H$A^6 zv#~wgwL5x0JTjt=1UHAI;BRID)|_?%#+PSgGfl7D)BBlTZwlhZvJlSAX~SPN+LdXz zi|X?EaMV6b@hzl_JwyO>^Gg5*cA zBEbA|vgOEQC=eS(y!;Qa(;3L=?DGAuVx7KtH?$*67S|b?$9iOkFIF!2 z+yP8eC!cd2dtp+gSjBEMK4F*=SWk-u3x_)o-0f`mR2=n9%8KI!uy}hcY9GMY|Bc#r zK~){NHQwf2M1)rK-H+ZwJ|;YiR`5BfsD#ZEHFLGX0AL^hJVBr7SYaT?B7lUrTEq|N z;L)Q@VuI%mOPV49GBJsQPX)^dfyJd8aR6k(1Two=FRHwUypsk2B572)7RzY0nSNcn zTvYL*b=%(fO<2bQ-hU^!{=YHP;7`~8+mJ^7FaIfrhS3THHDqJ9e?abks0n{q7g*-W z|6ha>d?3zBto4O;yeqDr7eY;61zxtWUfR7yN_y~t5kTSVi|^20SL8K3gdS9vMJ+@= zzWAQM_l8A~jCY&#@YN5JoESQA!Xn_MqQ?Oh6_>Gso{Abktt4J`P5Bj7H^kZ(N6 zurLN|F%(mGMr{seKDsh7zwS%aFTH>T;kV$Gw49NFt<70hnDXRIFvneQ;#jSs-HNvX z41W=QO#x-`zk=|C{uN;VA2IxRMc0Kwi|l;Vu`GkAQIJmP=jD-tMS$R0`u#n?Qm*8F z-2C}pasHAR{;P1uzNSVX-s+84$LRjj%~1e}Z{F=3*_tLT6Gb$KU>O=#f_r&OkDnpw zKRE!=+8`02`vt1DKtjehaeO5U%Ll-k*8ohzCrRfy49ePvRpCS1BLW?2 zJdU|aPe)uB5~rC>S}-bzx#JN*rYDC#1&VdxDnLy0>v_wZq|27QSy?QJ(k~y#l=r9+!$aUnZ$lzIg`O zPk*RjodBF`Sf`RPR7%DWk-}5*&yt=)Re+B4fvB6{>c9$zK_UVJHXLsG?*#d)zy5;X zfO4g^f5%p=2*B@$@RCebOH!^5X1HH(?KNgDJqWd@>Po;0lxZw}ux-2VuqNawrmKQRN65B`Yx=dsE0XdsiTF=-4r9Ahdz zdJ8hEhOH;p4cmqa;J*#fyTh`PxOHa80yPF_tH(oX^rZO5zyZfjFDQ}a?IkJG|9ut40nc}M^oooI*Nc@d8L1uoWGkXfj?GZb z9f{D_HBWz)z89#uqjcTS3e)t|3T1b>dA0*c*3maovnNU}cD-vM1wn-eFko)s%L)v? z$z;Qt%DOMxO*GGbV(-IXT~7dT)bJ{RCsHhL`K0ksYG*uqZnfi_8k9WBWEbjReBBcj zHwr$x0AT-v1d~Uth54@~#dgLm?1QTU&Mao0s4_9hGY#vx)!z!(F1vm&5_qw3a+lpk2 zDNe&h@Zibt;MAR};bHhzPw!`|)tjj4B+?5i_Lf6_cMV@mwM-V%);)w(b6)zQWk_4a z+(%_3F63?(P%;1{sl51UNasFZN5$n))t;%OjKY0yJGl$Ds^T;W_nv=sqj0JIzfc@| zEg8;COi6%(-8>@KFIBxE6TWGp;IMtzF{8jO|57uo)ZIo2IVC;JpK!gd5w3{V6lA|4 zgvmrJpu!K@OG}OD^ZB3Hl^^j&9EgvA(eZjIkd~7`pShVLYzkLgw||l?}d#Mw47L{K-#dE_8F$#BPAp%8dT&2Ij;wUanq1T9-s1}(IGI{ zI!x5Vp=Ac__Gla?!>w>VR|2zm8*xnrLz7XQOlJ|@+UniF64;X*w%%;>8n+glXIPKt z$~{fGpwfki(mQ5Fi>30(;IU%Zuk+uC7bjlTXkb|e_ka-Zhx6X%s1HH&K_?4D-6Xi0 z5DuV(m?Pbf3=jFCnS7Wg#2l586b%yR8)h4s(F6V$XJe|8>nnkY(x~x>ZPv`X)=EE* zWa|a};{sc^^r!wQfeC?^N?=E&%Ig*@lIIkJIbCw_MtBXTVo!lC|#nJj~K zcmWka{AQB~M|(xuF&gr}_;q%4xbtgo_N%ixlB+iUtV$JO{^s!D~9yO zB{4KQ0zq-0Yvr#>jQfFI|MTHlFUSt?=VYH{0W&lhcpAw1H0SGu5QYEnT0kdhf{Z-b zSkc;-Zr$r(i~*+KmFO0H*{*UbAwaYOUoRvR-G*SR_?jDV@lnhzL+{dS=J8d>GeEpP z8zS*F6pNU^R6UXZpfq{bD#AEuY>r5%i87VEid>VLXPe6C)#WPoUDwH8(%s18mCS7y zd|I3}pD(Stq_3jp*J@H(_5^@GlEGGXD}roE2JR-m6vK26DF^GI6Kc4?GWd@DFBdNH z$9T?NV+MibE3oS^TUkh>C+F`p$ODiCq8M>#LrT-*xzZvgXwA^A$k3BfHTq;jhg_n? z;a*dp?PYXqtX8MpjqrCbD3U3(FIvy7*s_HrA79sm--L@3Qr zZaH6vLnSaCN>E4*v~9I7vOGirCYzut^MnsJy-Fyv{cRy89;!| z05fC|WD(p0Llk}KlFtiLK-s9JlNLBUt)qI88it@h5MOu1E+Zw}Qa`Esb;NB)`_F{6 zp131XWDtlp^r|*I>!vC$mp1Su)`1v!4+O;u$O-+JlD6>L)F}@hRa{Ayof8V@{@Jg| zwXQzI^rXe$vts3N_>`L~-+lf!%DYFpNE9Um(mDgq;g%SpivGJH#j{#@Lr}zhf<)%6 zq|rC^7SHe3>gWBS{cuT}efy`vT;I!@)(o|zbfKn3X)?@oeeA2IStApdkDc84te(`^ z-vek9eDl&13(XtZg3p|SfT0B6;)!LBWs#oI+C9N3U)FlBsiC;Xj~!t%RPaIIRoNm? z8QPX^r#zjWk8Jm-^ieni$yMbdSVu%jEc~hp<4vC4FIHIbD@;ykGVDe69dj?J=L0uO%l2l}rP4jgDDr!1#u zk>K}JXK&<)Nq(1AV!Da@8gg?K^g zBU@);`+ktYb$^Z-XrOWEPXm93=-=ooQY?SX`qm9UfOh;2TZnvq1dw}k>WStp|N6lQ zX5)K?vMOB88)$Q!XEn6vg#6R^~$rn!bD*Ly?d(-jE z+=1Mhtmx~r9T=&?hc8_#O0BFgf8EBgV$9H**J5ck7q*D@dp|YVhk0a0NiD~n@!EDTY`c7|*mm_CTL3i zu;WOx@Vs0BGQG~5+?qNb3@0^Ly1(jq-2*30$4c4)p z%)WKUEJdP>%u+{?iH6fKZ_H~0K zFtq!!I^YHk{d%%Zb0t*x`HoU;kRFk4d#{|4hJ3PQpD6Nc7_iTu?F_~EC`#5|%sjHR zNHT?|1E92V8n4mb@Tc8S$F9gNh^&Kjm|P2jVnbcuMdEQ3SCpP=-C4WXwR`%~2FcXr zuVW7k)wIZDOdF?mv%hc5==WVJn86L+<@xZ$f#V((N4e#5PTW$^agO+!*nBBr1KvRU zSo_b3#5JGsy@OxHqP{_p7O46sSGcE@z8t@!b?%W(_h?1+$R$?b=U~MMdL!>v=xZ$} zClaO4ZN!Wu-RpsUfCym(efD}tO)J=!nMS+`gD+m%a(iH>%6vW?A7nhOf$`xGYlu-_#Ev$x~g*HPhCbBeJU6E`|t(^}1jA^PIxpb}*1lBIBBz}*%J=0@x zff$_d_x-i^)&T^`9732+(}v1K%r8n+4D4_;0i`D$O>}G%mNxjE)9Lsy7{M>4QZ}IX z$hDmW#S(l`)Q-{p9-TXl#ZEB&f)bJqgM98RjHhAI1H=Ai=BQmlzN>Gmhikqu%NN0x zT7>>_EbwPbuNu&PbT8ToO}PR-yP%O*FE>xvPMSusV2?+HaPD5v0utEps;q2_T`4Iv zEK(q?C%P#R)2SWdT$zP@(MK#5F)Ub-xSrR4Z=6j@bs<-{Zv*jsuC6e>WK&q#+>7hg z`GzBfoM(MvDYxs|Blsee(@5y`$4U;r0IA*EB)Bb}wmX2!%HFXqytDhIOeTD`9`4lxxNH^X4FJr>dN(4pY~B2I&Hd;;`TY!^Iiizz5H$TotEcyw^!jAnmN%w zy%?sipG`kt;u;CQGX7EU`0!jL_kR-ka7lA$S2W;$-2JnjoX_=4^oy@MZnA}HWA0}n zGtNb>q-sKb1(POe$z1+9?-m(nTw8I)K2{aT)ynY#Z`yt!V$Lnn{8jKhb!Fh7cYQ($ z?Y5m3bRs_MF!)l=b7}$mMRMav^IXiTd&UIxFA~l8J``_-cu8@4YT6!KVp2PjXHVVV z>=Zly%+PV;-?)MK2Ap!&C0PvW)4hNamF?FzO7U6`%YefGpeY;MnE}UsabT5HYeA@x zJyYjy*mAmN9C^hjKlHyS6EwolZE|$HS&atrB%@2Hjg?RCxg5kUj56<}i4P5%74vmD zd)p}2PcLSXeH5H4DW!o0mtWF<>6~#lbuT2J|I5YP?v zB3M(w-mi|j*eAt>TK7Y^AkQ;oQq^x1Djp6*z0`ylX%)P&Z8rSwf^{2 zK!EmjZdh00i%v!l;ly{@*Ea#hUzSJk{A{l{6=f#-o^6EbBWd}52cXXy-S)`^7R}m> zj9m%*(96l5)Eff$nH8<)rv{)C*Mkpquf99)hl)jZQ5zzwELv|Vi2J4Y6$U`I6IM2p z0fd_X31^OFPtw4XRLfW8u)-y)UQkVX5;BfzTKFsruiPSiwei|W^kXbPY{5#N0fe8C zjT6W>4T)%mRcT9V^Gq!>x?|57`5+NZU>ta6%gGL^4e#RX6(kw(OyMzBUzXnMlly8K zirnDryPy*HIBvlHhm+wCHq5Q-44*q-4tqqOo?zwtA72#s5X0$I#N~z-I#oKi)4aRO z$Gj7>5f`kt-aTM*&2Wrmr1hHf77Wo|+sSZ`-@l4al(BqKZBt{s?O0|Y$f;#UNpbLU znQ6EXU@s8D6o^C>&8AwZ^wL75+BCF=m_UQ1`S~E3n@P8Wi0#5Wfz#GO-b38ZtJ5~0 z7gKgWniFv-qIQLeeM1lnS(!ZkKR>m7sK(Bu|I-BxBsZdeP_VQObi2D}YV=l5q%YWc z`tKJ=^EQl0tjGB%KB3#j|3Ek=sxh2KIc@eT++Tg^rpB16*_&EY6I|_0HZ)yv2P{Q2 ziLtztJcoVwf(uInUcq=pvtbK(ffNpok#){~7|U>j9JlA)4qd)&-_>(_4Cnz~XY@@? zXAfl}LF#6^bZmp?#vOKAcBKM^&N&vLFGd8Vz6FOxJLi_7_ZCqMAIUia16%%XFXMyb(4TB}=t*OH)pCtpzOkpb;Kub6|^1&*> z*sW#4m<7+EtDJm8{b&nJ{h6HGy65-O6Aq93Z88MxhFi4F_f#Z{gRmAvTPS*MAeTJ^ zkhKDJLeu`o%b2u0%`=`n%HIzjELA{wDRMR<;oB0J*U3=G5nxiKfjHBUVlSBfG8$Xb0VD_j}@h1krn%Rt%il( zT_<%^_J!T!k*7eAz-+16fajC?ZYKC&i&gdg$;d6<1J%l%tcN`rFI9_K65m&jQZ2xB z=x9sTUUB;)=+7Aa`Hucfk^jZZ$gp7=!9}s`s&$+kBF>l6#W|}17ntk6B`Naw2OF!~ z@zk+gP^K>?jJ^Hg=RswBCOyuZU)SuY{;8~eCBH`3Q?t=QgAfOT3*~o;^#7@BWq;kh zzXf${eX`R0yX?UIjX#b48Q#A>x<4P%+4TCKoHA0R(qw+ni>u-_PnYpOk+wPNeJR#C z@}QDn_JLkb)_r61?rC58Qzl2D*DX+Imc71Q98P0t?{wMqUp7a}luwhgzP80wV~^R~ z)Mn_hCqXB9aTnt9U>2 z8$B<7Sbp}YY>^M^weEWN0U|~@k5uBty{T9{taA{DeXc{GGyJpN5NlD0CDepGzo~%g z@6ymEc^1|6PhB`O3Q%XFe?AF9Wc^DQBrq9zi%Gni!GPr^Vfn$(%xyl8hd*@wRm2C# z_S+M2TZ>y$1VUFGo0<-MPG92{MY*XowVMrbtFp^UK=S7c#wKT`k4F05P!3e5o1WWZ zR71!RfH$cWstL(Ans2zdE}$BzhmjySm>+wFtMhZx;SFF|z`EFTB*`}%u{eT+VnM94 z2OLWjL*l&t1A?AamqpNil0#5Eaa;H&r#r6mUSN&*hHELCbG~RoQ2nz9MYsw1B6W^@n!LxOa#N%vxCvua(DqnU< zto5GiR{xilnyCAizY>Y&Pv+9(cS_TJprIbfXa10Z7dLSoSF~0MmtsMVj`EW5P`Y!n zSvu#@v!`Z8%2|F-1L&SOJSG}iyg~dZjL_!EpHBQ4i9g@OzuoL$c0i0=Qkke!ohmPP zyI+=zdv8sJbn}+-WYhy47tqzK8;z2GyF#KrGEZ-&@mczbJUrE*AOtqLnoJX zRm+{YlcXP!D%4~53%n_a(Qs0Vb{yZiD`X+Rx>&`U#PD)I|2ec^^R8y2f!*z#@>Z-@ zrwD|4pEp`i5oql9jQZT^v#&;#%H~OOzX)^}?93R9wchGMH0jX9i7UiHfSB_&cM~cl zW!RNss$&^?4wXP~sh3vuaL87M9;|!^47e05U8lO!A}Q`!M1Bi2hl}_PU;Ux{3x*ka zGHV`q#LBp(8JwZt??@R(4zB%-u>Nr`Or30}Kj?TPiCbvb*NHagMT%Pc%e($~Z&#|Y z9-_Vn>|C$RYQjR03j|@p68r{0oi{rTR9N^2*3PL#@yhfCrQ)1KYQ!cWUjdataQqAa zot?QAN{23iX^a%LCDiiF@1)7%Hp316GNmi4?!5b|9h(ng@O8p#SM1&;q9aWk#cr$E zs=Bs*0z@U5+zfexWsH64zWJc*7n#D(y-0wSIBAy9zcBx5`3% z6dtcWTa|V1^<4vhxRZJ9iHRxU&4S&=PIERIjqMuA`@NSNK3%394w_ypBO}UppJZTb zKfZpozA*JuOEH(n^rBNRdz4rE_lwoZ#RDaIW#XPjUN~An#o4xF`$~oFD`~(T)+^c5 zPA*@cPs;8azP<)QT~d+T5w*KYiYZ+1)P! z?gDP36(*ln-GJpc#i1pEf|^ovVkAw95XRxKw= zSQQYsjInmwDY~Rt7Wg)#yDEM^#@xXGq}fV=d{;w_m7Jl{KbYS?0Ovnw?mtNQKd}Gp z;s-JGEIWK_w#t>9C5|_Lp0w~v&1@+y9y&xKRo~vWpl&_(N_g2aGxd1W`9a3S9RU7u zS$>}E4B`oBg-AqKmG8P-6{k0B9(xd9atv<8uE0Ot>n0`R<*MDA07Uy!<-2EK{&{4f z%;;<_0K;^91pGVv-fu8}+iz@Z%M8=WH@YM7vwFv;p?)m8K`_|-cIokHA==P?IO%Z_d1@4xs8yJqO z-EoAefcC^?P)qt8$pB8I`fNcL1Sh%jE>ww!L3BOG=RWseu>b&?z&{W?XAu8F6EP3p zaI9M{1TK(7{j$pfK&@ga1NJ9xrUA;pKZbydGE{sOUfQc}KD5Lcxe%_Ee-70zZus1c z>-Qx0KLYj96AO`yo}#HfhuZ_5)JCy7CZ0L_!I7n@oHUSEUK~qqII>-Y#V^kw{6D^& z@ugl|RBNa&oLv z1yp5rTbzf0Ds^ZET3=)nDQ}1iqd04j|e>w=- zdUbc|bZ2m_(;6Ie{7Ceq#pcjmHJU2L1yT76M>waGGw~kl3ajC?rDJT#Z)(DPsnZVp z5?TFT(#Bv8q*g1l@_-6DBC4>;5fH>Q9xI+XQHpqIXqE0Wb3DRTcUvEE&wGLH!r1vh z{y=ZuMk`WdIE+uL>DRh1XAK-0I;L=@d1N}rZogTGMDjX{uT=MKe1Ke!KnAx=xS^HM zaPJ<^NY#zTXPN+_%^W@WgoeY?Z$%;TrX|2==$icaAAc&Ww;h~ECZsGF@|(Evn;#*6 zN&{=TLZHRAbaYP7a6hMK1i}6nlQ0_M_S7MCxQ=PwkR^?s9#X9y%M19)mUi32rVI~8 zja=;MgqQbRQ8SLpy2ftA9DVtfi}Rs5iqwW8e6Y#eHfuQvnXSjd zvgy#nkWoo$au@2fEV+gx6o`}9u5VYfiBGh?g_~}t2XrKm9(?m+-4}_dznB~B-KkBA z>yZrx3GqUO1^$8PeO}-yex(0O7oK1 zbotW1|2Zt1GT!jE&&w?J_3qd7i!+$pXc(=FH)3JfJ-duS$y0%0=30w(b_2$BJNV~_ zk?mIH;Z?Yp9lze+~i5(OO)dR|g3)H=hc=2T1-Q7Um zDv_*zHQ2NT^F0dE4)w6Dn_u5xSBjLfC>3eF{+>lX^w(lZLu)uwHoyME}*ao9fd%>4Gjl5bK$0jdymtRhHSt5xJ2 z#vJzMXY{WICM*Rd2-IvY#38>3Rrn@n4t%A*X(m`|3VsFvKllK_0^Bq%6^YQ?i|+V; zC7}R#LzN(Q83L{Nsvv;B!fd;p4af3A+qC12lwuJ9YWPaTBXB&514XSLC*FISjns=RO2jgk~5Rd3%U!Z5XCHn(4c7+?O3 z79l@M7*M<806m;s==Li+RgVBiWHN^lp6JkGeDk2nT*!lF*CUF^0hJYNlGWM^(>Kt2 zmqAp@M@YU)OFfd`iEQ3;=%@;-OY&W-jd6@yCeGRQgLILs!;ywe0);je) ze>y#j1p0KVENhBD^FH4yNT>-s>Vp9|g$>X$EG^}ppD6LyH_sUSBdg^_`6 z3G^&#QmR{PW47;!2eee0`Wh=S$YYvc5I3abyIp8DkS%Q*!_DK$drMwi?iJ?@fvmud zZBq7#_U?J!j#JvuyoHwm7!CBC8&bR-GF!GXaAgH8J$3TqvD974YmyDGY9!i!RF-g=Ze=@*=in(CLo+xrqjE zgbI5*6HOEmb4K|AAXqDmMvzH$^BTnba-g2!RKBs&sM(^(%U?e$mvkm_LFiqi$n9xm zI!BAUQvLH(m1D!fuZI0(T#X&4)N@NAn?Id~s<)mQhrR@F28+l+LzcjM1xA^bsg-qA z8tvamKru4t;DZ5U_o-B?B+FdaHXGO@mtLX3GO1bO8#70sogA@j@x9~Zl8rt@BZbG8 zUAQXg%nkVIeha)Wn|(CTS&J09!VURIy_R`JerAWGo!j}v4b?lHi)(P+SM1+!FNx56 z1Ye_>>98j?^kH^l_-JcS(4g23O651}q+nSkJ)APPt|K$UlSAgl+CR;|y2R&=M3Y{3 zkNj-6_8H;WggI0o@S-(zcqlG+OIBR2K@na`-|0|UAMa2oKC#;!PKqB9e`NX2GT|X~ zYKP*WlFmZ|7@)mn5W1K5IZ5VlvFxZ5#=I}r5rrsS3$`{HqPhJ}yom9Z%@~amo`N6Nl539or5@P0YPXi)EsIQj@U}Mu{%s)RFo1Vh(3e zgf`2GGujk-cI|dQccj%qbKthz
    f@6r0r_~RNt?qj{wnam*ea<^ysS&}tN)^EDvamrFk#`H=a837}Hr}o8naNiu^1ff99J;WE=!o5V_NoFTF z$gyfr*vn~c-L6Dg`1?<|Y3=q*K=Yel*~GRtz^bq2Qb@yz#V0J;aABOh?4=9G;GE>U zXt&eNwJCTnuX@=%$iNuH^p$k{a!`7cVjBoCFFatZE@QU4as*LGGw#KY5`XQYOzFG8 z7Vh|V7R4~w!0Y2_dDkGVCb85}N*vYKfI(>ey1W+p?q-a;{=QsF?$B!I*w7aNL&HhqOyyFJ@qt@T9I>G&8NWu3$nzrx%Vc&qA^A$M)xFc0*tT-RVVZb^!QXo zKKzYJJ{y`KP?5S$;HoCb}Kb z&J@nVHXQ&30c5@nND;>1cmW9;l4>N&q=-I@WLJ7YdaySWce>@Sf#}?A@2>yS`toEc zK|L>RFVyx^IH=yUZgn0s_Ml5Qf-zO5@oQc-@n%@Jx@iq^k9R=&XgZlQ)pek9kvuf- z9kmH}I0$_#2e0QXt&@`8|KdNy6)6=nqPO6`7MB2iKn+H&xWbF8v$b_iIKC^-JVI`W zjv7?xTcy6c!3I+pIY@^>=1yGEOaeoznz{?&;;*qv&_nl0C+oVo0NBd(V}oZImj~-- zq)QJj@2qA;<_Vd%WuI=rK;cTde*qW7nd_+xWZ%)0g>p0E|{HHY@)sR-2Gn)2C} zUVFDcD^=&({@6 z?^w$>^>Tu7E#l7hgGiZOkEGX0HiJbKeJL_E10go+AJ{{`iF8t$ z$6luht&hKRufDY!rh2~I=5Wl4pHGOtGnBtEY;QG9WK-mEP9)^{ch_wcNiJ;a#pAj; zCh@#oE*b&8ho0rDr&JHOlN_WvDbc}+$&R(sQyzmLo`i&aOmV1LzIJv$WhO22NU34dTA5)_>abr=_Ee_oMo8E=x( z_QHO0H=#lR#42?;+7*A!vQr3_WQLxVkJRXa#TgOP&wg7QTS-%|&?@2k z+#zREYe}W$j>Z*4G*O+Om4$<{Gju4|OKdHCBaG@yjsWCyyg zHT}VxynIUAsG&_kMwC#<+B-|uX4`)?PiVEZ z_|q+v2;LMyhEfrW)X9+WV5mSt%5s`@MCE!&_n6@ve(lQi>5>iKq{DZT5(W4z%;Fm^ zve)}%?KTc3X7e{zMQqZJO-$DN#z$D_>WWR_U>AYwVcvBJKxr7 zt$9YDrAS)kd46ubovO5)CES1+)JTy*mx&I*wrcJed!uFs4LERWdnOS>Cbx4K&s zD`+wH^!m2cK>i1{#g@&lpV6)-!=n#n zoTa@FPgVvhAFHM=Cp&KKL%R7=b2CIUr)omMnkFE1&+u9&I3FhSU?I1~ZtT%^k__M8 z^ko}H{V&sb)@!Kx-DSf;Rq?4b2iQih2=4Hjd*2;*#B2fYK$5U;i*kEEwFgD2y3xxq zFoy@d{ikcGn6QL4qx*IQ-y7?IkU`Nz#J# zH0Wcl@k`02F?o@h)nn^q&t;KzhFI%v%{0|$J0S`TL@Z3j`Bq~PZ~ozooaj9>HMiK6 z)mPhTcZzG~wa6i~SM8Nek5xiW2>F+rZb%;?Lv7k`PBJOM8W|kxJQJU3nuD-In*NdAa#fZnWzF5A1<}))Z4D+P-|Z&QY15t?8k-0r*t> zqkQCDG@QU9EVnmjeC z=nqBv-;89=uGC-6tZy$Sm{Qx$Zc=t9PZswuV?b=e0s8u=-ldY(=fcaKi>Eoo)#J^? za!hY9aOl3TjE}!0#MT%z|k4>uE=&0j;3YSr1_Y9Je`2UBp_l#%zeZ#-2imIYY zX{}UiRn1Z{lcGkAhH7h5yK0x(#4M%6-o)0H8nyQxwMlCeo79XLNo3ra@0UJb*B&1YtTF!UQ$=l1o)Z#8seiJbf!+6-_H^) z;!yNa;k|EQX1nRRp%*zB(fV;!E2^FnakH4&{cHzR7C9|;H7ru ztL&5OM*q%t#W@FlfJl1|%g}>#u?f!hY5OS~W>kdzSE{)DvW};&u{u= z_FSqL3$pj94NeFJnFb|Crn+NqUo#i5STuu!dCxgyA>ds`6d^`5!TfyATD=*o!)8*< zWL$C*2{un2!!O||VbC}KE|>u(k9A}w!*PFcO2Jyts@WLHu&eEJ8(3y&#z9dG?XS%e zKZ@5d=v*|NAQ&c#}rG_3c(|)?%%f@zsdhm(l+(b((?@c^JNGy^j z9(H7K`y7QxJvG}{%EV*wKxnpk&}qu@Ix;jU)5?M5aAV#tZsK%)eP5#Oc@usKK*|mlfwU~Bb4tCfg#(M%A!2H`CDGNgDJL9*I{ySE)C2%8%=-{gANAB#G zY`O$dTDJhsRH!&=~@87Y;R_dQy!k{Bq%h)}G5ApZ}Uy+EjIbk9Rrq3rRk(S+|)asVU6oTC^7AL%aiTrAMs zW$jn>4-H#KRK>*IFM+&@7u}B?DglIyprDwWC!p9wt%Xzcg(yA_5Cp16e~;sCAJz0+ z^;PC#9P{(!00U}w#3pr8!9-l;jvb66BDN&nY0=?AWGeJ9qhVi!NCY$#F~5`(QN)aR ze0+Z&duopuFV_N6Y-ULnBbek|ayc%Bv4qzNj~wi*nzq zbq>KTfm}~NKYWJ0NW%gKrXy_(bRR`?Y|p>6kb4#f^~Jx)lHE>E`NuS>#Ez^4D;%(R zN^XeCyYQVxT^vSgXjxJ7Jb6^!b+k6IQec)ILA+Aq5xgUk^nsdZX#721+xlXV@IeVkoo4XDt zFL@y7Z|?q%4Ur+a2A-F`hWP9kWY+z)-?@rcZZc`T{RXFum$1mkYpjne1BEfT7-!{A z0b$gO?!UE?N+60DZMp1YIMTxoPuO0Ee~5l$6E{z9TP*J|?pVSt_OtciknyJU`{ z=Cz>bBB!jMx{vPx)AwM0aKSOKafzl>$RJQEkNKXN>-+Vm7pswgLoR6I7XfXWgOHe+vJ;*0v;n8QSHtckEhJ505=Bla1@(@#4A%0lra zhAvKt@-kYkeTi0^Sxn^GU$k!fkAji9gB6OatL@hK$QHN$WhgJcv2o?@Bxjea+<{hN)BHCU>>>_)d=^Eok>*V zdV3b_!;_E;76&P_cnj;(r+W)i5oY+1*i9z&uP>1W95-5H!BQKCCl1Y}wM4IllEAa& zhu-3epbp{~3h4RpIY}zEeP0^VoDr8o`32-XDbAtKSOL|g%8 zs`W5;rhne!kT^vvKrjs$k#QpjUUn5uDK8b!MYY@J{zWK{^tX}GpF08axwQ@ALX+(A+3>vgbnElS`=#muic#XDX5d_rLN z|2*(6wkXEs!e4Iv(7Fghs^UP;r1hrN?ljVHf}z4fm5LqqJD-+R-)fYN4I_ijt^IED z57cpz6D)`>%@-B^eZSW+4e8r?be!i1W>s##^p9aq%n$`VxsBkZoktW&#)o41i;N0; zWyj7hT}B@2JcHcKus@jFF$ofz(tpNX6n6h{>}mdAgBOla&rch&r32+)NB1vZ!CZ>PD-!t6PwWxNo|BHpzf1EZ#OQdA8aGvc)FdPv0DcUTEJW3l$du6|%8B+CXJgABG1AxZ$WNgK++c3m<96*gjZT~c*`^hgez#^ zB!e>JbGeUhpAHOw9|o2sBF6<#SxqDAmrcMUMLkRRz=Esh!#ti6n-qS?eh%0&&=1_m zt*a0`-YZ9B`O_mWXsw*2^7}&QY(eIjF{^ zZ-j|!P$1hEfv{QC5YXw(d+P7^vlJ8|kc^d?R>DWEVjbxX4j#|K2EP4Hpt9~l1X}=P ze$^u@ni5BY6Y#T|5W9R^imTtRCtYrRR0qF{?fvHY_vuV2JX^yfDJ})ro~OX^H^Ckr znEG#i{bb+RR`fY=d~bHqsmq!`NV6~MF!hRU8(`Ms%FM{+>~X)esnWi5mGc69(McLZ z(#n{ICXw~K!1MydbAC|C!WpB+d%Gg z&E)63g@HQKy#&9tbHD%$KR`M)$N>NRHOrY(JsauHGxvG_TV+6`%SiKh|90zI>FMHm zC*{Z0L|_~)qRCQ|2dT8N${6V1I)qL7pf4%C~G!N>*qyv$l)qSz8fLYabdb? zYnNPG`&og6O_CxBW-=xX_qn$xFmepo+WKh@eGxnAk_+$DGI^3gH$^3k!zbhaPu zvB11j@^g6S5p%11*%wsFcW=F1#gn6+;|-RRTG}P;LExRUJ`47RF-e8D-C>N1&rc6c zPCjZ9v%dCcCs~s^d!DE}+!!J(pfT(oF25Dgs{35tiqFiqll8TQ&^7>Mlq^E~P!ono zN-+09Q~la0+aiG7D#eBx&N50DqW)NzL)G zAaEYX6CBZk5J*=t?p#-WIvnIgkc!gkH|1G};`ITA9EYir+~zcmmr$cQsyNbc?ZS5 zy&Nzpc|}Xd%ck_D%WdX|Mnrs1)9CIM0NE4ql5cyBQCHZ)$9%>y2s%Sp8FFy;i;ja< z;(n`JY}El_}g=d>R{ocGuF$BI4H;t&7FZ6e?Sr+_*oz8}=Q zCLuh#tmc?Y@YH{R$^Q#H1)c9Wy(OUW8u5RqRR0lx4#};gQ~~9U7ed_-L)Y!!yMgH= z7`&$Ua9#vj&}YYw)-XN0mrq|#*Tv!+wvC>+4Nk|2dRu-hp=D*8jT93 zWGsNyePbdH1O^<1l}$DPN;Nt_7+@2v?9SAt63u}tBnwMmkS|7NpUQK;F>eFF!M#X_ zNUkXcd8aG}`2bJ+Sp(_?b3j)#wam!`C4w~z9U=cO3G~jy>HFr6N_XT71X>K>L2IU+ z`83CEO>8RH|G;q_@bM_f^I`ASAJJj}X-5DR9L6viHo9KfJaw^|HJC=Q{mKdM5Dc=V zIq0yMw{yg=B=&cF4l1$Uha5pdcO3J@a*C-?v@BW(pb|8&KjVagH!vyItTyod=+h}! zP%mUq12q7~8O^(rDX*g(vm?0qTK>Mx8pd|Wpf)@g_Q}7n7=0e;IiH7X$0h6E1{Z$%u?v0t=;2rjn$5&%wRUtX%B;XO zIhP0ab=x}KGx5ttRsbRCI)PcRm6!y|BmDzH1=S_*Eq!wvS-qG=*TBVi7a?rs;m;1q zTW~Wlnx4{W1up;J1pWY=7P1a^??)lV7F=IcLI6oYY)h@^eL!}+SpU}|5osf^NSjU5 z&M0zu+ZByLdypVflh08x7PI`LN^E1k{&C!3(AIHB2?81z#|Z`uRBUW#-MH(aLR1rn zwz$5YPYXf@+MQn<5E?J6+ev|&w{adO$3O+Py!GwL+lr}J20y`1EDsI6+nAClE12UoAZxOb!36Vn=q0%3o zsku(=^LS!tp;cqdU&v?(*U@gK0@!j>uh}SE%*KK^!*P2YOq#x6iVQFcidI+8I~Rd2 zdF)ANrp*#4>f<v!mcUhyvtL-dXt4<@YnS15h&J-;W@&`*ON^1ctR^|;RhejROuvE)pJ7QkDun<)Dj*Os3^FQ76n z4wq%!K~gzJw`5Q8pCC9C7}lWjORrD=x)L=+A4pij6}|H49F5r;>A^3yW;#feXk7pI z7q)Rn^uSrs)*Ug_A4#Z~5YqJHPDsmd)hAfSVqY&XvFLig#f1tWk1n8WLPsFrJ2ywi zld0!6!k1jTuya}^FQnow-m`~Gf%<%qbN-6zk8W;JMjvu9Xd8!&>ljp!EE=yIeVRN! zUqwB*yktW!yYt@tXq2nP3F3G?5CK>?ME$Z^%_$RKQEK z{@UFh3OrX#R)e0(w@2evgC2!Y_kcjq%4{U{HXu3f4|;NpO6JmX+W^t3XQj zOxlZkt!|$N_sNfof_C*;@7O8$UA;+MS6>7u0~3$>W@l>jfP`N~;P!04mHYwC5nnrv z5nxd|Lg!6}szj*(CowhG?K#HPy&3mzcN8cN5N-YlT@-UA6h+g|6be`xDmJGD8Lz!I zw#OD6Xk=zhBg8xu3#ikf1d+gsJ5TuMw$lUc{Mfrved+JLfKAa0*ynt5Y5q6Q5hW?D z!@C<_!DHiNmIWrcBK!!9cv^0Biql&jt-zlX?)wQ27#^Akvi2cR1H>^}3Zc!8s zj|n08YHjZ2;AQKZwuXpZZ z?W3kiNB_|=Ynd^~XyB*T;af4L*axzmm=WEe$1-2~v;s~oHLTax?e+Hy+d@h3eJs4yisBb+ZpM-Ae}hMpU#ooYNZZ-gdszSJy_&Vz#&l3YqU-~PLA zbeYp~{>4ok8T5}()|nOVu_S%z;p!L%w~99E%&1lR1OCTlyoCEHUZ%huLtams-cvP9 z`SU!X@AG~BxT_AQe%{lP|1l~pUTG!@UP2&;Zy)=}Gq*w5+beSF`2PcOv*999|NpR& z%L=FVoe=Aj?1QJSoY3nj;N8*hR<7<2!u&+tJ5<|c78lftTdD2N&y6}==p!DycdTf- zbjRu!ifmDjXzQ6aiDf@?{|gvRfsv}7lM&k`IAkF*Ism&$gSf3#k>|NKri}D!O>}v^ zvRkz<#ms{(m2fI#G=?dh#Gh2xfrUC2Mqv;xc>5P`BGN?zfE$#1zU~?VEBd=5z#9~_ zhMwBv$N$`C4A?2$$R9&>*rpjt=eXm4uU*``9OurLJuR~&v+7kC3Ivp$nlg^w8lO^n zV!F7_N*5*zVH)r`4X}2{=iK?Kvw@jH);~PX!@@PM@u#TL>&x~XlnC?ySzG)tjw{dx zFIBhBgf+3@aB6(f{O?Cu@A%KkyB-q6vja|tnWZxg0l0SH5f}eS{=Z3eK(6%sdld(7 zMk0tf4PS_BH+o7-pStaWla7`B!VmU*J>E zu_V0{AHQb99Y915>{3Sc!k`wuU;0>!={oSMqJUAw^Tj05_6^OZs;c$+tYRbkVmjSD zw{`MmbhvmJwXo^L5jePfX0opUx{N%*aMmYXcw@(kS6pDI{OSGXyr^}g>$usDS~#ld zJA=x_F3F2I@PfoIX*e(AZK_jyXfQJ+O^BX^z%Z!roNwK zP2=Bh6dpGiVd#b>py_I>bgoIIJq(LW?LVVM&5P;i0%|%Ro;a(Ib)2HA_bxka-UKqC zeM$Y0ejCZ+sgioq z_^BAXt->00JR)8NdxqJn88E6*EOeUtwFj*&m?iFw@4E z5(6guoU?}IW!?1*Wq#E0)?s4FG5{05`sS5a3A}%WVV!UgcMQ2 zu*U3K$daw5dd5HuC!6W!+NR41hW$^j$=)x@rA`UtqV&y9Nl(lq_XQ`z8&UHyRW=Fq zWh4fEx&WS{e+5lFhrS&`waJ!Zv}8%)`l!&+x}qt^Vr1<0%nuXapM=*@ZHzKQ{YI8X zmx;;`jCZ}NQ*P2t#)`^M6i)f}U_%|ee;20}C!y?>eHL6E`#rd}6kc@sN%i&HQ{e{* z8&8EpvOwWK<=Y!Sv72qIt*;MUE>d`iZ@B^v>(4DY`=un77Hh>%MW3vpvK# z?8zi$lvC{Ax0-N6dmRn{M8|SFa>p*S4*Uw7q00VLp0gw4_X?(i3rdC)WEDwL(2F!_ zm+TpE(CQ!*jgE8jAwOko3ULV{W_U$^LFAjXTX0oMwA(S~Bu%h?yn)QSloVyQziAe! zaN|4-qctZ4+|~#wcQ-@;lxN)|8aP=8`4!TB( z5^+vyVVyC9K2$_qDgbSwYx-KLB3i9y&T;u7coOv}8uuEZH*!8Mu|1|WGU)ENdN{m6Hn(rzq-Dim1RTUrNtzx459Twk*m+Sg5UlfnwJ$6 zd~iLqEk9H2I4py2)cI*+D`fmHs7R2)%ey`fZkOf2$(LiY>qOW#r; zpX)p^`aSOmIBNGsUckLojWTR5LojcLEhvd$VCNjc1DkTg;+o(Bppg(4*=mQfiA0$z$)Vsi4r%2T5 z*bfj_JZhT(T2H1~#iZ{{KXz4P>=5ev%kS`L{fAOvk@gOI80K(NU}c{AhSnZ=Ox~H% z5yYlOv?n(|bGPODnRx|7Ot#J^G{CnZ3>`#L7Rs;h-6I3$=xDS2XWv%C7{SsrOP;WD zu>3*QPeJ3K>W^RVaN~Bf?}E1Y8$VxYM(a7eZudiy|%t}RY8CPk6fifR9Ft|3Z@*|)te}{%{Mm&x17?abVvSM0`Hs=QBK>^j*(U&>RywM8{ zP|IukhNY33ah(LfC+7w&oeomihyZ*7@{6mYVezA)3&Qz5gFN9q2CWVl9sn$y&JT-a zp1vEK{(O5eJD~d}hjjNjba7Ts+|s|G3AJUSV_}&0j*Mc>Q;TJggtgFv*^2Hd^r5BP*!o%txlBZs_QCZM7yhD}A`&o1nf)~8nEdOOrIW(T< zRta@wdDS!Mg|9Hq-X)*z?g>pZhlbogwh1hoDVJXIqnCc{PMH*GQ~3EbWZ{bZ!Nx7R z2H$&rUas4&9GGeQL()S&r~zRGneVLCxxsM`|IO4$0X~eW+)z7AU&VIK*SS&!cp;7> zYEvT(;uBgeYzB3&+1fVp>avON3XxyPNcrRE(u&N5-v2@0U{?tK_*O>u{JQ|aF>{T^ z9}tQr(=TS;{M_;3Ggm#b-*fj*|L|jlUb)eX{g?Qh6DZHWyiZq#ppniEeXIR_-$vJ< z!GEtmT{SHyXE__wW02h3lcP6W=k!4ft7?wtW6s6Szk8;&?w$SvDlgVmEx+B)wez7{ ztWG)CZn)Q~2>M{?`X{pA;W{3?d2d-aP)}UZ{n-mgit?-m19|U(So8GNG`Y`b?va|Q zKcvnL_zgo+gEM5)}DZOft*0 zKBFM4k>!T`}q#c2A_DShfTx1Boe#cy|IO_z&?`tyV(xLVHcAkL(Q6>qb?^9joh=o;#0 zXvE~Ik8rpme$fgm%cx$L-*K;^oIlIiZ>=;aWo1b+)_9!U!F%L`dt(@$E@PB9{h-$+ z*gcC=lP8dRUPZ*1ZHGRi7*})a&iK{{?m9t}2lK(sMCeZbA;LW`aGYq!%#^9pvxND9Y-YlUt0{#nGo3*=qa+)G(V0o-D!B+fKSdTO!gMx++U-L^nr*JHMODc z`gDWR%-i!Yx%^@=3}x3(J#8{e{`a>kvNMr-?q!bJV^NpD@Q+jOx-W0cfcL>m)w(#f zFd^n2t<7Dkls}c-h=5qv2*XJc6j^^!MKhIeAM-_u#*4_Cd2T!|_o9@~M!lC^mjll!eMM^Tzv&QV z>A!ZTk{rVdrFqPaRQb9oKK5Y_O((~FOs3v^W?Xgm>hQ~2JA=ELmLl)tn)WMbf`uev z&*muKM!sYvt&;RYVdhkt=7@?9{Bus)q%5Q@45#q6JFdE1R95Xrsk z;sy+Lj=xgxsI6r6GK7&BIT?VeNKsKN=>{%FHHt#_?Epc(@i$4Aq|k5h)A0&wT%kBa z_8YpLyRZE*{&wjxn;huL7JPtd zf1YEDuWGuiy663?^=$Ap>zVDVzFWtU@5`MM-BX@X9c$_adj>n~#b^GRMc97bHYGI? zFle^XAL0q)9a#TI$vW+%ovUT;?WE{yuQ}PbFBp3hp=38Fmhw{ExjKoM0EG_z$~YBF z7h_5gtzwri;(t0eV{x6|0xBzaqaOjC#hZkNaRyDQb&WIMh^M&yst9~ zOw>%I?-Gkk63~(IKWGwQ;gL%h;MYn0<+K@gjC zH!NOHIwDI62VLmxo9^WAdfu&YVL9>&n$A>z;_ks7Sz)I3 zxSD_~5{4<_-&fyO^5{g7k~#(>u5@=`h-C!%m!F5P^X^?RV#yJt8qpN+=39n;J=Sp@ zy7>FVPRcnwT~hQ4>|dZebKGtIeSR4!*}av1aj+?X^wXV=-4`WS+kKVuNswv#O;Qb1 z94SVe9J%;FA?(vCKvO7;z!Pdl!0dm}$J;!zqt9XXgRRxQ3QivHl)*iL~WN znoOnpP<-ma$IW*R8_VR`B`!~+$*QRL{~rtB!7h@EM)#Xhkl_GDT5VI_Dz&JBOUPpw z?iIv!u>^UWGY&}3>Mv*1143}O5ok{ z(+BDK$U-GEi$uEuwk`n~93zTR^2jZzC+`#O*O1?*umjrn(|#(lHnlW}Ud$~=9tIu5 z&!S@A%6WLouiex33f7_~>5iKW6n;M9moQwPtTqAH%-2;LlEs`pmEZ;rKB=BbE(Za& zrdJaw_Ce*S5ScvClMfz)7C%8%WHz6eThuh4k0h57%O~6Ue|*PoD6v8_A@G~3*T-V$ zR?K^hQ*Mba^WD6ddTDC0XT>yl*L&&b);eUH$Ls;HwSh_UoK?r--$_lyF3fDsP>Vo9 zDVG#TMlh^%S}}#LyIL=1Z&5^3r`ohrH%H%-rlxUv_NTHT%Yo9HsaJrepU)1MzT`3< z_NVIpd&3z;&z9q9`Cp`|ZaR_dB40tV=Jy#4Y$BXw=XcflK}%*EZ;$R6&@+)F$bBQ2&?FaE7-#B z+c@#vOxlJR81~0eALyI6f!Iuli*wl(RnTsl`RwcmWjkq;vb5KYB-{Ar+q$eF53WV% zurrx&;n#mhXsBhDN!^3C`~PBvwVlLwoDgfS?Y^`y9GE<O}yS5!zOBxx&niVQrCSSU{#Y4<-|y#Q2@x6y9Wx`}R9e?E-dZREw@ zM0#gKTR%YzUY6@KzM7NKD=GBnyDx*3iJYBE)t#NUs`-~FwhO-Q!x7amfvUI6=CJ=O zK1RKkml8q{*x^=I%Q)D5_Wi-NnZo=oKbyyFPkaNKuIw_g2+e-SpXNpRtjgwsQ|7;2`;GRgTTq#$ z`h0>t3=WLCaple;x7GKR%x{k18tNMkP6C@5f5~p-!cRYddG9(;8;E=&sB>fieA3NN)l>|x z4A+WwUdaqq+7(dn>i(&FkSlicaq@=k{qFK?@LMhh&v0GQL?(qBZr{JYex<2tPW@nHXcImR20(Fy^-!h?x~{3D zaz0DDXqgo4OP)%1c>wYE4E(O@&0) z1D1+=zt<9Pv8;q7w%&Z6o>B?M;W6N9(xqH^4SrUMm$j4&7x@(KWn|p{YW?1P%`0}2 z-)7L_MEM?#pdysIJcbXhWoslSGEl=R{C2p6+}M0cuAtXIDfhgM|LlIFtYGAKLm74B-UC- zGL$%`#c60*BSsSH?*!pd+a-@u?j?tK&aFkCcBr&yb(X~>`>v1P+bWPwQ;ut#?C+r* zuz2_9#ZsD?_gvp%&_b+TB$wCqc}rj3dzU|*OI0nkey-riH1Zs|ExXMg_R;;x^tsqo z^GH&SYI1BF)z^i094DrB=0PZu_$+|qjA{%SV_|TdWZkgHX&YoMw^nx8h zzMQP)o4-`32^4LW1o06SJ{%M1d13fdG0?4B+UOpttBgPE$grpv>!=6$WBX!K^0G;L zL&*O6?npr3kanQ2+%L_X-C!=Npyw<+P9VnW-d3PZQu<#5oTT03qd(|@n;Y-RvSj(X zmd-!(P5ew-nY*Zltms=sOhTRYth^Md%1i}3EIcotbyMXTblabpR4H`!gt)dF-5h>U z7BaF0*-TQ*3n;)qTz^=XNvx}%tIG~Rb{VILs~;@U-dajVRuy-QwM1#?bi?1>1^We$ zYNOR(DU-_vlq9HW%y)+Ctf@cLx6XjIWZw#t%SjfqYo3kP)sEA2`W8=N3h1v=4V$v1 zorF`cFs1Lj+==X`c@C?4A#WPw4m|}W@)&sA`{;>ERUdf@Hj@M%*d7@yPDTP#7J7z0 zkPIxcR;^v)H_YE7sYLcgFczz?@*gi+9T8pQdN5@bd&#v-0lh=icX;BpaBS;fD>pHH zJqB;_8u!MouxF{WmNc9X%)BHlJ_*g{R+^sDl)pJ)CM~!&q@aRue98l1DPFZz!D#iQ zjpfsrzBPx(t*nthJiw&aQ(^c|Pv2MunYt?vMcUeyba8cui8GC#dr`A|V(67IyP^u? zX$%}D9nzg&-_D8P=wcV#en+l3Tw|X|UDLI9b&s`t;S68EyrXIK(+!WB-^C`K*`}A; zb2O6b+HP%4yIaF+RwBM5Mhla2Q)kk+$@AH~3_{7;UlF^9QXZDo8c6U(RJf-ZcL-s> zu}|yj=+i>H%H=y2pRP|=thXTNT;1py-(E*mqB;-x`IZCcZa;XSW9DaN<|epOnH7g% zzYV^xbR=M$GEbHv7r93{F>l^GP1r1RF{P-GU`R|=9WiClP=Jm;SW31pQF7m*`a^&9 z#A1f5*{IkqpKQZ^*x)^RdalknHT87TL^snUI?TuN{%FmJG7i?eI9pYqm|PkP<4i0h za|$?H64h{JUs(g%25)l7a##NPBc+H9-YIEthCX890f{#(qwgD=N4xtJd{ys@*oE4s z_aeVcZk%-JU%WNk_D=rb6OUJz7HcO@aP`yy-?azYY-e$)?^W*C z)WQ#MKAVLWG_meR9@ov}$3dL9QrX9!k%XZuB!3RQ@atPh#$?$=>ycoq&R2p{DSgmC ze`Q`Ht3ppUA&m-&Oh{~1=R8)Au)9O+f|BL6;=;MrLDR`UBCdfvVWuMs(;jSHyduw-@QN*1N(x=Z6y z00GVBl-b07gVXbOzO#Lxv|%o@OEV(iXjNda;K4OBzc(x=4OPP8QI6SkZ(Y1d3yD4@ z8{?^y^!hcO^a#XwhYf$1G3&yoGt}rPMLOW7N3Txzl8s{~=fo`+*7B<{){(@ZgnJ5B zt^7*;^K>{Er}E~VvilRXHy#GCWw{vNnZAK-JVMZ7BRPdF|o`>zgq} zv-#8s=3_-*+WC&_TM{X0)6#FGkUuT5R(j_S zTjMyQ66|^Mw~S-)yAzdaiC}VO^}0m;kv9vnzj2j#Rm&^x)?w3maDr9W*XhyEUA7tY z*yZpwt#2$svGxGH&*Efjlk`NI#MjsK$_!uI6if-BPghefy$+M-M0<(vS^{x4J3Yq} z$@cf}IdDFa{3V4bIMV)&d>cW?hCZ-kET&>FQJK9nI5@QF8nFh)VTZTDX_x=_Co(z% z*L}e7QcUo&2E@c`)fZ#N14x_yxy5MH;s1*3=sDcyfx4c;H8R5<=k-nRU zc$5HUN((XKh(Jn7y32sQ4@{9z zSDp_MKeE19PQ4I!x~WsxhGbq6VH&I_s$Aly_uoxYi?D zf`|CEL;I7p+D03IY={25za!pqfA4Zl=q$pIFT_Z#kAxKplOk8VmLCalKP0Zo3qZKv z(f9BmZeZ>Cp{R=Ido&Dx-+hLs(!OubI_}VA+aU=bmNUov#A9aqIr_7HPI+GBy)L23Nw&N}JD4iPA_6qp zVfOO>=fyUu9u-x*|p!N0;>e=xEXnMN!6mb7qAf<=3dE z`R85Z%!aR z2#9s^O4!+{%L8FxdR6-kpdS=(n)8_+}u)n(OEm zC1btS@+5cj4yAzAn&e6cU?e)t1b&atDj}@F!D#g5(*|IUe65sdE(^BF;VPtmGd zBORQ!WO0cQ1m$_3Wulpw6Fu4k#d!1^)M;EW2he2RKC-J@e|1B)ZudqXeL1vsRZ}%e z3VK=EsEISoF3jlxrB*XZkkxo5MVFcS;_o$%KhtF;cC2N{A|abk0;EQ=#X1|wF}sKF z8|}X7=C{7)!`z&9`NfDF+H$q1)Rc3&=ij?LzkLd6bp@r9b4D!@3C<4{WIK5&#mVZ4 zhpJyTrmMe#xA@jONDNsS(xdFNSL2wk7x7vT&w(C{xO<$2C52Z}#Xg@W2sP%XtA}#2d3R|abKU_~4GB2vZaoovQ@!|7{@|VHp&P|NzM0p-Si=@W*p*Dt56X^L zDL+4JvXn^S@MN^~HGoAe55XZqIe}jkul3pqpXHyfHiy(o+KowV;)bYA6Y zMEfi_{ES`rUz=U3<)N+UIUphQ)?E)!GVl2uhi2jwpF*caIqX@!b)a73J|(`JgeZ86 zRI(0s^Pl-W+hPiFnA}u7vdyWzQGc46MH_c&sKz(_;F|FFs(Z&d53T>IZO0BJUhS1PCcQx#})@#kR1tyce>lHSm7LuYZn2(Oq!)4T z;z_Ds1szR(wAs33C;eEy{fnsr<`6IjsF@z-=d)$1OmV;Qu(GZkx4kJ$g+5YHPz(M) zj&X%$Hmj(JK7`xro{l(Ug=6utd6UPDI%jLS~oNKUp&x)~#qx{yr0YJXCZr|(gzpB6AoS{DPM{d0mRK8rm zD-Fbde^CNr;R!eouiG5o9tAFcz@H6teS0`d+i-7tHE;UHP&#b8oe{Ceae+Vh{NQ=R zueCA1561!!uZ!fbgoAmK!ZHbnfJ>0mSrr?Y zFbXGUJc0ojAmLL3Hw9mb|LIg(9sybachf8^rUJ@4R}Wfo80|YJpOS>$+zhm+gaJ&U zov`$i6yjsTAqlxc3phDjz0_{cTXt_L&eM` z_c5||YmsMXf*{(>0gJAG&%z0s_c`h_Y(;o82Gx9ygHpPoz796DW$m5UeQ z7Brnlk3Fvq8fZcq3UsL+(s0jd8F zdv6(3SFo*%26xv0!3l1`39!)M?(Xgqf+Y(L?(UKRNpOciaQ6Vg-4onduvqi1?7h!B z_f@^R^=`dW_r9vT|I8nA&K^B_%%M}On%+5Q$AWav#3Gmg#IUW+ORjyjvx59`-O zPvcxoELT;Yo7w|ueOr-t{&;0+A|!N;tQ{}fl9aFw5an^gvLTq1jH-06xoKGvO?VB~ z!5I7d0t}Ck!RcdwzT;g2=zII3#$zhmluaf(YV^^wsy_WG)Tanom*5kp_nC~&F`EE0 zRbaTtc5PTt;b*lITEbKh^2cj$?&vs~)ZLA~Ie!q9uSe%kw16w3V*YT?)NxQV27qs1 zD#9rI*!pp4r7tvPNPBAY4Yyl2-?SGBr_6b`+d5*!H7{{ljU%G5%(PhUK-}BIE(7l( zdgNheouMsxZi59+x^G0$r5?=Ff#)n=n*|4Dhm`#lqThxJc@6OUe_dKz%ge+qyWjAm z-0yZ7M+m1jp8p-iiX~W$whfj2`AgogWvA;=vGq`)4|!T*j4;*nfRWc<>SFAO5Sb7M4eEH5DTr<+3`-hCbD24RJTxaM&_}fnJ1mrZ5~B<#PcH9 zdcv{2U~dXsFD9No45ycz(yJf3Y~X2j-n_5fqX}C`k9XwA^5VsjM{~FqB}6h5JXSk| z&~{LHR9D@*TUbI|)wCcsk6_9K|7CDH*{Dk500=*qei zkTl2-4ot$a=qcvoVAHtp)(!%Z7`Z=-rIl4pAVeUL96i$?uAyIbkL$>ZkwO3bZf7HG z{0_&4-am4D-8M5{HL{sAo0HBe8X2hkPKi6M;|?NcRK(^H`Jp9UZr+myVh zN-2jd5TjW93>{)R9x$XJ;HF5IXWSfFuSaqz?#HcQrN8;`Lm-adw7?s3g%!$Ejf|)J z)FpI1ua7@V<95IzoehWE@u#(1XNyKL$!1-kEP_e!WHwGwzjjrCuJYJheD4&_Z~AyK zVO7QoAMP#QW4lx!+aW)ZC84X+>exz@h<=i_tV8sf1Z9FHU^cywuicKRQ(e6SpA^&@ z%VeW_5m6kteX1+n*y;_q0O>7~k!TwVCQK~iq94=VkU&ih7sx$3m6)7Y2`|aNZeLv- z$Vt`h?bLXj6OTj>>ZGx7XawI%PYo54p$udscJ=mXGcr?XYnIeXA}nKx(}2y0iH#*- zm}u(Bc@8Ra|E%&l2bPA#IxH$JZ;F^z2fYB@3kiZN4PDES-W{yH%P!Q1{&5m48}L8K>Ip+d|MV$Ae7ys7 zfMkz?Ak;7vFF27~_{={&1~{@#eEl=1%jc_yZDE;udC5RC94-~j%={_ug~OB>&I0+3 zpF#o+mZs<$;J!Iu^z%b}DfQ#Ch@_adKF`W@Q%F6Y6 z;MrI)4}`{hT+?oGS}I8@x@~WNWqg=-!2qTp^!k+C`zhR$MIVujPG;gBW8pOyQyB?| z%Jpw=rZl?I-1Ph6^U!(M3FTR{jE!?gL}-quwTgG6YvK>eE&PO+P|w52A=8#ME8N%D z_{qR{%SH%Ey!H?1(P?vq|Lsya2Y6`YozBeh3z-=(Giq*pxoZ0=zt-2Jsk=f2BaA92 z*z~6TH{@9S@>5G34v1cH2>(1XuaX2iwoah!!9=z+tVh1UTJT$KF*92%$Tl5WKiUT0 zuG_R-0Nfi1QSmh>I!p3FyRL;;MIznz= zK(Hx&g-=S?FYv~Hm6~dvj2{~V9D33&Nq`8dbw?Q>*A1tQFqW98>FTwAr_LfxdyKR| zetYiy5TNZ?|>SKF_3}E$s|JN%jmskz6=w# z7vFQVUtnn%Su_c5#b>ErsoMQ>9Qay4d>+Mj5FyK_SHE|CD~XUxUG&`$1#&N2t`4vM z-3c2c2%8)cIOTW7wK?!5%gKMY-m@bX?DSzs%AQQ*aJOf8P?-ETu1_;GRm}jF^78Nj zM0QE7?$24|Yb%TCxMU@fXP3!SP3p z8v)T0sh;$oz8TCulh)kliIitS0NOED3#C2(U8#Z50u5b8WOID97T-l(xd#$?pkV!L zlYq{p(p$A`C||@5+n&@}OBMs=Ch4Vv=i?`_`N<8vWOOs-@86a<8q4RPmyb@~1MxMo zn4b0V!Ou*Ez|ySBci<;jQ7^(!R|iQPT6=aVIZ9ik$=ZXYwqxIAZx8Q`0vvH`ds8TD z0(iWj;v%;*8X%sVLOLT5zJCeeZIW6c?z64vQH~a#tQ5Gr*I|`^2KqdZ0Cp;!62UsP zS_Is^C9qMr1D-N-Wo7qX><%EnL8VC$%B^i;o#)42WTTUkZV(>)mI(ET!kSw$1KbLu zd5dhaOZ7ghk--^uL&?7!6dC44h<&oKrW2}#AOi7^fZd(W<0?@b*ZS58Uel8>P6N2E z#@VL4lb?ACMmGdx4w)$NM(JX^wwZjN)B~K9-=kNUFRc5u%;{6kH!in0{*1~Mwg=U}&qe9```W4S;X7BQRT?x9+*b6CYOXH(uD#0J06O?;|NV<-JVIgYyf_A^z0&bpLp zt<2}Q4}p{6-4io>H>D`b1HLAZBRquiUf)&)ND{t1nHK^1vxSYfC*ghY_~SrS%~ zx0}ZF!QK#AlK1>-4Xz?(q41uu@iMP9B)W@qKI?ROah_&o&ytUVl;|C_h8g ztI`DXpo=V@kZ1A$+zBhag-4%CrG@=!K2)jAx0%OocdkEp$CaWER| zf(_>G&uLF0b7ONrEv>=^Mv3sC67ap9+{JI@g#~fB;%^NRtEtUi*%z*`ZHCEMLZ2D8 zY1v-=E-xGv`G_C7efTMXUueT8f7&caF_6!HCKWODWL8~O@aEk?2#d_P`BT8<%Db61sKCLUqv_l`6gOrj@{g z>FfDC4{5%yeh6;bLa#g9inEROx;*#dRVQ*@=PWfG2=6zmcD#6+KdKq#{NAIFhegct zS)^?J^hUKbhGZi55bv=DS`+RJ=hQOeh|ef%zil6Vufw>qvw$kQmu<0$m2Od&xC7^rVs^Up8mIj;Vd*{JWBDHYxO`!d+Xu*= zzBh|11WhijV`Gzdznw{MsSJEJS@ux&tADKrJuAt6<#yv8xBar2GBY$X;k%lfo))ai zIDc!EKZ$Sk>t@+HeHKS`a2Ro*fq_9M5(!;VQXLA1ba+`)dI~As_ZfO*L{r)?&e&c> z?!KPRA+jh`1@Wy9N>uA1uK2CQ% zvQa(w_8{P_=+$k1^pgB!ccECZhtUOlP-#PHU8#PZjpHCrH&A#c{G#_V=2I+2&WZgd zUBX-DqD4k()a)tq^C}&7QaYdYutfODfX!y6t0kSa=cEG80nib$aqp=vM(M@Gj$NLm z%i6aF%CwcAT%G5VF0a654#jMK_PjM%(noN>~VRw`mE;It*l((oU2;s zstfvN^eQ-Q9)sM0&MHy-5A!cAa%`CRN(;L>mQm38oJ)0>mD&2%p^DzeB+0OvOgjIc%;N$HXU8LWr`2h_{VRe`n&WemP z@5I(*_}1*yLGI6m_0StKwBscGmH7k34-ZmDZ>B6=7oU@2A2!R{N{Sk;?2^9Xkj4%> zeh!PcbH^eDs|B2RUyYAL2oRQP4@S9G0mfO^Wh%aY%h*hPpIwR9Id*8rjBhd2ikd(U z2-}|$;V4^_lv6rQf5rzKYUj>JSm4)6n%g9bMVW#Cx18)afl%m_=##8>_lLkhJ0qC- zy}bk2-@FinDYPsUOh_JPpv+o=UcBc>V8wzf-3IWBlMDSApbv*Ti9|TKm7szsEsIUs z0pjs=uq;k!&Ficd6qoyZ#|DqrD%<|qEq*%iDbW(IM~Xed^)6{*`hl=6hxc~bxDIU#M>5LdA?KGKOs;$5z}{h>7^KsDjt91HWZ#vG<Ed1{GK;VW%c3AgG zrr@WfBC3A!akvGihE4&-M-!MHuG?FJ=W?N54zhCfM4?TRn*J}zy&%RSyO)_gwAPFi zENWs=F*eM|&LJh2Dm=S8Q=@b=;8)}}ak5AQ(P*0gDJuwSD6+ewjv5x1>`)|pLCcns zk6(!rGs@QkpP1PrgPi8cvFrwq@=fK;Z;Q$(Ig&)BUMI9hh+XtNdRVx)SGN54jAUZ15~_>JqF*F6 zCA>f`wH5l)ck0JouG?BoW0NS1a_4rY($GC{cGw7}rWt-1&lngRR)_%qTv)i+4^_s}cu@saX8w+xP+V#N?>Doo;GSf)%X3er!P$dicQT- z0|puzedhji90qoHQH^H5ZC?VPfecc|j@1*vua@5hx2o(ZVVHp1`)a{1sERY=U}I0! zpS86rrx)PH*69WS-5}TiWwy6?$S-|F>y);%rDojJ7SL++M_@gsnaSGP%%lXAvnH{l;;+gJ5Y zBAf=ckty5vgEH&NBeo#&dbBXb@9E@jeCqxD;Wb^5gtkYRd?_GckzcNS5X(SDS{dsG z@++Fk%?OfTv)KO-c~Y4jxHoW*vnu)HXgyj`8QCeF|IN;3;Crgg1|B?%u$M+g@2h11 z$IDz;m+K3j=pR!4vp=*cv+C3b=_&&EBQht5QvJK5TS7etk#;ai=E-1UJY`r2sNyWi zvN51k@fr%d54}BtEyFUof`ZJ2!Iak))$fb8dx9&5V(KZpbNSsI)Ig=#IzvOT!sqYF zuM&Q6;XS`TS{ZOj(PAt<>C0b=*Wv~}H`)e$>*A!@x*BQfED`x?V<9_xTjLyHlIf{ztGwy=W z(SG z4H$bblaRXmG^Qp_K~BsJ&#={ zr;+0;!gd1`u#<927EZt7lx=AX#P!&cBh~twEB*gtOdf0iz=d$~D+e!5i zgzT2U1_vK8&Wne~Z(yHFefR07CfpnW6I62HQ2WLk_7McfO|NCxM?sCx>PL|z@Sfcn z`41fl1HJX(vrp!j5j7PSRkBFwRDX_**cpl0MfDW>SqY1#O3uSZ*YkdJ=ofYQa7!`C ze(yx@Q(+-m3uw=m;SfTPk<9I;#~j*#PrC4Av;0f9FHzl)(MjktvUfUepF6&~2-f1= zrV+!V!X?xaqioTq%}0|~zr!O&z+Ocv4gT?eJd9`OtLeVv2Ch8eNg%va;tP8BC0Gjf z0At>!)Z=I=;;KNmJgDJ*W^s(nA}#5kV#z^FcUZ3uS!qhD=G7svVqlRrp?hy_pUDB~ zxqjiYf!Bo-SoD5HlJ^ayAs*cQ3X{|GDfnW<16miE%K$9NT4bl*zbUG0?V3$b+k=<` zFpK;x7&rF9rDSqm*Dy;a=%6qG2(?VbPD4yP?fMItGKXjI1Q-dc)_bKm{sTUo3imCr z)FvfbZbKGKjLR|iu<3khB8Dxv8gNxGmZ9?v+_adLz}KTVeR=^I|C zjM`m*FCxC$&9ypDw4W{ZeXt#9bYm4gO12(PO)bB_ZQulNZy4I=*>Q#B`7ZmH*D~S~efZd( z5IBJ&v>GQP%0}veu>S^I`=-gcPi|yH`1(h8cI8A04>}Nkwt>aQ1jvE7`H0HYdB?y2 z%5jK|eEu_x`ln^GTl47@dm3G#N*k^vfV^RE@brrm4`bgT|ktgHQ zS>c6Y_476Du6!G^&fguoi`&&)>NtvG@cC&9|A73@?bzPiX%m!?xqso~Ltm#ye%Rxb z7N)0`{3-N0)t50XYt8A*<#xrLd$qaJ#ja;>+?YpwB20H?8t-8fwpM~f`2$A*n%;`j z`qqOoX_U6(#rG_w*PH5H>+&?7UzP$YDE1#|GIHB^o?wG<@5I5>9eK!w+si-^CF%Gf zSOJODDnioTe&&T#pE&E4>x48_$9PZ3R{Qxo^;EGm(IF6C)~$mEnPaZK>a8|GuTq32 z(S6j$i;NeGh1q8lf@eL6qPA)==VkR(QdLTu_^~~<^$8DO;OWov-E&ZmtJ6oCt!Lpw zl03ScpvgikbOHJu^AmuuQr*Y0B;?X<&O@CFcRu{)qiw6e(>KUzd#NVyn=N9eSBMyT z=6~qP_d-uJOTOWBh}u7DiC`x~$OqJ0wY9Jjq)%+U2+rx*=X66|&<%kYMD#_E1!AYP z(JSnpY@k<@PbyV8YxSnXVxJbm^xEC#Iw0QTTR?o zWa0htmYhxUZQHSx^JwmxOwsn6GpX9!+GG1P?g*v~%zCc5nl5%+Z@t{-8rV5E2zbqg zuQBNe;gh0dtCJ)2Cs4=YvatAwZ^O7;7Ku0~H)fO>f}iy$w&ElY58Tmcne&!f-wzmA%-Ej~?#n~fOVANeXqwRLj4d?j@KfM12Q8ch@MN^Mx>%XT zlmCG@)%N;D@Nt*U@D|lPel;Kp{5cL4N45^hu(F$gO`p+mXnXd>v`%dNN{d8{Lp`HF z`f-S|KyJL9q@An4{yZ!)VaU&v6MAIv;S`S@=NIo}XRmPX-eC4^*AHqd=RJz6J%{O0 z0nWPjfzCYK%QE{9Fv?zA6i(748j{WRphr`K^qvk$3jq#+%RlQ${wN`RGOjZ`sd~l< zuScuoh3E1SBIc$#?=kmIs+ISMoCOdCLJM}(i6i<=!>YnMaGh4sy%$gE8aa62kO!P9 zZ5|Ii#~nOBCiV}t#S{jHQnXSS9N|BlPg~CjHh>&~mVqp2WRQ6f&Yg#LK|Y&Xu|eLi z+BuEY^$qftdsm!(a__US#9a7V*ciPvl4|D`{}k*Eg6O0%eTbB!%qV`%NnNBIKa76Y zrQVf=$1c`lVCDw6@2!a>YZFSt6syCc=8}E_?=}jp-8yk%FcUykxN`$}5F+nuaRX() z!2L%n|8N|UKOQV$)I{vVV&~IDcFR5n`bdc}wXM_GO3FUQ{ZEdhqh07IDyRt+%3Km? z8#wI>Id}=#Zlf>X6BF2oPqfp>IywN z7Trl(#YNiNmdG|xC|WaSzh#etWem=jTehgT^-iw*uO{&B^^EZXF*s|I5IDJ#yFSWO zgHdDfYepYtSK8#Y^9CD_rDO4rf!1UVUlKX=fmef_i{Q`a%MLs7^b6$u^-m^YpTqn# z99!0_n{Za(`6*ZZCqwiGw$?z~+0XaJOyxlg8|Wrz1b<{sUAgyL^h8^K?yQ53SkaHp zpRx@TNUCh1hKO(~JNYY609qUL={|9Ho6rr}zWDMY6OITsvEkBkyZ%Rdk42CT9sxG4 zl#P{b?AV~i;XlyJY$4-PDK(&1ZI^%NWL{8xxk4vw{}GSu=lIX$vo1L%Bw5%~Pl&b5 z{`tt=#x?B7)H-S|FG%NO+)kxz@GFqDjm9`VaaA2N`l}3}aXctCH>QK6?N^3zj_Nm2 z6jXVtq?c8m*?*}m4CDHCbivRNneUt)Jlbn(JT1sZdOI92O*|}g1{VY%%_Hc>NU35r z3mL>^Y)86v>oyX=R0ikvSaXFF#LGzQ=h{8R7?)v@aq+W%cvzbIqA7!m?+_y%nBQ3H z7aJ(zrh36sATjlB*^xPr$bg-MT8jSJi$@)@7a=o_mHiUU=yJ|^((N|ED6ROT`0swa z{uT5C8|1T%kJUwqCKE3jQTwV0l!7AHQeo7W*M2}}H#VvhS_?1KAqcw;6AxOAPr9;7 z+O}V%haWB~W%H;!CG_i?&c!7_EOh3GYw{uZO`8_9SG}{trZVykztjXx3FOAU3U3Z! zzFCc!&V$|OJr(1$R_Mptla3MGeC(|HYPSay|7=oSt+sgO1#*`=vp`8rB(x1G!^*z( z{yn_w*0uG|b^aG5-SqMn{uDi%-I&6)$LJL(0xcVZO_L?e+rE!;nPy~=yW^i`xLOe* zaAQP=4U|O@0^M;mGv*Szai$-}+NIJ2K=+ zAL5Q-_&agGBxvT@t9N@P3 zmyJ5tM=ITDb0`lmA-WgUvySxWtb!k8&z65%@$Q`EQVFT4{JEmlh0Jn4B&@(GZQsBC z4M|ifv3+Fp5*~e7H>BLS;9DsJEaxhS3>VrKT(@_=Mh}ApfTx>^na%BXCf0R zCCl`4mljIYmJWQxA&QU&~9=fnWZGvy4Emax5}0?Q2tmfRyBNhPe$i$(F%FD z?J1u#^irIC!0$^C7YUt-#S85D3Dnz>xSPaCOEf9S{>8`_q^*>B`#!dAx6apQ5>R2e5%_38C)lHw~`XWzSdg8B9T9ZG>yacObcN-;(5GR=et@Vu6 zyrVJ%h>^NnMznR^yjO1SAY}0DD3t)z6ziyi z!aWmAqNiW|9AeRL%1G$)N>d-+7H`gekI2lwwd`4l9ZyQ$p_?O|ZDhq2Ru`iPB6gN) zo0ybQ;1MQMQhDr^j&@Dt-Fg6{o5-t@kde`dMUKJ9T@Yh3F9-WaU<8Ar@cI z>waZ47HkR^v0im<3%6@t8mQMj0bdwAC2=BSVw!F)gRsk~l=?3B)juQ-hD7#Y*& zgU8b5R$K*VOfs2V+ztV4vsPA%Y&`-JCX1a|C0k=5_lnGYDFHXCQ}e zOvLGe9U?tT1D52i!iEK&7;fZ&Z&~Y{G5NzrvAMhJGfzR5fO65WH^Qpn8a5flv3x4h zo%gBCB1|irU8kOLqadrxc-BaUEiTt17IHrenK^Twt>#sTb-Sikkc+Y{n;C?|#5R?T zWoW;UUF1WCiL_%T!S8`glb`~F57RF-I$wOh&N%D({?;j5nOkXIsx;b6Aq)MU-8FAd zE9Yw+;o~CQp?hMUq#y{wN8qFv>%^Qv^m`YAn0es{-;rmO!Ag|&ZE1E+|GiVikt~gG zFj3+Y(6gd34lfZi-AjaoD_XvkHXO~GE5$O$)L`83ya3nUFkxEuQ0_m{OIz5jy? zU~!1F*dboqArre6;Y*`uhO%SXpwh8*tVZJ?Yojvi;xnCP;jvPFZEL36Iyn}j9pYss zB$sDw|EpF0x0?Tz9pL{T)|{~-ip5u|s^iv0H%QqIkI3>-OSw%#q#&!m5y|*0Y)SVr zKlQWt=itEtV>%1P7$Q=u84<;08B7P0;rWCATZuroh+rmGHG?R{14c(Y*3In^Z~H7V ziCkMfh6$Qk&&Cr3~0SC{PW z+e34p;{NVW@?(W9!0o#8yVa!ExS+`^vcr4*L%G<@O|;8)3xq9s!3oqkWuj5IyFpCT z9L;`x>TlrG5P4aPzU4$fhPAOJ`NQO+Gq%3&Q1#QU@56pAy5}#F7bc34vey;f@jaq< z&W+_+(=Cfyk2^vf(mdyHURJ$a^`DYuA*f2G=_sW;bXYTW%AHjc!L_RvYLW{pr?M)> zo!@AW0y{js-w#;|JOf)Or!3y2yc|drgIZ*5xgDEYIRHOsgFbQ=+%z)Yw)y?MvlDYu zks{@L zP^poKrku<$;Jqr?3EpOGeN*d(V-V#>UEADt?m`s=pqihzFqGEYF4zP(?b!hozgqe^%t0qD1 z{T44Um*(oM`-vilkJoKBq-B@JfBX3roDyqf!b6kq8QAEp2wL?kyQyqvYB+yYOjFyr zN$brL)0f`MPuu9G1LGki7%z5p$hSin*76(0?uc2wTdW@~lgvq;H*j~RwW+e>k9HyN zwFzF837KN?f6*TrVP+NcI21N?U)&g`M^@;lB%T&#HG5_V9~m*(*AEB#Z7p5>mJ}qV zy=tr|kWYZ*i_QhyGQ*wxFjSJ-o9E6uz~d-r{Bt=^q1pRcqu&YvtU|+gOBE8gNp@D^ z{Vn|njaJ?ZPl-|Kc+CcPg-*Y|Wnmc=SegYuaOzZKza~;)9wCzmCi(tewFu2{=86~y zW?UR4>;3Z#Z*57j4jthL*%4Ok9H&>SS0}`w?VwNtVAXA`yL`vh^bHKaj1k2Q~=s+nomVUUL~O_%l% zX0o2H7;`c0^*YBe)NB}`fBE&<&u@F#cFSWmvEzmt3ax{S&*oEDz-*2_!R>6# z@pkvdThAba#%BWo*K&<8?~T`_dd|4Tfk+s<;O~P5=uE?xB(;&)1JtiDUTsq&8odXY z7G-d|C1lx^8aWuQrj#asWy>m_4B56M> zx|io1o|~%HMi!vLC|XfFg54!M0W)#YtSSp#mKTHCipZqhM*HN z>GXfNZp|vs-V|bHj{eWyDUFfvE^YU`lta<8S6W4sSus!nA)X=O-!J^z4*xIv13Ns4 zx?_VFRnAcmT!vh!KS1p29ah*vT(&+A}FMnXsWLB4|UXe+6uX16*d z7BQ#6JjD3EqpFK(_nX9)4D4$~56f5)aoqFyDqw8$Wk@yMsJ;OnsmwjKr?oJH!-?Te z;)xmJ)ir2)GvwsUcSRDGew|3=u$!1$^Yzm6pE&}P7FVe{OQUyt9zBg*)jgTRm{JieVBx&2SvU>op`raY>T>8jWy!KS$~^n#&ZDy z;*9yI$1KiTwZnj25ljnhE8VCV{91HgJ6W2ok+VeqMVSvUi2gC1?q)UOBR+faaGhF|+0J;7&U1pLaG z6NRU`hcgjev#sFy?i>@OK)br6efJ~0uj!$@GD}d$kdJQl4lin6ndG^)pJZr^&NYqC z<4ZL8zD`iG4dQ(K&8%JJr0e{Al$L-!=_Ij+WEb>~yVUTuH@yA7K8AB1=KMkKwi9<6ux>IGn*U$X@<_=~b9 z0sSiniUtce_S5H{8ZRMc9P*`i_*GTI*hr%0z^Z&)%;*rDk{5bbc>Hq@1%vjV+82#) zxIB&Bb=^O`{6r51d|xE&r6vN_g#h7qHg_et05Uk%K+ftnk_#jjx0H))@a; zc6Y=4KU0yRubBYY@L#rQyu0_oQxVWdb{LE>7XPPxnz|n??E9z!E7ONN!qm?cfm%%G z&w25S-}fT%dcIL&O|Ka&(7_0LgDvY&crK}um#n3rJQ&+xO>qhs?2GHuVsm;uZnOf^~yPADpC|aNRez}lCuO_jDz{F0$ zUV8a!kxb)%&`Cm(P77^aZkw;BSY=vYAGnA%{>RYRSLzZAb zrHAWB`*Ko&^{>=awvef)5cCrw>ZoWwt$(QeS!t8cidOnD9L;JwE=`NgJYM|k|D34v zexHfUUY#TQVrC9$7aUtr)W0Tv4E-MqR?y_FctK3(U>Hs6wA_mgbk)P~x+NOXACp=W zif!rP$Nru`n^={;KFu3kz)&D@1pGP_D{E4R6)C->XT$ z?jrHG%b%Ldsc#IEkB{fvPqSIRI^is=_J4j=*>Vv88=mf1+TcRi*tZ+7&(l_5vQS9m zWLNLIJqIo3mRp?fcUgA;*cAX@U)Yad>4bMfkCyTS6-rbxZ@63w0^PxVcT?&IzWMnP zIp3RNE9ITfz^#!{uS_Liyha_c&eS&&a6$`^@>t{j=+!%O@cjH$2awjiys)8>kRi&N zI+yg9q!B(bM;O7jjz>aM+ZgewA$Q>Ww?t#(O6YFQ)yck)+AWykNenq}k!27>rImuaXhoN*+kz?OsMA zOFKf%;Z(hw_(u_rY6K;e<2mk4hUe=f*a7etpeO5HcN4h4-aMoKv_4({Z37VYQ8U{L z&evXv2At}DrPcN{k;i<_h$M;^AbHq32b5mu2OVL3r5X-q~hJo>% zXsbIZn^0m@7Bw6pA5EOr$MO%@80I{mmV;~hPy{f+A<+YsvDORZibK76%x#!o>188s zwn`lR%yUm-{Uk5@<^W&78wR<%17AX?hTz%LR~JBGJ8*CXDg+?Vse`Vd)JU5B2g|da zSIGrz4@b*n7m~0iJdE&}VYsFLVeY4N0Xh@%P?BGvw)9AUf+xeM@xSx@3pxh^C*ClZ zq9;F0ch7N`iF`@h>cy{QK`AO#{(_>EQXnyoX{o-65X+f6NYsw^CETcp@i#_aCH^fk zb?sukqnPI;O$iHzgteU8^Ioh5Y2oD0(xk?M@iU|edaRk6!sD1*pI=6BG`mogK5ZNT ze~#R9f4h%&zh>bjYZRN+sc2T*-|}26#8(R_nFgw0<;G*zNO)pyoe#dnOMW}?P}lX^ zDZ0uZYF4p7$leC!e`6?Cq*czJW6?;t4!6`p4@AT>a9QFnxOcCEP0y~J{}dXw`KDc- z;plq}3L|0q?M#}Mk@1-?oXjr5!!jSPn5q_=D(COGUU*q%0alwj+gX+q0QQjTR`r>W zf(HK94ADQeop>z#kCHr05Q^I*c=n@lxPK4CKI_k~Z!mfI>5+6|*hd5aIlR7RN8dTi zkzi#hy^LsC6t9s->Y!DQd(=mb(s&i)*2kajr{SWy*^HdcE;*k~a*Sr4N5Czp=A<=j zHCCp%90V&ZW%`Z16=6u1r=Ud#H}xAwZ%Fz7f%hc+%n0a*l|M7%Cl>kzQE2#0Bca&F zRA@Lnk9YkkOrn>0HMLim2w!HPu!p0G<8zS*$L^)7cv7sCc#iI~zJ#Bw0)@jvd1S;6 zLp*w)ab>8#8gO)p9c0Zd&-xdcUJv#~5n3+>QmcW)2yuBGCq=nSfz>4hj%0xgecQs1aV&;QmntC7}Yx9_fQV_fWI@$`W9q z&ma@a9plv95n7jMTC4W23-~4{u*5`Jefj~svwLS}e|CB|eJ7M*bN7B-b#3i&Vj^Q@ z#j1t^CCb6yY+S%fFZY5!CMMRUSiDg`9#OVYjC-Ggw_?JNLT*5=d765;;tc}5Q308E zeAX{JvG|g0dSeH?6WveG2so!=+un>j@fEz$^i1Y#jJ*A(861^yFkr%9*YsTd)0fs^ z(q);zUo4WcV^>zy1P#k^<(fJsHdrUcKb(kZOZNPE7orSZ2WMH>xauQrr_BT~@qb=+ zWI6X&3hp=(laMV*2Ri&)&3{|--+l9c*%0y+BaqfpWHwZCIb8k{NBLYiyX?1w#yqQM z8V0%LOHs`x>B)_$nTcB=Z>M-}|2dO*jz^lfp4;I)?gh{nOYbM=oabzmJPKAs47d(% zV6R7+3LCG-+!b@vS*r(fY5{$Qu_rw8u#+B?FB%Ie91C4-PpmC%8L2B9tFZlBp*xTl zz<$>SzjRdQNR-J>{2KNGhz2bJcVYI_fOO3(Vw#OE#*N`Kny;!ZQ?Cs$>_(qzR)PP# zZ0m(Q>MX~UU|e8#QY?X0fd<^-RsPUasKHEaoQADY#!IVj+Ue|sDZGt??6gcIW5W>d zbXV1q{juAHeU+0>3b!D^h`PuJRRq?r25-2)ZP4N|8&l~u<^@n23}eml22alGX{?Or zcG^o@Qi&}i`Dnug*nbde0e#_12{HdB^S80^ws_S|ztm1%1uV451Bt)CP|DEZVEEg( ze_W87A&I6|D`$i9O|;I7ULagiFlAYVp)46CB_!srl~%g4*x(aJ&pa#FDb{OwSs?s zv;zIol`SFvM-i0h!mC7ILY1PHv>yS{>Fm`}hm`-6M#%@n3b_g8q*!cFzPU1X0LP7x;HVwQZ)f@Y%Fv zKezsw}0x3w5zviwVKO_Gfd@&mLyad};OqCcH}mJDj? zjr*m^RetGDNm=Bne`LZ78+-2^)nvE!2`g1WKsr*D-lQl9f)aX1iZtm( znqX+sq(qP|5IP7#kfKxp={58!RiyVWC4o=^gd`Ju&N=hEGjry9=bLYRf6SVH?!_Ye z-utS*>)PesS5XnQzcW|LJT^>i!1Vl1$>zl$m*z8I){`elrD==&9!Yy*tVhN4$LTi^ zMuLw_YOh|i)v(d!OM}kisvlFRhoL2l3P>;KG3%#1b%1Vr1r1doh{PbGQomZOD<*yH z4~W%4c}W`3;s)=Fggvlpphm29Tu1bwi(m^0X8_)#E7Tl%6&+2 zOfdZQJ?Bq{d`RdKN+k%Zt{j$#NYK|3CpCDXv)T2McJK*@JGq{%9_@dRQJb=&FPXK7c*1xZXnAqF)2$>1j?wC=9XcpVsv$JDxqB* zzY2l+KMcbLo%9U1)^F45_bZ(%k82=V3d~5vce6iUs4L_g-?B^aK%Qpw6I3SK1v~IU zebO>t7#>)(tSkQ@U*i;~8V_{RuBARf;md-z%hByd!nu3@ zY<(3;lI9@um>l-LeQhA9g-NGs89yWP5;Lg8F^x}zd(T(pjt5lUoY)}R`nIWR_?vz- zcplq#^^jGHN3oea_2}Lf=*1}r3GypYv5k845DBREO}_oxQg&Il^TtM0Y`;t6Iz|Ns z`t!gIboK55PclXnL8RZW?mqua7S!Ds53a9YcxOk`z<@2yhRcHaVkeW zwHM(J3Uyr>_?>Qw73JfaO%zJpN~tEu(AP`-eCyQ&Q@FYbo)$mfpbnAv4w(Yi{b25t zWINvXj3?or6H{fA)CV3U%f-I!)KSyOQRA|^GmxX)VqJJOOyd6?=Kl)q|4d86)AR`) zT~}1N)BTZBx2;&&QdjAXp3?fnvtb?=aRozK!Bml@8?*+TTNDb`c&W3&dvs+A`l9-( z0>;cA&Xo%b*)xpR*DuTNM^BblKP$WOLqcAOw*NFDxC;B#g0>|O2O;+HQ_*b!9QyhR zd!QMt$N77TE~G5a=M-m|gD)-`h%^0vDzk^*=x5o-02aUYhO5__;GJ7GAOE5{2Vk;$oapde%kAc%( z#mELPuW7Kn_q*={h>S`(3DhH zVK)$IyAU&MvNLIsO8(?+)qr-wXy6?avJW5ZuabbIs~^uUavH+7Y3(^88t3r z{QG}0;H#i?e~L~ItXg*O@1vPv*Z&H&hbMAgWCbL5}sTKjmNZt=w&!avtI&b?a5ATTm)9=m`A&8+o5+S&E_Y`z zGnk2XMEk|Zw>K42wKEJiZG#{sJw$)hgG(iz)_!v0i`vk75v|$ z+PrseRVS|_c=lT|6e&gLks*vsxCnhE88$wd&o4zr^%AdS)JCkMKEXvp*?VrGV~dZ= zfWCn|(E{B($+w71)bCaYjMqGfLM?p8jW~!ihlWeFnaT}K4K+d60X;?bAmPHwVBB>x zS3l_m$oE_26mX^ioZ!DWqa#;Z=_jUT|BP1zdc_>8JGLMwNv;J^br>u9(B1c=BZjS6 zRXu#sITlDJA>{PVnnhv@vJXLzq;fyEA+Spyw7jA=bB=9pRGrY;kI!QK8b=+paxERj z)__g8ddSfocoh_h656GsEE}*XR}VXsk)E8fMRb~2Ti?}WE72nv1!=&3L_u1IkN;!i zao{vn(y64LdUU);`=9uE8!+%!9HubM%wT-36W)M5)Yt}XD@Km5eHYKF4X5P$twLGR zMV*`9MMu=ln=Y`$<~-{t*R6i4ck`Z&QLr3uzU;5TQ{kD1S81Np@1*Y=QHfAaDZMs= zO++uX2{S2oR9Y*LC(&=gdBonwfAuZ+ zuf7{F_edij6Yz6PLAgK!e`z^$qBxZ|gHN`@^>DFji!DyuFsWM zBd0v#CrC~C%UCuLD&kRP^fp7Qm5HToyz$IYezbUl1Apb|I72KJacNn0&howAPZERI zPx;a4UPbA@eDE_#=Ok(6=Ap5g;nk2`e}??aJ^N263>a!H4r-n?r@kaq4qlJ^QF7bZ z@L!Iv6K1^|W_;vZ$|)d1!l`0o5!UwoADFOy5y5}URQSw<$3o*fUY@Ln;-!Qx zwz}NTuRg8E7K3Jw*@aSuBbaqX`%B9|f!YULUbebP@XY~GmL{{!u4m)+hh~@wyq9$R zPa810NyeO4iyyeewalRC4M9eUzGbELq8 z`tJl8yOy=Y5_|#uaM0)e3a$cO$FMwjq!=%?RaysE9khp+a%dkn=ki1eoDdn&@iI4{ zR~SPwSzB>a7X6Qt&pl9Uft{H>tL?@Fky>fyKYo)o#@1@d|>pWk|^CLB+Oj* zo-A2t*bIr$>?Vf9n#c0!QstIfQc-hYgC5AgA$(vOgn1bTr=fzVM|vD5N?t|728^5> zu6(K?q5f-}8=Cn|E^~Ull27JH?s|2+2YN;F!1NUQ{b*vD6L(T};|5nH<5LtQBjiUa zx_s}6xMY+zm*Qi2wNm8~%-1h>tL(4>(%NLtR-fP0jnknj8LPq;@%6dPU*AMVd{XS%Fn z>gRyp>;_ZEnrRwVQ6nYgEjz4!>y*f|zTO2}@RRV%*`_7TX&vxr=#keP{J_6%IfQiE zRbX=j&l6jGgL8~aF7|SbY%^pfztQ=wn_rESj-%M7xpT0xOnE z!m2#y12T2_;iQ*-r@#inK_i2KKMmka3x8n4lzZcA{1uXN0^2O)=;8O<9ZGi#!;J<` z!1tYO3eB*_CBA8tbGMZw!~Q^)JN_w2qpvG&OWIsTyjkxX$VH7>VdJ9Lq`N6*I-IwI z?@wwG#Z+N5+U>7#aA#MlcqPRHZF@E36kw8n(XQ)}BIUDtSAd{4|E?uOXwfue#CS@V ztUP&_&2+p=rvX!GcqqhCdk;tcpGoa1(H`xa!$qoqp2oOWz6EC3=|t{u9DOy>K6fg~ zbVHx_os5jMVEmY=$;ls|-IjR!!x7u(#uBvQ=Ht87c`iC!atWC%Nt5TwQ8fIt$d6^r*Fu!-P{m zLghaS6Ga)WgN&r2vWdvi;3_vRp3!GWCa$yTiI821WAC&*Swta0l%_H1cEzbd*({&W>t8p%4(}{F`YV^+(f)OI%5_ zrKXxm;{~nrGh5^qV5z{#XK#A!=>eG7tg1V6#*}yE*gvsXi}5DM5Hwwu3d(y){)P&2 zg9K1@DN4z{ho3lK1~qC)Bw@XAj`y1FGgOZD6^H1IBq~==nm@JspUX}gxLn{*RB~;I z&`F|hqHVz5tFjb`r6n_<+rk*ZKpX$@k>Y65v*rk2f{Xv#z7B<>Ow!UKXD>NPrulE=7zo_aV1@ zd?*8;3(h9BXXb-YIvkd5=CX}1!(8%&-tdlT^yHQB{?zoq4N)Lm3}}vK^XDkM{kJ; zQG>QoBF3()r${YO0saPp*w)bWOD$R@mUU}0XW!WIGvR!+K=tO9{%`8oBe_7GKuQ%q77|w7n`6%S0rV=(P_9{t&YV}qyBl$|^)(F*UA#bk<;6aPX7%rr zo`ZHL2kTSjYP5#sY3OS)G$}HY0KfWftC*sPDN)6Y8}&NYn@`fi;70r zp`cKbZ{zP8FcE3`rbKui!Z%aY+x@Te?}DOHESKOnGMC%7)zoYA^N&5vQ7Nyy@ zNV^B(h4bU3kE`a>MXAT0#rSB{m_*M-Dbe#)Q`4T~BxM9^LH2%b4%jnP^mD3XA0WL5 zE;!&oW1=COu3TGeY-$AwK@8Xu%?uCB&3$b+iEZy#TcLuV<8Fr7>mR;vi!kV_%^%*j zy*b!W@0UfX_svkJ6LErx%4GVg!F-lNJvQBjjw+*dKRtAvINAJncp!~FqnLmX{$E5x zCkNNi$^$^9^C}6Oqq=||HQvwJm%ksQK|7Fve7>bmP-Cbv2W9r+NE^lygeqf_2%-X1 zrx*d(G9Cd};b`eIwijCTH7=1b@2%9}lwRZi;7h@T8QsD18At_-u(ECkmj&>}r z^c{i9t%I=mLurL?5K?mpB=;MdTexB#%YuvF7fohk}BH`(P*u0^PhrRc|kA^T%7+cu*J6=M17Ptcs z?xj7Hq7O1?o)V67uk%A=aJOC8i>~#ofkI3f*RBifN_thW%AP_QgI?}IWYQ0OuWj0a zCQJ1%*uDcuI9eY5$dc~8U!^HfYGHZH{u~Cyc7kQx;c<+eY)M8vsG$cMb&29L;y5jw zOmGKY9_mlkzILAaGSRBPHL^C;_u;}enI758IJCv)yTYi)>xQo;e-pbqf(4wRgqx1_ zeD*3Wtvsauc^5$M_ky~`x6VErDMpQH76JWUvnA9=%D327$fYku{HTZw0ie8V^kL*n z{+HLQ2Rjji!f^X*LLq7-YrV0a8bWuVpeGmGc`zR+iiPJV)Di?xV^?;-@IV4q4dv13 z?yZOEU(8ukU(M)Mv5GmyOS2^LY?GHa!AyLXgNchY<9|Z}H%-dx*_V1{P-8U)fs@7=Y#Q&^1X?ihnhjul(wz4l~Uvc6}DBwAv^w<~20R2jlW3b((M%HDi_ zH(3~DRo%22EDGymnQh2B&<1FC;c;nEx_tu0c&h-RRI8=>mzAa2J!Huugs(b6e1jti zqxBKU>I6ppH_r`oLiu!(Y2V`hN!JxDruRM?I6#7H82w!yH&R=OWW4e#oiVK!!Bk&l zbq%)(+3AdL6OXHs@i+3747VJN@4_;6U6BR7Hzbx`;@2UwK{tf$E$-R`C)x*LDnboM zd!&eHO$)9F&EXX|#-k(^jKp`!C!$?QrscIJp|K0QYE0;UH+CW?H}g9lmu7Ho=_sk9 zV8vbX{3`;(#NYn#^;xkqYMQCq%mrT)dJ1^AIh5Iu6bBd=cUERGyD2kiw!PrK^%Q2Q z{gjQ>Co*&rx%^(LfhXjZx|KO>7d~qAZd~9!XsUkWh|0YlCUFGPsdYw@tHo-*h-FBl|%d= z+W7ZOhG2ux_kFqzCalXm%S?neE>3qCtCc<|0mmcQ8a#y=V6A9xy4ggj6YS)m@NT2m z<76IX#{^Mb2}oaAy;e=7bvz5nkR zrhv{hYMJ!CaC6^+%*URog%4b2tD~ep58nHBpGckao2;HM`F@wz)Y9*YDV|G~#AWOy z<~#AC<>t@0$6r<4)!>H5YuUch!wTKppTA&zLx!`FX#LB z>i(bE^uOheXk%*0x7R$dbDx)b$pia!s>poaV^A=wk?A-0;gfds*Il>>{`>UAci$_2 z_b}B5lE6=>AkR`-_D3954uWj)yQR0^waj1e(yzqwG)mJz&)1>5B6WA^43ZVH{4oWf zCT9^=*@Y*~u+U4UhM`9AbTp&?OupxCu)cmctLOJVJ2Mc`9Zibeb;;5`kR43z>`N8$>J$v zbK6fhes9%dRcsEi3Wb3Q$Yf3n7P{Hbfbdhhj;?++tZO@AW+QdeEXFvJ_mEI;Q|$l; z^7<*E);InaLWzLRb+flOx#izHo;3HKv4cf&#JL>}NkE#8hNTxQ(r?I>7j}w@t{x0$ zeE{kmFeSa0D?zY%oZg-~n#fiyA3o^?QUtz*2+<0Zz#F!*B^y^qwo!sR+}8I-*gpup z3NX@p1M6V|dekjNxklFa!+5f`Yv*kQgcUKwY;Pl*V6)D05*?vUeBb;&q<#wLzfIVZ zg{`PUp_Z_59FOQcadW8#`rTjH+vkt*)HLn#T_Hih9;1izbeXO&Z}gfF?DyAfckt8G zbQEsYa>MWy^!uEB=4+A9woG;FR72C=5N!xdIga@^E8BU!|4IXWMSM-{T;ZBBY*c~V z>quAxy2(fhS*v^K(5O<8*Zn~lx@QrvLWuljWNEwV%+&n+_0H)6$TDb2jWxVwEZ+D} zeC~-!GXBfdsohm>P?Ag-+jW&p7z%1ce^M3Tj%@R&9XRAKT6KNqtGJ? zk^Uc&Is(XR4#HY<$KWX0g4KvecjM~A7=sn7zCqgphBkRM%xZ2$thHX1V`Sdn0BLukgFJ?uQg{&|PAxk>ofU{)|3DzKOCSrHc zp0@wJxb;;~|F5Z~@U*I_kH)|my9JW6F`*Xe*+6CCRhx}6)}Nkz z`fwO@bO$=vhZrR}h+Q;u+8oNKV_aH~;PfxB9i$Eynup z)S=&gXnv=pJml~l#r)aLAZ8cqy|`HvO$_nDj%D=b5g7eVlJ(%U$#&t*t?Hx!oNSw2 zA`v!-uV8(L+~$Cg!)q6#l_cIyFML^wc+j`EV8&C-h6p{ma}3#2+;Ojr5qA6p_EHNuxnI{O@WKl}1u}FEp<1n9i%5Nucbf>Os${f@Zgr2mY57K(!Dn;1P-1(plAD((I_qoJKZpv?j~Qm z?j^=Ln%l4&=3Ylg!j|Xz>B76(;f98of`53>A~Boh;o9}(nZs*C&u#}ZH(jj$&3LW6 zCV!m#4H^Fhg-Rc$e8)!vDf~g?&sw&C(l+c}+^P~+KHk>Prscl%$%l};diYIjrNY{d zZ#g8+;B35Atofc3}_=515 zKYcF@yjx~cy9(aTRi?ft<<${)yHLX^B62vwE4(n>@d^oZI2rD0J#t)VtjROKN4K$X zx5q{zaeiL;gj<11eWgf&}t>YoN8KsM{tKtx2+;eKA_Tp)Nsi;=RxbUvU;YavPd z=|(EBp&I2j5TSdc^pcw0f!zD(tt*tCa6u&T)oY&y`ts zu<*1&DLAF_$X3tee}xZfRjHS1Iucp>hmb(*s6%p%BkSkfY}AVsipH5 zCvA6oNXpW-c#OOfzGgxIA2rIXHMyGiu#3Eaz;gh6Rp3z6yV;bQ%^obZckP($cQ&&` zqC&XEK-PqL5Hxl!DD!^%$q3j`I?D@YS6a6PgsKqx+V(gdygW0IunxPFmbA#LWO}># z`&AtJ*>^;Qt%MWnNv_4Cyc>lAp zgu6@)?fB2!hYqOJ>l9UfeDa;WyQdS1na-FHidvd#=w$`xy6WPZ}pgHkNu7H9%U%*u0!rB4Q;ugMPa&KEDzHD*?pB9ZBEZu-h!10cMFCd8x2Af{baW z`_7T{e8LFK>L8#jQEGQyqv3MDLHfcyGmouTDRU}M943CyIq5k_R(6_nu>QkYCx z5EFNBL$7ZG{Q80#ip7|rKyNsI^tTWn7P})-SZWtKo*s;@?L9vE=0<^0nTtRnFJ`s@ zWjk@o*naw3uT(}s7o@{X;o3;aLx#EzlEEVXpAk##zR=H<*MKUI;C-zo5#bvMN{Oba zr7jd1(OyLMjI9n+hX>dzk5^*XT-mIZqkE~oc-#HWUf8&6Q zFhcTPFwfG(r=%YkzSzz=pt9wQ`h2g^HnoVbR?yaQO!RgFTNx;F7Wgu3-eKme-dgKH zsyUA3Ugx85CE;yUntFJJaX)hqx@%Z|ZvNE1LAZ8(-|5M_0gZa2@MP!5Zk0TbIMnYb z;e1sGgHCLAeEak>!CT;Av7U1BgI66Ks`s`=D0Ybvph}oeAm;ect4}1x_8yjy?$c5k za<^vT`AEz5W<)u;bW?dfUUpKxU_6_}Z~5^#5mpfdUkq_5QrKi+nEIZv>FU&>?==>I z(OUvB{#gOch77h(uB}#5JF@Sk03UIyUb^F$y^QO@4`{~iC47cROb^Kez_V3(Qh5-S zst(G+r%m{9C4DpP{qVzgwA*Xn(kk&RZ7|tsXz*(k_4$%;<)x)ZHyKPz&?ct>RzB4s zs%kq=|FE?ShucU|@*k|dKOd=yN#UsLvY+HL z``Wpe@4Xg+P_QqH(%0c94u=f#=F@&1V2MHhmgC-GIZ!EItVG0RL*O||ftPw4?4^Vn z4{u!%lLzf-z`(kuJ^O>AXF06VAulr)TXgXDU8C#O@96ULbDrF&^gKt&Y`}-5;cbeM zEz{XgDDkA_r*r7A*{1-{gBP%Bi?8l_4xik^cUj`ftt^R<=UWg@CSX0~ARLMfs_P_| zJ|GzR3JJ>ad7dt68}2;yEo;tcD{Do2{}=Z1sH{<;QI2F|3vlwYDBu&3(_Zz@VHmEW z@^x;g=H2f5#5>p_Fp_G=r>3Ja{mqj*c9k&K$!_^3I@n4C+iEiJW}Gx^xo5?(Kw>F? zTIGJ72a`*Eu>Ykc#{#{jO|Hc1^Jl~?Zz`HjXPw_sZop4SHM4U#6dlJSLtob|OqNBO z^RsmiQ``2&Y+g!x&Hh{nYFg?xK6a7HHo~Akk%cDaO;M{`X^z=kA?PJ5w3MJR*?RwW zo-xY`N%ezy-qL+0>x_qR0Am%=M1lDs^ovxhR+))HJ*x!&p@2Lvz$R@5U{< z+i_AKZDrks^}f#mPmeyPl2Wl|?*etg>rUA(duy>EPt12FMX7p9G(1G(+senrUG!Tm zpKUq+D!!d6Y(B-;98ZzXnx4t54??vf!xvf6FN|y#5R&vwWcC_itpb3~C`q=s;is?1 z0&dC>`v$pu{;lu>a+${eI78`)`*=ii@%JH;!L@=!nFlIZq{QYRahmTl`SF|mhVNdH zt&nJPOd?TO>J7lqQxulM8Z=9|dX|K;Rk|?q>G{1dL!6gY$&dV)R?)aF{3OT6qmIMi z4Q*LtH}H0~I`YhxBAB@60z$;r^ixIf)-Zg@$*8WsXF8VHqjBju>Qi?TtM>+d^N{#c zL`BrWewD~!NXNUy`ZT(scM0@HD7K+yw)Y-YckO@HIaTH69c}$?er%FbGyAHfzI)ru zB`!LO&N6VpOr)@>&Njmj)>Ts`N74-b; zGoL`B>_J$-E2Qm0bn}{8^)^7{?wQ1`8$x&x77u0ZeIvDVXLUB$k&b-!(u_pe)35u^ zOHAUkXvPvoX|{T8Uy%c5n#|%0EI#wl;rW(j(3lea%ERrY-aE&GD?zilPZQ*5 zIfn$IdOtId9!geUNY-lH%UlL|iby^TLPP+^yTHCBJGBDrETvZ81}tGMH=KPXCtjuD zzAgX&u}#N6T5ZvuzfS7v(=7Z3U$<=Z0KouQI;TQl#?OoFeS52AY4VGPQP_MKSnGjP zFwux@{qlH;U)Ym<68CAjYK=5k(6>gIHTb}eRPff|ww~oC@ zK=D47DJ*zkh9Uj;Xb>0Y*bU)0>iGz^pqS&iLvkSmM#14anDy!6SSn=jeoM0R98ifh zzWRJ{;WpR085-$o3kyt4`N6V~wN{5>Bs{bug;} zxKBuF=G4;#=8ZAjelf^m?@iIT(>SN|$g+2tOlBC-`^AwSfl7L7<8fB{0*Gz#RsfKf z_-PdugBqH1mQ*&ti|##fAD3k=e4|b6Hd4$rq%36!c9>czW_l&TnS-)(v^o~iTy0n& z<0Yg|;0(}FiN|XyaDmWE0q}qwYi0rc&>MMSWs3E9Ww-n;(=IG8QxHvr$~Ub6J#a`^ zBO){j^%>eK#*NwQg%j|6nt(ur%TiC~Hm8EHfjdsgAEYrM26{)C{jP^TW^VnzE{6}8 zZf*OJ!%sLjyw_8v>KDHvnJg*Je5-egrDqd9P7g(Ti_Ye+HO^z&?!qR1Ml7Q@HR=Z0 zYJKLgz$%?LEoet#;g4^`a(pB%Q;k`R1uyRyj{m$fJCtU|jGv;>Fp>b1b_L5rUt3SH z?rT$*@+X~cB{@MFkQGczA*6!ahRSnQ3^Lzl5Uy|#qxaj--Z9?GrnWVwzR(vF6CxOi zi<0>iSpk%LHdb2~+hfTGHML5I4porQ*WKM%WveI48)-`i z8ygHU#BJwY*v*L{?*;$SUejuhY9@MkuKZ~y@!Zd%GStBS_akp!VfQER9%R1Ddoaux z4W2j{zK+WytY#?^>GuJo0s$)EtjLAajK*3=?QP>CpQQpH46cy3CUG5aEOF=om-nha z{YF^ajMMwmmrlnsXF*EApX*3c6acIuq$Q_D%IBsN8lLF#5zC7un@6Zi&@fs!Bgb>Os8_x>$`Lt0H-Dob&Xq4l=GyD01JWN0&))Ken z`|d)x8@o>b>n!Xx2!KV224UZ|)7Rr_#>}&L$l|WD$tY>K{(i)VEthTSH`rRv?CI&( ztaqqSE9mS?pOrBBWYbMcDXQM1g}1#=(*vfa%_Wl;UHjm>^9EC^Etp>tB8&5rUQai5 z*mx$Oo(I_-AGqypn*CgldmqVz1ZloJ_s{y>dclaU%<`7?Qw04WfPupfH!&^RZ|-Y> zew6e-KXl`sEfJUUhnrUyt+=w4bZOg+!t^)}+|KVr`S1t6zeU~Px29aalFnzu_&beqRL#Z~TJ37bB-t{D`HV1Chpuo0KC_2@M)G9NkzGl+Jucr%ro15#}d1n!-^?vWy&`13BV`OxK1m*Ok;vpf_qy zV@YEWDg2wV8h7IyPSNU;!^myWVcc!C2kN|uUo7OJxW&W84Daa}D9PR7ON>m>;WYS` zqnLzf3Gw!?2i;mCzJu&z5g7~i_HPR`4_2cRqYT0Oh`zDMASbP&8bHVU`9{@lQ{zQzl<`d^y$up|F)qvCVt$eV)da=TQ1&7ZLavO&a#;gfLc4rbc0>6D{e}=K zt$w4N;^>eEdYqI3pKl0IbQ@ONj`q*_c6xbzuvZHcb8NBfURi>u3Ko%Up>?MLpz`_q|&$-#p#4 z3Mh?jdKSNjo3y!0%zH=}l8q=|KTZm86lf=#M5Rc(S-MmzkXv$a)_o0S7q?NWb&Osh zEDq=89cTpiOpEZ^bh(_|LP~!6D|f92|k^pVNbd{Mzn5xcpGw;0$c+ta-Ik zhf2GE4n`d(Zl4u0WGGo4LoDKc;U2x6eBp_C7`Zf=>MA4Yxp# zv>Q4=nzDQ@v*z5J%8Ui;1fixmrSdOs#U22gfLp-&-$MJ>o(Dna-aZU4n;SL{yZ_6g z#|p}+3~hJq&IW2J_0pIwUVGV8P=6$d5$I!?<3>?8>a(sy29ez zoERFlE}Vhz8|mcoos;Mr=;|m(bJ}pxsHF(-jwJ^W78n1w@^PxD5ayQ9L>+s6!mmqk zUiucBcfH+knle{7>n0;!H)y#X)QGz?KD6#T^91~*8>d0JVwH>kF-yl@k{gk$bhD!_ zLv+f$JW*#K>S~SSM5ANCEdK#xwT4%Ehkw7H!&w)JQRdHc>qnTyEX*=1dg~{UWR?rQ z<>)^ubkdPp_Y;5(F)BIpzDb=Pf7;=g7AJji`xc|k)J;xa3|4TqAahh`s3@~@&HNZo zet$gNF%44<5w?7UJ*%PyuEagp`(v+M{|ol2T5Kj4^<`b)kLOT+2H#(J`>9>VyXQC0 zN*+0Po%_NIZB9i1F}l*-QCP}m^b^s@j0&aFCAPo_v+r1Yg?mqX1(If?k=KOGqI31|c=+Z`^rtCn@$F28e@hJ@vQJW~0CSOi#Y0 zM$95TPWjLY8t##cq!$vtEA$vLdvo>CDnecEXl?thNaj+$voCrhwyd9NZ(_l;Cwd z*@z6bxM}6l@vcal!kp$$6nz=%qFdl|3r>8dvE?g3im?~x&%h;Q#kK#f)&7mE{{d(P z=gLe1AilG3eLURR{Kvhv>;&g*Y_Y*nFHK}g+@tc57h{epj&7g87UM2YJJ3AU9Evj- z>Kcyqv)W3mweDQNeZGs} z{}xXfI58*5?7#u|$jxN&=#oeRc&T`4u_84^#nwd8b7$_@v^d0ZcFD5ja*7^emzdrU z<&WD?Oa2641!R{`%f03#!h6sC;L>^hVNirJ??^}6qx)~})-AK#D{QU+r>kbfuYskJ zfMac$TD=~8TucbW6c{bkNX$q1e4_hiS$^P7e`zbqDvR;CA=64XM;WcXcHPWkG;S0{ zMr&fy)wXs$XIRni^UcTIqa|1!2{LL*OhqT$*XP4U5LPijQ;NC-_4_>x*5m^J)^slP zEDrG%(o7ahyjPvo6drf1h!tfBv12I+T4un=Q;QXjNDxV%y3dg8Ym>Ts44e*TpomAX z-$}2h)4~Cjje&ssSn`&TPRf4>W6u$^{}V8K^572XYi` zIHT7E;=`0bliPvmqywb(J*$ma7Ssi5+S3nT198hg$4Q6p;-_&HSaFLsD(8Jrxj?5U zcgb*D3sobx*JHDuH?hDBJBEvrg-?!ptnm1>T9fh!PKXi+Y8)m;I6zRz7~(#(C%L+B zXb;2*(Ywg-HHb!96G5`-CO|5zx;D{!r~)Sy0g6yl_Z4B4_9;kvLaTq41Tzh{u&0KU*a|7Iy$;V0OyW`#F@A_|x>56UA(41Lwnnic4xPoxs9??<@@s`%X8etzDAU~DJaC#_J zq)$p_j=hIO3<#9hdj*}8te-Erb)LXvH4Sq{uTv{7`J%lRxl-<|jDOW;n_j(zF%WJ( z#=CfvZWbEQhb5OeyNyOa|DxFrqn);k0VRQ-yq*>F*%R%pkCm9|+W$T%1nhqFI@cI( zK$-cPODH1|Dr-Q8%c*XB5OogCA!6f+{dl0>;5fmks`)|GtR8Ay?j57>Dx0Jk9*-r> z`_j-U9MsRmcClOM3XAOJTb4fuZ+{m$bMI-Hf0k%u#f@tQ&ENP8){?ZXzx)aU4KJB2 zM^u8~7>7K$OT4OWWcTtK<0JeYXt&D|?5ke)GBcU%#p@w8{Vaf1Xbw4d)|7&9-W#Fc zQ)k;x$RCCmy~=+W;Ph)su+;n2`)5LB#aW@WA^K)%ZM`AEf!ZP2<>rpvbY*Q{(<(O^ zs*PX&O7S~+Ql|W6)@fwHdzId@mD=n(mh0pJ0MKyub)!6`*$fltOds=**@36^0xpr1 z5-KJuTSC|WG{RcoJ0aZxi_I?XOgZ{KbAo%7b8Xk^GmB#jPC(BG>yp$V(a3SFA8hLJ zAnv+_LkXm0E$v?Yit9Y2Lfj;9r2wt;{eAB#;DdR;ppcKr1nz_@f>WdI5s%&nFqGVyWhz2LonFT zewkxlDDYh%<9mWk*YCk|4kKCZv8?PPP;3sVuT95i;{DF806qPW3~xAV-&i;d{Ze>E zIr@#4=aiu@rfO7Ztn~O|2YXa+&e$ms;jl6tY+&?ytF;5jM_s|fQzJ2yaX)J35QEsK%?xI-hg|LS|8uZ*9Kp zGL6U01N-AzxX)6(`40O-u>BDWUyOs5(B;1>5w=e*Gl!$T&Y80c2=iDM&}d;^y#946 zDSfDLYu?sbZvB@#ezmo|2Y#93onVAK8cH{mnYUM?GEX6L2*W?v%x&Haypc(QYSv!dmO(cJj^ zTqh?gryS4_UIGhTVy1K~zR3cBH%ryoLK~sX0hlhH(%q;)QTH1T7HbN43-~GYZ?!-7 zm#t4#hhXtbX+F8Oas#~(pigO1uV?A^uq>4cX8cQ?+ zq2hPOL8=-7CrGorz+J@%-EKL46POdECJ``Q;IPot>psng_uj32t|S|J3URBZs^KW5 z{+7(%GUX#pOUk5!&5rdB<^DEww!Vx#)TXgzfE6V}I_~;ZJ?ceCZ=M6j3vDoaT#8)D{ zKzNWsEpPQq)1}PNTLiHrQ2{&E=jnKbdmn0FfbL4pha(WU!Z;1F5)asdl=?(4sfUuo z_BXuaa~8I@751nYC>-C*Y-YMb2dNQ#9ei*2-`UB)Dg+7DVPA4p$YrIm)N{Xg&S`pQx@BN z+iozzACPi%O-k4tw*4Gw*{hv)!LOTQ1x4D8PeTEQv)bpr#g;BK+(ig~$_qV}(9_bh zONXHMr?+sMQJ8V}SD@WQ=-J-6VrSEZgq#&8CKsBrOrNtdhGE(%i0AnP~WS_v8RYZy2NgoLeRg_8(BUo?O&1Z zEEUf4&gIbGi)}(i>Fp7RWxwVbOUgR}nKP-imh-dTZ=+H3b~m!N-+}PUKAM%a_oB3-k9&h6c&;PGiH}qB29+3L`gq>qn*2H zD>$5YHxed!CA?$F2#spEj=uCK zKBq%ZzNdIR%@Vi3wA~lepTyHdj5(z6A%N?w-1m~=HoDdJ5|3$G8D~Sc7e5F$Z%-~+ z;kzZ^X9HN8#@spHLd%5Drt{^d&GvGp2;ihNhK>u2UT}h*4SA{Z=F3D=pM{f;zc%V^ z7sBW*Xm;0^am7g8Bj)^FHTC5~o8YacJPtaXvxlpR8p0cM`8U}k*kC-Yhgr)ANB}0_ zXMdQd-Lt^+qqy6m7BMuCuoby6Jv|;(qV^>lkLVfWfl}F+?A+*z)`FcuOCE&-E$dWv zX$lmWY0>VfW=N#)yF+EoooIeU3j*v!mHH)NK+x`(#vqjTzQGc_u4wbJ?3dnPe)8D! z367v^<-=JXs|j&&pK^4nvF<#!HPnXOC$~&Lc2|pw+UXJ>J=F}oJ0-~~fM2A`xwtZP^T5)(3gT2d-`MJA3ek>ulR=Z3*7g-PjKfQDsHt9pg-+Eil*_PBRSRq z&v7N~uhlZZ+Nkk;*$M3XPWOMMK)#v@HQ!PZu+B8h_%EcrcUY5O(=IBabfgz)Q9!Uk zK&rGT#fUT!0i`#kH-XRzO?r_gNG~EP9q9o=N2E6iz4sD&AR);pD4g-OYg867Du)6qXqA^qP1kG4Euz8nC1s%HeQ_@T6&ID1U%CjmT6)i z{nDCe%%SImaFASuzap@9kyn|>H`c#5XDgT?`hm$_W~;QvR?NApc^*+hx5$4LS1R>I zm$!7Ei1@L8a_L>0Y?Nwfs)j=Lb6@66xO(3VqN5q8l(2?4K!w7stcU>3FH+8zF4hw` znPPeg+L>88#K8+f>to`j#%#H(+%u+=0+T?kf%dcVarE{So_#mJ!u@&6;K<+|w-NoV zk%83IThE{9S2K-&KESD^-Fji&BGqo^wpB2NxJ_L7!{&=gPG4^S(Y~jK$iR*xkL?CI)#BZ~mNK4G97;54vR1E^2>55=$mCvg%U5`KSqF zHk_<5{R)5UDskQ|+CGS+m{2t48{fP`-@wQ&ufnp#{`t=udPAR(NQWpgXqkoCpn)@1KuhGB*t$leL=7*4E_9x9xLjVR&wFz za9r{mY4CqM7tX`EMZngP&;5B&<1rUkKr(Id-Hq6)w*~L$c_j0y;z1n!-Fd`7_s-~- zme^TgS%*CsD&T>p3t8N6>C=;6ip#MFPaByAx6cp_>K(UyoYgnKk-3%6d3OJ7k9`wg z`ver@$@^kQ+y~kAmFkfSH%wp~zOHf^a9o7<^yIWS%1%b^5+M*G9bNO4lF6^Uh9;Ul zBkX;P-}P>As3auQ{ye{2;N0`%<5e;6;Orr-U?LT`HSG0QMG5C7(?#u1BhQJDurUmA zXlR-}j(=$)!V_qQ4m*O=uaLm;I6fx{zueQc!n6-DD%5;7K#@s03#W+{Cp?MfC%e(W zUOZP+5z|AuxgzFl9Q$E`9Qw;#&TOCtm@49iUBMBpl2gU#!{^~X`Ax(8{ERORNP#OE zDl?*4!fD?2%x6*;BPe&g0|e8Qhq~2BR&`a)yx78is?L9Wf5&heE($m3cX>RoZ^OGG zq8@r)wnC><6wtjwGS2dt%%4T(!*hWT-I4SojqYF9WTo3JCbI%IYG>X*@YmBOjgArK z3R>ytZZHPwKs`>Q$CGC?_$Fx{Gs~wN$|u+7xb`+|muuZW-rX>jyShTMa*qG`V7f$C z&#BMp44dJMPzzt^MCSb2z0%Y(#_)yNCeuK#V=MurR%ds^iO=(pB_PuWc)9|5VnHQp zY+L0uoe3Oxt4ssuw+w&l#(_Q#o)L~zM;$UH^~oxJ=W8Wejdm*d?gv*clAph!{8|2E zcG&fiIANT2L2dK9f;Yi0^!ohHhW)Eze@gV}X1v5RfB5ZqRUn&oI_dFh0`eWx7!OkH zVh8bLkDB%8Xk5`VrDJOzVF0-lT99tjH0Anu>Fhe%!fhm+Lwc2wi{xCC7^fixz^r~v z4xSW$BAc(XX}alOTT{8Y@_i7#eD2`|-TrHN1^j1*8ye-%ye5zh%wN8tIp>EB%-ASF zM2(K1A0&dCcR23%OZr6Je>Hv=PsmXsc!oyOyZ_QRiHxLAi})m`PhhDLUauo_Zw(}r zIWGionbX6-)e+u2Vkw>JA6ioJY zcxOi?iyK z`>4vu#nF%jn;zlzKM{3`7OHD?GK#()!15iBQ<<^3%q8fjQJ90?M)k!iZ#wtRze!H1 z%$FQvNf7E=KGv)(d75;4Q#ytXssZgV4Yw3=QSZL-;Ma0|0%V0^pLgX1m<$9;4iMAJHNfH z=Whqy%ZY~X##&nvX+s|ktg|F$6T)|ktKPc*ow$ecxC%B*?lG`0={{Xs`~`-&*W&&f zI&Gh!QU>=Ug9befjfT!+JTvg<)D`%ltwBGe?_9aGB!;bqh#Vp^Wv)pclu*02tUJ^x z=)t+{28Zxc3hAR(Jku;HwbsJx#4YPFylQ%i$*_Im4gd1`^^_l_xqpdR9Y+`x1x#t(blbH)+AcDZHwun-zFTHr`YjB}*i z`~30bDaOL@dwwgz$n0gdLBJ@H)w+JT^j&kWDT5Mj(GGW~2^E+4Fmz`=mliKfE zwBU6Fj9XLG@6YcJ(-O^043Ke~pY7G+^ckkA9`fig_5**$Fb9GV-3F1t@h>kXri;xd zumlHUsx5-BBSOl}gu(SW{yH?4B8j9?KGdEC?BK@ z3unm$u7m2uuzALI>*T!BRSlU@ut>cQP^>ZE-y4W$F4J8!^x;5#PW~@2JWGZj7FIo0 z&mtuG(k{ccCQ%GqE}7tm1PHm<^p+Q?41Axx^R0cX?qkf;abfdTmyFViwTHD-)dVT- zy;ou~YWj~TFn}`d@>7Sv)W79S6VcP^`pUHrqkEFC9gku?l=ZXUjlX}G_|xVstNwMB zrs@E0UBc97qF{Ew{9G`b?~QX&>J`7^SW&Mg@jt(J-l!gO2)Mn%Ydm-w_qd&ovA=z4 zP%v{Eq|ISIVJxl5M|j<3qt82?wYfP+?gEL{t1}7em8&*zrhq{!*R*)G5$@Q)yvx?G zJY$0^d#^kWKBI$K_BTH@$ZPY|O_vn>#EJ#j@+Q0C%-<0N-sFJ^TF@sWtXs#oBag$* zXgAJfq$o&tl7{1F*6T7XcGkHQkBE=SfP$C;6>_4Yk`#5iU;B?4A28=y2;-ww#1f1QJrxG|wfOLgVDBJ}n6TPkTKs^u4sDHY{ z&x%eyy4d!sd`vO73F1%m-$(8 zMsz0P&pOI@VoAi9OI1#Gok!x#D!v3aO&a=A1yBjF0K`eBn~*%CbJaYlBTduUI2Wp| zcO26R^QhXKtEF7uFd?!ovwbUkIV%%KCoQih2y!ZDDO9)jJsCTCD0S#^g23QwZiTDy zog?gYd9ilOgVZzC(fPaMb@a7GJTmoCsSj-7tJ0rJwF%$n@(=#X7R+{~y-{9sM!jvW zv~VR6g1gJ{?ipaO(T2W@T+JXzvfP1POykl@qWQp z<3_NdXDiu`aCn2&B8k(QvUsJ3Pt zQh@t_^L0;pxWYtNYxI~{!V)12p}4H*o(2h5@d)msZ`Yp)=7b$O?FJli^3aK_j012_ z1_a;O*IQ9aDly8Vf6}wPQE~hxFE&#B zFk0}1`ai}es;8Z?^?yXlD4_yL%Y@e|eO2}M?=Baf?s%<{pcs~wn#$d$9ihAG+>lNE z6y&}%T)P%u8NHQ+$w9g zQ_;q6*Fc{fo+XUWZWPp#vLo!IElya&H6|G3Y@+W8W|X~JJ;^1U10j+ zlwK3Cx&Ch(S@xc-lg3Id_~7O;A$zddt1AOXI5hRjK&gR+5xp!(8z;*on~)XwNcr3q z3fk4{u%M@OZ)%f5ZFw+E&#|bFe$l@>FZAy#c)VO8?(CbqXwi9{+L*gqOVYf>qRROlJoTiobvC* z#k6*&#%MX@C^$w71oyBZTE%f}c2YO+iApzQ*kw*m{)BP6VNJFlpRO3RPj zUMAqsZb)J?+%wl$`V3`BH<8yXpH=aoCr9*Y@KwC#i`4e+wEoJOeFUNzGu2ay^7)u} zjK!TavSPS=Pl3B3KR`Rfmg$0c<;oQz5ur{Z_TOX_yT;_LtX(7XbSf3O6sVV$kplN& zmQibU-C>oMYB4ATuSFh4zygf&wdiE!gvHK%M`^!&Sa~ZS#bS#l_U{hv?#?v_nnrlA zwRmpt&+h%B(lPo{$%W!%?8)OLML|; z%IV!v>R?$aq34$2aAJr7SP3`Qv#d?l3n3o{t~QGoI>h|Lm#Nmbpl_<_N~)#M=YKR+ zWW?H-4T+^vxNtpYIyV#G{+r|JY$`N{pd2rFvSOI>K3mxU+j4b)ZgwH^3X^Z zceSQP7jJ22R<3j-#D);F683+`vt+(nzap6U*p|p*@{5g%RoGndzT7=)Llf^CS2Q^` zTfRt6)Bq$9brYY78-GpgbvGY!jMn4^*#6neS&e;?<9sh=eJ#H9QvPt&#%3puN2+XsSmBV;=nG!X=N z+nve!4HK@F+H>STkDQKs@B7pC;~uw^7f%ced+e-EKMaFKDy3%_H|7~*)29oO`Nr5g z;=i4K@{I#$wrj#k{5E5bgM2_J`y>)WG!-VBaSGFg#v{Ux&nNFzX6{5+UABdT8cEOQ z#!3zAjImj`wWz*E?~TGn-tOz#xeKWiAe)*hl@2s1#3_!TYb49-zLI;SQkfU%XXn(*M#Wqmu}IR#y8cy^F!BbfVg)Yi|2}H-t^qF5UODgL0|)cc-JpY7^{B8n(pV z=R&5)s|1`-tz}L@*VnCmi9VaICo4`X#RhJ%x+C#8`P5YJmnKKJRJq%OqX(Nbbi3@^ zhpI|eSN%(pqwXaTO0tosdF;gjc5WSnXmFexpKuG+qy!V;aXhZ8s;}NVUA(?-K44NK zLy|OAbc}nL;q<_u`1sC1+T#vxf38!wU6~d})2ULj^k&_proNvX5~=PA|TuYg6Ja=6G8ZS?iY6;`(myNtUw51UNPM!q)r{MO(ic{L%g z>7+we&tAvmTYeMB*U#BT+@--d_u|s;9^hhWi2d%F2D~AVzAAdR`3^N{ywPXUqHpjD zGD&+S*-nSPSP>0_=0!A{E&fj^@Xmf7U_&Ucqi1Mdv>mgq*Ia!-OIy}M2}KlsHd250 z0itkhXXFf;yWV*4z*P8aT&=d*_sQDXrQvdgNbJc1bu*(vafX`->VaxN%@^fJPB|c_?)Ts+2)u1u^|P|Qp1|y1)jLW!1w9> zeJjIg8M+mcfsBubfk(I={(a92*y_U*M0&1q(oxkqM=?U_Y=LwuWhMv8X)lZ#E-ZV)kSf?1R=_vYcvdsv%;eV2-Q)CGa0@7F-+#e#|v?E6CyQ zSRsiHKfIDLdL@Qj-HS-dLx*w+S!j=HXb&`T>0OvT2Dj`=E?iq7ksSs2IJ}LqynA2D z!1K{wnKBK+ymtHNP9d}UrYp^x!}xZuCnr()GO;@G9nz|^%9{~sG?umma=qWM zBtg{@AHP?OK&%lhbg-Brz-I`@QqiiQhB?^$U&k{z61tvPRP_!}*}1ZL=Iq4mmlr(DZmZbsumn7f=8&PtvOM7LdXc z7w`iNbeVuMu+N3m60;pr-5tHySLom!=SnkoW^#=SL}jlvpdv(O>cD)TYCF8#AnUzD zC|75*ri;YkmUCBsvU8~V5V(q8y!dFvep!D>Y}_gHs0dA?P*?o>}8 ztJ`s^f2QeqYjp3YzV2%x&B7bWIR|P?|7OwKY8(#&fi(4}#X{E}F|Ty*M9IaEq`8iL z(>NU5HR_4OHK>7`L$6DA_gQw=PfXWX1|S3cjpMVMT?(I(ZgP9hF4fLC8Tt%-;Def= zVRIgAmQ;L9A}+mMsg1t|Wya)*?Z>}i4JNY^FRO?{@cCUBYDw!3PT+R#LM%~Y+)m6@ z)ji?%CjLHeBBQ#*YH;)xJ?+3tuY06-`7EC6L|zy#_E1C>a!j>2izuG)e<9`FfFQgr z@#SNb{-VF7=eRvjo;r201hjq0v=ZgQxX`R>C(W&N@*P@)vAsAw{y-QbFVgQp-jpHd z{H~Qmq*Jsc?uSxtUPG@+VmqAkY2JX;L({|~6{JU$BPOOgnblkVL8lx(!jR2i)&?3T z^ocbyTUv%I2Ggq>Id~%S2=1!ra|pSpX1Gk0H2rm9lv9>9%Nt!CDE$|Ca#hOg_ge>a z<{0)@$s1x5q1({u{0m#2c6Luzzz2{f0U#Lhn4A;&BZRzsw12Ki9#V8YV(r9jh8xo` zgKk==F+A1ZuL!}2a*QZEDBxUk%{c9+uaIV#h*Amx>L$JLKM+u2 z%+Z%W7kZ1)jX^)2U0lFH7g}KZIUJ40*f&j2U&~M4N@YmbLN7u=4!qaceG4MOkRQ7< zC*SnCl1-xC4cye;EWWN=H>a0@06skop^lDo@>=5p` zhUOpF5)E0Ge_Q$<^yKpx$HUZwTTl;irbRg(k-n#=QnOBo#X=9uG2ynqxgt-U(Q}@w zuwE1Mg{MV`NUtgRPlAfMOteeM&fkr(8Jyv&Q1Q2TY~WngEGiblPX6>^a*Wi^AOl3uF>Zs+)NiZtOyP_FzCO}mgd5gs z+Ri_oorfFBMAaZf;M3C0%#%~JjQCD@N$HH-A+@u zJ3_unnU)597axr7>3S2Y-7hu&#QQPR+DGi0&7OfWf^3x=D4FCw7~0y+c$)>Jwu{+O zP0H8|N!-xt>5)l4fSRLPo#b32T+-bGZcnpq_l-=PV;0Ejd=RD$S#=8>prpd4#TUPb zME=X1Y((g0L+9ZTTt+K&Q_1RJWw_`2@uh6maJV2Hw`YHlQ`cJRir4&}#rAG$#Sm3n5~b^!EL9P3(f8po>!qYqM#*j_WVafv0ZN?m4@!OOb zS%AaycOa_{`^21BI%VA<;;EDAH&d&A*)YCTD>u%|WKQ&qYV0TlAvEpVVi| z0LDX0xyABr;$H<*noIN^M!+nAp_}x8A)}AKXcg?fTMSeU*npJcK-BR$R#eECouP-6 z5PNha6+=E;e`_lDsBSoz+Ct8Zwhrii)?cuFI=ad^MT9f%4Mo4PJq{f$Ue8}v zh2MUpsbP5|!=k?}448}cqN6@LTRsdtMYVk8r{+8Bkv{dYAM<(=lJUsnr!3JThCH{# zTPfLq7GI+a;H^_YbQBn8;m&k*7u|PGPH+cYyn{qMODE|y^3+);7)?5G-e382J#g`(0<43>|S*DaYT$%IZt=Ssbb*w`(pO{kTe@9_w$PYbzd7aKd~pS zOF7~g>^87rzaK`o^*-^(lD{L@W7H|y+b=@j4c#Kez;sadAqhfweab1)XCd@3 z5yj(iRpWEY(KG#HC4WMu&O!pw7|eA0lO>yp*KGksE(#j0ZNq7z%~5#T^YsOgVYSWD zy#EIGq=mUpYFwKFvAC>pbnn-Y>1_v>qRdDA+>;mes~3j2czJBv41H4T=2DjXa-`G2 z;%%15zake{&dC;kUx4iwQ|Y%;TGzcA1h;q;n`33SH?(z}6Q^>09F`E!6UW`59I>gA ztZQk)voc+}-{XQi-P!OtJ6W+g6Do6MbFxd0SS<86&C7ys2 z2G5BUeFV7WJacahAK!?F)eT6_bbmel#vEC7^|RfjCm}wPUR)fSXHs>Y)MSeIP5bq$ zf226^|LAk7C4P1oIJ+b0;3S&;{>#7h7LorY5PJHb8l8lH3wMs#{ijAJ{NKWzHWQZ3 zxSVx`bh)WLTZ!7Dpezd#(KZkp~JOjM>|7#F!I4olc~h9!tFH zKRbVp*wf1hldaZYaxQQeGh;?Cq(vsIcJqc;0s^J>Z@onA{`8)${piVz@MftH@B6p# z=)YFmcbq>FF+!drHh2f=A8kDj+w)7aN1P-|GIS%m$%lmnY0dm>kV&(_LabjU!G}mV z1mA?X{F(6PY1Q|FAm>B{++`m-ih!^WVo?pj<*+v?Ocz}P6K78M7l3+4@j7POkz5GQ zpLEMpQOrI3254!$?H2x~mu-!wW>VN-JI&nBx19lD`z&dBh`X@R%^0uBOAVk5ijhBH ze}9bJocG1}?=K9iRKKwy@w`fAZ%|_*j!Gy_z_Hqt^KM7HmOd=w6L|FTL&2Ye=YZ^L z&BG>ki8bY7hUi8Twf_=b#TEZciB+ZeKSfvn_uBs@y4v5k8f6b~7c?!hw(g#gR&K}3 zSqqFhUEN~uH$q}s$mbM=SQTZf5E*Ptq;-u zAjDbjaaS+^_(RcBocYp91LL5AP74t9b^wlZL3pYUyL=3uqihbVz?;ts50LxzUYgW` zFT$NLIMBak!tqZ9N@1# z_t{b)Bqy`Ahzr5brY&A%KLB)h>jEBT5Nq+jL|x3M0#thH(}WafGTBV}hmv)`#GHV$ z>z=?I$p_+&I!8oL+#Si`9ls(b+@Y05dc`xQ!@Fw=_;7@(jo_J*Y$d_@udsaM&`4S4 z_>PsPoiyxsepXe>1sUnK;E3H485Cd7s_GqdpE2NrcuMNdNWA?`tZV5(zi_Ny6I?}#O*0ErM@(&NTS}`Y`@K~oRfl>!(R0#s7F&bC&BYQTW%FWmo;szs14nCM8OA#Fa0B^0iu*hgvWXx4&jH2Wjd z^hwly#e6wo$PpO$MC|Rnu6;aA$Op)qR||SU;e@eiJH?V$4blv2!G5mN(+TSU>Lz%@ z6(BKbusg{fy^4R#`MX^wkJ~l`lc4~-y5qg>U2>(nlY5(}jkD~F@ETatU%{{cu$~J; zQGRef`4s_vZ0<-OfRU$b%y24*q({QU85FNhA-7o7L+gjoWuCWSlYE9BHu$`u5rVT} zNK-bZ+c2t;CinXadUKfa9+-u^A{LP<%kD zThO<8(A)JxPEGco0R9x9L=rED74Ihf+xq5dxT4{bqX!gmLJ1&+>ZH0!_1+28ScCHA zcg{D?P53934%GZYWhys%>$}NzL$_zda?))m*U$@SibGab(`vfni{{J#@|>8gXj?fm zPlJlOY^uA30o87zVAKo~z#@})7LK*|G_T7)eB*L>2Wzh|eh~1hFpj*_C_asYp1;{@ zN#H_D{U7tRV=h?p{`b9^=<@WX6}6)fHTapvW8kHHr`FNC|JK0%e+H^*uVbb2cH#5C zmEHh4@;l#|ZRJqLLA;RE0!5N#?X&bBc;{irmLIQBS%<8~q~)wdblp?9!+oqJeyWEI zBbzWoJyXYPs8s-gQO@tMb@;w8ZJK04KR)TPYVxMQx}Lq$D=`T;1z38j!JL-*tkb0u zlpiy^$oKlp9yVpLfzoZ8-d_FD9MwBrWVtjKd@R)=OT#J?Ih)sKfKX@PQ*|@U9um-f2yj^Bv0$%_jaZ^s6YB{Z4w&R8F;ZUac z)q)PHQwFTro6MFHe--?b(ZhM9f)AK(cmA!bTqv-nlX7Xj^;O3$gp3Ymto3sr{#%Jl z7FJ^Dk)kWD25Z}=5WlUYI6}B-oxLT)?e?(9|7^+{!51eTe7MOl4$fF7G+|6DX4-4| z=UqZ#XMxJf5^JZj8f{|5BRRn9G%6(BWV%r{(0MZTP!!;=!nBnt)GOnbCa}F}bHAH1 zcqtm3trD>l5!zUra5Z>p)o=NNdut)_ewIA3GSX;ARTHY{~$UDtIZ=W+=|Z01L^ z*I^b=8(OSgJWI@>XTt=a$M_>^%qRE z!aXL!HwjY9S4&X-7ZP<;wN^5WVnYR5zC>v2b6h`psUC1c1YFLFqA7c$DdA73998$UnpLQ^j z;)*Tzv%34a^`G`khU0}&_%1I^Yka`|9dQoY{d&#n;B7XSLObHI?00oH#9qY2P6k%D z=`Z@S)^z1^@CLcLH92zy?LNEvJ;m1C>Wn(Y7lu-ah4(fvCOx*q$3PtEkq6zTr5(LjMxc}`ym96@g*zY z^`%50(Nsbt{Awdzag+gi|$UB(VW zPR8kiYMT4O1>4C7ExM1{v`3(j(34MxeX}-G<<)m^M4xj?fOfmi43qe+G5BR!#;f#* zDp9k|$8rznb~-IZIJpp)w=&iC7|FKvI$}=w5@C^F-{^jP+PFh_O!c7DW+P?3^Wk-0 zqV@1KdB2y_9?)Hi%1CgXRgS_UO}pJs&x)UR&eK0^NN=78G86H7X*Q`YR!I&YdxL|C zT9;;t&Z#25koQd3!!7N%1W=MPILO*(nwHxg{@;#&C0=5*NRZFgkJEVQFW4b><5u9U zcUO@N_w90!#B+)S)xLuD$=?J+oOsYlXLede;0_2?r1qvQdm3WjxyCN;H{lq}{Q{$50N|mCw1U zqdC| zMtV%ejHc`LG9>fyj<%n=&oG_|YF2Idv5ebMcTp!@>PR^veAb}2&W#*Y!B#156upwV z$u5B8>(sPEZW7(U4z7418(8-?X-Xc=uM#C!xgWw`;OYJ__Y#-!eZRyXoBkw9kG&;f zN$iE^OqnrnL;NYoE)@2TJ8wG_Y2m>#c2z>?QKc`z$d^4nzLobdQQaLZ+sVV2-&Zc`wJ&`DCl8&h=u02zDma zmbBI`MO)b2&mAM|E3+5w;$#Z1PrJOH$PN`Z%g4d7AFI3|ZY3QF)Zzorpt^Gvq;^xG_TOFJcVwnSY2j_A059Ls)k?`rz0 zUf1Gr&cpuB8%hBrBcx3Rc$nYote&i>tSy_XA5E?gQ+k0HjrAFd1qDP#wq0Ia&QjaT z;`LqKTfzR2@|VPO-2*RhJEAT*=&d}Qqlia}piw8w`ph8;7FXVGN`6zCe8tm$pZGQobO>pg08QbKQS{g~T|^W!niy5=>>_?|U&_9GNrvFz$w*#zB!w4_ zv$z@RDl+-CyG4Hzbl>>?Biyt+#Sl9qrM1ONa6 z@OxZ-12{B=UC4P{=pjU}x_2dB#H7XIXz;%0Os;C*xbqt;^YmS=7kS>2N0(c7BXsrO zvfv|J)7YCUd@t5gD~fwZv6o%ofoQ~D5dHA;dqj2t}XED<8 zc*j_YNq0I07o>fIP4Qc74qMcn;QHbAFsg-=4cEuOH_WsmR z%Y)Jt>+viUgM}fnbfqzY53dcnZEE7{*yMY@6z=kR_mNZdK;6SNV(J^3I(h*;oj0ys zEZkc|wzvmpKh$woZio^4u#kO<+mt;g1)|Fz5mv5V?_Et9s@B2<(3RJY6w2jzXS z>)As`XaYg0yV9fmar~CW#O>hcR?0t(5?aNol^?VxM!mbd+#P$Xv0?Tpv@Af?gQ zHD0WuGAY^kVZrf-E%jn!k%+c%x!*NbN0CI;Pv-EY?wK>@MCr5OgDV?M$Ney4nSf5uunl+%aS)d-j`j?gi4w zWKUl@E)6qm^x@0lu`l79$Zgqx01SNZw9ZU+0{+Vs6cp5~D|*g4Kky1k>Fw5`QBdL5 zUeLsw?^#!H_+f?9^k7i|<>14&#&_Rb{X%13@Cf%EH_iaA5ofDdE zbVWSU1&;!MSM@#Y+PFWB#r%ZNZu0nAR2$arz1sgO9KQ5I$MfbLa?B01(Ij#%uhUiSbsEp5;`h3{oPe^V{Br23| zEf3U)+1a@DQ5w9ejLG?n&lzV*3P1QT9#A|m3qu_xDAmttLGZI4Xiuv5RYNY}041+P zMeO~xjcE2=PFF(8ED?m_3>bo5dD+h)0E}+oZCR-P+}3EfMAChX6bM&1Smg72eccgi zFBl$h)N5VlyI}sjppDyg*!18L`%K~L&GxWlWWhnuUx3?!4zcu|&6@yq-|l@^Z;G)r z-jOWbT$cW_CHBpH;sZqB9W>&H*VAv2+_UlaL@144{z3SW*31r27rr&K+rReiaSd1| zlbvWqOuB>$e3X05FZWETCq}Ij@PN(@qVWdOp=g#1*8~t`W7fd<%>-+hi4gZ(C|!fk2mSZv0sbkdIs87T|Zr zcjhT%?%(qhf98gvRZxt7>g~;xWbEk>kKy6EzN|FhAGGpAb33k!{HDHPI33DmbBic3W`8H6wHS8J)HaNvG+l`#EMwF0Z*4Yd3cg=kI^e^-CFNZ2QbTqRHDp1 zrv0gqKWZojUK50op&b!4xvr0eAYv1E>d+W{y;d|-{qkh z(@nZS4h#ZIyJGhx4zYR|NT1qGI^WYXN*hpj<4<%9xfkb<+;KkQ{Kb9n(r^Cxd*7!O zQto9_xKeS)F2%bpM=XWMbxQ-me>41kGmL{ScZI&pJsKd|zG6~o*pVNrx?jkqZ4v;C zHvn9)Hs1k6SVONo@Y6dRxkWEildqRJInhY_rmL_1Sp?>iT940mKy>m^K+9Pdn~i>g z*nQ8?=Xms^T_2gPj`)M~A1aDG%Sb=?;^CE(JR1)T__Je147p!y<&3cWCU?U+z&y9K za9|aTBANk%KGlXa2)om6s1c>5h^D_}_m5r<|JRO@#_C^h9Z8>FIXPCy?oTpk$Pr|S z7LjxMLNOAgAY#cIN=M+ag+_QT&_OLP2~v?U^GF-6A#jXM4>Y9dbad)sx|NotYns2iJnhF`U~>kD+fEMK@Rlhl@1E~@j;w}FUoCDf2orHP zPmmQhNbR#HDt>*~0q<8*zC7bwAr zR_Lq&gctSE+M*;hRsXW8U)6G{R>lMXcvJFP88aB@i<_6jDowFz5GZ}TdQd9lnjdi1!moXnN9 z(cXN7%8FQd;J}gIBl#gu&gpTHsCoJ|XsR&N?clf9 zx8msifi(E+z5V`~wrBmGEtJBD5foe5SH?xeQ=%IRr-cVDv}EDUk^~9$`)_HgT=t%? ze`L#cvoBloT$r)W@t(aMXYx54MFhRGSi7T{#7ose}qpkC37rA zbLSrxedTJ}5N)k7@JEM*jS&CoM9ZrxeC=uBiSVCl6g(%Y&EXb(Yhdjl;nhYn2|Zu{ zb7^Wb)##KC!}y-cGLF{Sah$^sBz_$&kQoJ6kYiZ(;ED~pxsq`R(;gwvPk*4{?w7Bu z+3Ox}i|IZ1Y+1d%bwwfC--E`>f_iga>7bu;_OqcwjOM!D<)y7hZz)RhSd%7f7@zs5 zT5zx^eMo?%O#4Z-sW-9R%ERqxOm{th+)r&Sksu3+_O!50ePb2n84>nVU{RmWC0F>v zo|N0dEjbuXJy;n0JIuz%PSl<*6JPHxcyEyIugiWXcwTFKNvMIL<7VE-F z&CA`~t!PTm6_zXf=gRdA7`Ri@5g0=FY^*eOI^#TBQb+(o!GpIsg=5uNn+OjwzH9Js z_UayEtz{vMvX~0oybO}_4i~q*!*n>1Qv5F7tJn4o$s?fj6iQ(oT$Ms^yLfM-krJ)x z;%h-Y9cy!);`--_gSIP7Xk7ajct`o(? z7hR?n8i*Rj&m_BH1aW)+t7NT!c*i3QrNE#>R{0Ok;CQ9+u$PU=lXDeGoz|Q2BVWeH zK?PUI94DrvEl&|))bi7T(D_$*35 zcX+SG==X2;-y?WMraUN%=oF=SCa-~Ht|H?6A{ux^lic!|&H9ykArrdS3|%{r@m;Pg z$$iC_J}Pw+?=$LC^i6IsW1maE4~vV)%>v!cqyd?Tlr-hi?l&~~9TwX6?p2yJ6TMRQW)g6i`}t1;Nes&C&p)IEN(MBf&zy8t=eC!>$OH{va;NKbXP z&eb{SZsCDGS^p`w7Y8gfZNIjYe>SV~7teK7wOe9IAaLb}E|vs}|FNt8f1x!9JdC0j z=sMS3XjW=BS=z^e-or12E-P8$bYp>rU}Af?p89ITu0h?oMJWKKPP%C!`!v<#o`AL- z{)BoJyZ^mIrqQ&ti5HW#@4aZwo2QkWhuQ4K$#|J6=zZYeR=pgy-2ZH7 z`_w&_O}%=-$IYKG9(S^c@v$>KFp1|g$T06;BFEBzyV%F`lY zqb;Foi!vVtrfWL+Z`hgMh1LRSX;LfJhn6$6KvcF7ansJXMYQLbn&ZjF2zQP#Gy3#5=0#G~?J;v; z?s&*mf!;@Wmc0#(^{}pMu$kOoIwty<69>xj3#yw94V6JG%(Z%HCbZ;CI9Dfom@rLfJ!EK z+#Tx=_j%=|XS&ccX?v^pyw(I&6+_(b@<_+sdCK}=V7%h>vYI?%oAy0~JV(8oTfSXe zWCM@mi0kDGoD@HonKd-4bzL+ea61EfF8$pCc05@BtI)2YIyCV*rl7#*p@CHB$qfHj!+9b#SDoh5I-fW-k1E`a>i&qlbx0P zpy$$Pggs+fC9ibc_UxzVzG~}Rt&-G?T}3Wv`-esoBSr1eho%B7;{@y4(sjlB)ywL! zrb+|?trQzpFSDls_&IXDwCA9mS^Xi?Re~4>upgbKb+USkl)lvsV0LQISshFr?#J9e z$$Tk_9Qv7O8AzEFsl;?Uu{7MdY^nM}SiaPYd|)RHcil|AvlYYB+`ie2e&Lct;yGU< zMoVieHtLbY%S=M~jL^aa+iS6w z6`WY|U?bdkmN{%1w_>tpGyseYw|t;k<3AWt+U?cxjsihflN>7e$sOR z%x0XOD?j~<_q(*eO!%eAhE8E|0FoulGuN|IpEKbqiC;Kf_BJmzrE{iPIslBK^{L-b zi@J$5V&fK7=f8MPTBXkQJyk;ETAtnbPaI&kO|58}G9{S4H8}HMG23dIAY_!}kYVwa{;i0rJ;^U0Q43AC5|7 zyYkGb3_6_d?~YwYgYi;W)Y|QzDp*J!9~Hlr5Uaz^lRSrylZ7vG+~owfYn&vDbsHev zoSV_=PmVaR^%`S{xEJ=6BN=)I?IY-I4CyF2^9)@0-E{g=iFMFpF=@0c9*E9)dJ1`l z64JP20P>0Je8M#RXE6-}fdzT^>8%q2aR2WVl8_u;i+&~V6Ma)&kgwrQGyGuX@e@bx z0JDs!!OY#0%d^Z`!d2Dz_dSo2lUG5owBP9HCuPL5>!Boz95juvUs8DrHuFlVeGsRG zsOZ@QB#0fN$54{6ex9B$?YVenBu4<4P-tWB2B~_LI21BkEM7`tJB|t7{1u{4VHm(8I`<( z*(y-Z?1pt=3NjGg{hobzBb8glQ9%^Y_?Q)nLt$VsCI67;ja%KRN~6wXJMl*SLZ{|O zJ!&Zhw(ENkr;oMh6bP7yI@>{Ou|vT^qgewDI?U$6E6k}N37$+?J3s8sZwk^&daDO? z&T9r9T-Iz35eV>yHnOy{B!4ad4q*Hs?mix-!*F0|1 zSfDxMRo0F_@Jv^72G-X$2djl?D#|Hd7lMBy+vmpsFUg*@_b9nZvv*hDq_92^EcZ2qmY z?2_^E@ zeq_*z3Y?ALB@-=UP5XJ z;(N%O&X9A>wS)5+`|?iBMY?AE&}Yq0zu1dusz-PItj}pWsZxnY z2X>a}7zG|dmQj-)S;7gKz_SHwRr9mzPtBpF*^OSInOBaRn^`I*qE zguFv(#jpe8N#LDe5Z_jLJD`k%SHs_y!)?w)-V+!1lh@h;wrjylim@y%Mk-B4#QTM; z(l2ay8BE#wxsFfm5tPGslUZ!te01&dOh=qf|lFDb#* zhewHn!NlgXOW0@8pPc4wfn=3CJvanV%{!HT%Aj#GvLBNw!Ui8We$GcSLSk#>r=Z^< z%NBFZs1jxBAeBQ5ta|u-IATst!H&Yg$Yao$F5d z$aTKpR>)exWa+N@vn}&(zFaTki_JGT;iLld5bqtO^NED}17E&J*{+VEVVkXVbGD3Y zv7L%f{g?bTlTyt;)sFF!O7Fxw%-IW*Q$W1EyKCN?XVh`zSKoPwP5nxTZFPUQe&MbA zJc{Qr&T5jbweqFuo!Pte%?lxZ;s=q%!n%rAPM&} zOzIwX^tq?rpDW%T=}A38jZMBvHWDGT`3&##cgU^0fwTUoRr33g9;uwfbHZGi-BDI* zGZ?WAhcXI|$9A++_5G1;^5j8Mgh)ovivVQ4E1_wdNI)|N)^40F32j)Ftd$*4jmo_x z=6I|)%_c!Bhh6jkU;&V>C(+jc^NzbhUQMz*t~mw9@6fD9Q@94`4HPYFGtrmLVAmPT$Mq_YquZk-d@_BH;IC#`D`l`|SdaN6v+>5UFr~>E zZTr8^8%N{&&mVF|x9S2ESLYJ9i%krQfZ^hUEXZ@prCPa?g6``c;j@N5x8Q;a{uC#Jyx0`?MMlqH8|Z&K(NbBW zJ=>k@v&QDR^b-TlU+-PzaqxUgI~azu){?_!W=iY#QsqEAL7;GiCsW-m7(oG%&jS?d z&c64(ox$&X-*T8Qt!xeyJZ$mQu~4sp`Hb3@056wFG*Pc>T4WzFOp4-g$Gz_pbXu{mOQ}#pa9X)(`K>PkqY1+oRdX9KmJnuIqZSV#d_2l1+HK{Tqk`8!oyvniV(o86A^hFRvaib@&$}eQ z$J&2vngdtxmH0e*If2-Z|F&RDu@Mm0es$tX?1rEHX66Mp%d1NV)a9Dte!F7~@!`re zrs&>gIh19sKG`QC`qvy67;feiQfixf{wev;hnYN$qt69y8%|98{&Lx_=QU%GkO2Za zvBM{!GX+|A^?2UD#oiS}RT5TFHvgWYf;K%PgE5}&sCNfXSVZmn6O=TXTu`g*vypi% z;H+Xdjg|T>L%@AQz8@6=53$x3E;oOf&I2f8EeG&=Oi6bkfEcglF{2^}121CTg8^dn zH{hnXmN7ad?0ZVbJK+;Izt@u>MeDk2F6jmLou8y z=YZgIq&IKZ`UVFPzQg@g0*CJx>FMw*l{%=xE`+Z8?NA_i+JtTFWNlqhJvJ(W7QC7K zMIADkOvM)vT=Jyz9By+6MqSUFx;VU{ni_k^b1!-Z_le1J9$$HTll76PtiZ*Fyk1C! zz?FkGM-G)-#Ffm6Ne4=7)Yn#X$D>BTjXUpbAh^J^9Gy3@uKj3fsPk|uXes3*@EdQv zrIOcNCKc~RSx59U^>*P?6S1diNw$xtG~LI9YnvB55MuNP-D-1?`U`l9N9)Qh>?8^f zW8|RHCC?f>Qhy)K`pS3OM+Db=UUtCl^q${xB->M$rhV0>u#V8lH`-Xc15MbwxhkS+ zANP3#Uz}>~^qj82=B*w@LZ6|U_6&-f=oZhl0hJJ4XD@y>s$U<@I^p>qk=IBJh{cv~ z57_2&(>NgUZkmnwVWPc%nd#L?u1fK%hCZvFQRw+@T4MuLYRAQCQp&pG=!?B`-|BPp{y@BZmj zcN3-Vfv4gsKtMbE_4Uu`P&a=MVsdu;xctPbp>+e*S+lXq{>jb!w5^~tms@Pq%Prbu zABO5?9k;JeHkW-6h6cH2T11!X2kqcq#N(FZXA9eqDKuu2*-rYG?kRHE z3i@S`J5v;2?^Ih(DuK|HoN$9+Q9 zF%MpCe%DV#D~Q(}Zxk~J?KHI?6yjUVEuM8%Ppu%+5;{{-@LP$ITr{M%BCU35*ViIb z2okybT{hBXn0vIy;7)=_5iKdl#DVOllx~nYQ|46X2zAOEqZB+%?V9Lpeyd^RowKR7 zrxXd{n6lW%QeDS3WjmENxKzFt({9rJIHsy zwutx!OBK14C@Uti?i=H7?>ivxfx%2y=N`Ipx-cvN?k4DbGwZ#T-i(IMWZUJn&Yd}t zQkZRV?@M9gcYF?s4x)Vv=f@c#G($DaSl)u+>(7Q!XTkf`WzUkat)89%TDOsSebB^c z5PBu$d3sHUzMJa|`sw%J4@!EavXHpcW$ZG3FXD4`g||Pte?7A0p)xRQ6L| zkW;~8y*lXZI`HZUkRiOQW$QnoauQ{jMU@ui8F{ps4WrSh)qA>-YddCwj#yTJna_i}{F)yDwK^w&`Nn`)|QAI{Tt!Lx=gc1epcGt-?;F0!ZC183`3 z$H_)z$$+U(q-#&pNF#iR2r~X%=o3t$L2s*xCFlH#nAdipNa#xa$i$RK6WT04Qh}N5 zq%dQq(D3Dr#A%72CmQMFKe7Ajz$a(wSd6ZA zJu#7m=)Zb@=8afLc)8FJx)1A#-&S58@BG9unp$in^)aW9)OYmU8<>`0D>|c#!gtR2 zDs%hiY-!_FQSWi=RdQ79=L3l=3%!K8-+lzLbX|SwhQi47Bk<-yrK^(;LW>7@iHkE6 zS~X~1y%D{s6Cz}#eG-zbS}A|AU?cqGn4A_;%K`$pcX#`1*)61bd(yunjzC`QI8}Du z+53jrb0t{(nK^t|!XFP3&4c)@w|%`q(}Yp=mlVB|2XFu=NAaZLwb57xJ=z)={UIhq z+>;X|r7X>#3o&1O%X1(%fWae+qcgjXkN?9HM?u?`7vE!?SNh#&-+?a~PEN2ii~V)I zP~)ee)9)(hs{qQwxn`K!7*m%~oqBY;CEjX$4B_VbEEG8Ee*UxzP`vu=SeJ3UAdKZ1 z0w%B{Of9xyL(NOkD?ID=4`Gc+nqUS~(l|!c%29H^>GD;^j#ww;kmsz}2w1u57RI^^ zyUsNQZAAB;s$0whjRzF4TrcOwzEh_%Sfor$IUc_7?b+IN-_m_h+wiB3u?)QLb#CeY zD1MC2eR3!EWFp~3Ogcy-Sg#SeenhNr;fsLmrg*GPQ#G+xZmSd1hHBAtz^BVyQJ=O= zmq}K5K|y3>IHKIibsZPH_x<&LeT$vNZh9E-Y1L)#cro7_Kx=|Au8)xw$EYzZ>7gVf zvX>_pkWqL|7y4`Q;N~cZy+j3pNnIu&OuzMLm`u#(1z2%+6JJvK@pz)AToY&lrU4F9 z1McP!1b9o(NMR@Fb#Gp>^4TSKKl;4-0nCRH-*dC*2B>|8q-jC<7Qt6tA=-7(im@t~+K2B$m`D+vh|-q5V97uLUVZl2tIot`umQRh%3 zb{s)X)|tcjDr|H89H$N%m!qMl*A<$YK&fL{HV0>8qGI8lW#^H13<%CCU`l-(OYSXQ z#TTe6pvbAm{o)%bXOUuEbVM9KmmJ61)70biq8Qx@7c?`ju&L@AN0H(g)biOGyk;nT zeo@8f%8;?t%$auWURHLPCD4yf?uU3WB!y6@_tR^F1iAhu81m(gNa7toMhsnnihqCm zZ!*Bke{>XNcuBZH|C7j^&%u;Fj}e8X4T^1{%f|;$%&=?OIf>4aHfZa+jHdnV#rF|x zu&wRbcnN}x^|Si5vX;e1=Nv<-`}BR`Y~~Yq>#}NnVVv2T%r<9dZ^3(m(>?9|XRhdK zQ|fgM?b!Ve0EbX~*4uyC6mcp%BqXS0|GtsTcdKqPntaXOkI9OdQHJ=6Z; zR2`PtZhvKQrYYDTkR0cUw~pt=b?*0&J}n&xE?4%i&x-oJn6%1M-)IU4lLQ zm)i~$;w?5^YZq$4$tiO}NBO)$uj}vEdI})#P{E-j0`@}bs=pzgUS3-m)m||=SA1+Q zbiXfU>wLe>EBLW(Y~t>zK$Wto*28?gytLhQ8@(C9-plmA?JTz9eG9iAvDz3~q$}?KKVLA_L;uBvtSOlGMNI zvN^BQf;k$|*W$`Zpfen*N$5EG!Y#+LRPT59p5nE&w0gwe$(}%nW1#GE8GmL{Elb+l z;DjyoDCTczXn9HZnq}s(TpLWj#F+^NDjZBv$EBHFIB|c8^Ldy$2Mu9Of~4(buDunR z`%o5`1R`33w3VhSS5;M%xSjg6WSM-p3Mzg7*kli3e-mA?d4?X4#p@*@ex=KcOK9l) z<0SOWoxD&+4w-=lDFulqw0Uf|=5;5WlrSS4pt?pPKsB&>v~GXf^m)o%8I7Q86VAyI z=7O+)PopKJXA+hy*xG}No&#cBKwGI1NWA`#6Zt)RYs?(4kM|tv3J9D-^M2I`1$7t0 z^6&~NBIbZT6whJK^`G)NpsKd8kPq7`1p#RUViAy0$Dd?5-r=`o!(zhzB1{79yQbfR zA~yV#diR+|5Ht!M{4{{Wxa`5^%w5^sT!>t2+~<%uGDB*LoFB%$XBKMYt{RnEK7|1! zz0ZB6IC3Q?`Y%oUhOc`_Zk|eC61y@wZbR`Vc}hQI{exw2s}aCp=r#3qMg5O`S_X?V zm>|nLG7mH;x0PGYlfI?hG6&pWwJC$SpyIbPa&;?Z3!C+_CbBiKsFr7?bm{Y&>_aU^>>`sgnDXU+l)X@gTa%MVx8O8PSFjPCMH{n2QV?MT zBq8rl!5h(or%qbM2HDysB^uk5rMAu5ioQk3+ZkFu=z*<_pc&P$feL%BW}sZWP& z@vuja$l=W5NY-8oYV5cifpTdxeV`OY>fXFJ1YcG&G94_1YpJ;RJmUJgP*StuZk<82 z*ggNOy_iIA680VleZYueDLR?5N`PjDpo+r$0$ZzG&_F{!%m*!jTcXbHsl`}P zvIBt7KLfk4rEO`f9v{cFUq{%(y9?1@0ru$TCBF4D$j32_SiYphZNLavzcOXxx-;*b z=W?^gDrg#8-Zz4i5~IIwl_weOFfNxlx4usj82P4T#Feyi#L&ijUMHTa|0P{W5wAmw zSy8%PvYxe6qhy!x|2?rdRaqZQa(T0+gU8MF*P>!r9gZHMWAy4YFaBVDs+AyR(nj`$ zYH@0heI@b(uFtANzPVpgorhw9AM06$*RF;8!L)icDu^vzWoq<8xC9XLcJ7L+KCYOr zA|*5Lfy8@+$vybO7|I4AX#4RPihyuBn?`rLpy|e;*S!~PkiVO{5f!S&W6_90f%jim z&mK&SQsDi?%d4+WEVIpZzvSBIIJZE=Fl zcyQMXR2sYVPknU>Mt+KK^e$nk+@?}70sUwEu$Lg9FPiny%jXhaiodD(x2+w2!t9XU zdzsbp$8-!<{2z=N48G=f!P@KPihn;8b`f7YOdPaAcnzPei++RIrye>$rVoBynhpWd zxBoI07ThP%l**>ITCS*b<5Q>$n#zS?3IK<&Q&<@Q&pC%n@5ax<|5N2_9W8vx&^1R7 zum%SAhgsSCPk9onAa1B| zWwE4(qce^nmqvZR zQ_cetJHUJD{HL%pfD?BZ?c~ak49mD@q>DFrYFY;PFrh$&4L(v`H6Rcs@!OL=esp+I+_>S0H;ZSu}SrKWa zl8@;q^=iMW2ME(?&#l*F8Ok9p0daZ);)o1uY%9Yvc-8UvB8x;K$toUerS&@yjqO%n z-44uZz3{t|7bjyMsj~Ut$qp=)GU3%U&^PofIQ~LgI)OQ%BXtvM3fQNBF)|9_&Se2} z0{VA;>MARzmoX>U+;AqsBznUeNE~--uq|XxTb^Q5Q?mI9o7gN6MIER_;{I(h=l6Nc zD?WU4dsV*=dOOFKA)==1f|YbZqImHvw+YBuy<{_VJMcdVAY39P$}WY@#GgA1{6Y+$ zp>p^|%BLR;o6_uriva7^m!MIJiVoMQys>trJ`1*}#_g4};qxO`MEq<<;}kGqp18dr zi0g9wFBtSrAQ?&_>e*S(%KKNJml=s^k43;60hMnt2%r&w*kdnPD*uwCSfn_*s6Hum z*wYyDc=9@2S}XI04?R%Js>aVb1%32R?R4lY+g_#FJB(CWFQf z(8PAI`}wU^Cm%UwZ%k~|gER(kRF=r47-!Ef%|2DJimI2hmG*s92Bcc@^IAO%l3UwZYRyN6mO;)IoZ=s!H!Dd4@w z9jcBMxC4`bQ~{O$D;L8iZN_#Zu){Eg9HtmJM1_&L%RC;OEpN=tW+;T{mJJUJqWK|G z0sApM+>qa;zGgq3#y}#@_Gu>Bg1-mj*YL(zT>;F()huJQ@Yd;0@|zrUCE0i(pN&h? zZ??ms^@(dRB`9Z->?Qj6co+?QFN5_5K1zo5`RbLfUX_a>COp&zIKC6wIsz^T0COLf zls4&_ZMc4v(GPPz%{WZm-~fv^0#>hhreJd)udgkMpD(yMRVS2iU4kx;4@2SQk0H`vbKFoCFBQZ~ zBbmW=G&g&aC8F(=Q{ab}nV{zbj>hDGz75v}po8|i1Jqh!2uPs{vjUdeBOOut<4U zg6B{TxbC{DBMcUSA{M{vKRftCLiwIDuNAg(3dSp}t`^A-44nrrsM|BMKUHC{s`_S^ z{2-9!u3)&G8+%v#%`@H1fcqK=l<#~)uIriO3;KdHBlI9_)Z1oe4k+;(r zQPcM&`y#2SyMfJgM~?(|RFR1D>wPYbb_$NZTh}EJEJ@xil#+Y=r&KxpEUFL?DV6ZO2XTrY`2Bvx0I#MiDg!Xxo2%t|Si{ADK=sotYv+Hx(^O78nEOrZT_`faw|94d<0P$yRi6!pI zvN+7#z-rie@z8u&Xx2YOGE+@piPK89upsljMofe>xbq767K2g`_oMh)bAreEBRPGk zT$x6*uK+)qA@JIz;?J{klrP7a3^f%{REyQRKh^)|1y0VDGl(bYmeEk+_2Qjsm1PQE zsizSusc27}h4n7&|C!1;%xjQANKQG=h$kHW7aO&AdpZ92X%7O809(zT)97-V(HR*I zUz7ZcVlDXue!F&NMaDnwN}iP~g>Y~s_TSTpK|p)LHP&6qR<51F9PEwg$WFg7ENO%H zV1>3RU^;yvTJmZhSoc?s&RscRM71A5d>;nl1?W}Lf*sM~EmezA+VCKpeZ|&XAZDfb zd~NIEQSEg?4WAj??C@mWRoe2d1~gFN2m zHlhZ1LGPueybI#fwZk#*f$Fu-hU&8~%D3tE1PXT+yKs`EO!6LPt>ZtPIje^mVra^R zgAt>(!;EWRB#-0W;|o)IAb@#e_T?2BX~7dGYDN>fmp(wxKI9UGX|)mzMfZwIvvlg= z%W-ny^i!xMycd=rlJqEelARerq12(w5y$ylBm2G^c2N-r2eTYmC0ST*A7z4Vn6YmW z=dC`)SlN;Qra~8N)>QN7nMGlK{8}ueTv>`mMpB_)eo__`{Y%CL`xMw|F)X*5eoJ3B zT=>4a*F7%UTvYP$O+)Pu40v(fEX12j5VL2u^d`PxZGG|UcocWzsae}i!Vc2e%AJa^ zki9gL48?5v`!iLRcQ@j03Pn=mq$07mzGlQbe_Tkh7!aB&d(!kYt;lt#{;PeY zQ^et*$T_|J{P`1m-%uAu|69`3oE&=^7}`g&nB=R{IFtdr+8T3NSOqJgIBb1^gq(OU z3NjmH@HKkLiBuB^XtYV%HKd$_$ui^E@1}52@fR=zWce-KW|d@B7v$A^XsIEECxhKd zr~E-V-PSDIs3+5pB75-BX{W`gqC8Tp@&U12^~N|lyAFewiMumAmp>Y`oEG%Qd=^H(MlN0myyBjhpP?a)g3g#2K-&+KmwCEP z-w+Km7&ei9VH9yju3q#Xy3fC9u045_Q)0e+@g1Zy+;-!uP*_k4P5k$~c@737rTv;?s&WM~&e*5IqgkUBV_bYc8oo{ds^&2}XCq zLIvlBiH|=)@;4BWP{}A9gy|XldSl8UBSti6Jm<;Wmg-Ii0d=c~z6B_kU=%R|vQ6&N z9rKRj40_kMv`uM58RP^k@vm%EK<)n^S}8|0EF8+2m6hQ&AlzV zgX;Us3|O!C-JZr6;?7S8eZAY^&?k&{bFL|k+%kzLE2L=#+i;Gpt^Z5Jdlp~tSIoVt zI)krDOAdVv>sTxEyR@(M(bNyd*#Ggy!)2&^|B2E;)%|69C5Cgy^$-0Q(IfocWX)hE z1+t!&S&`rTXp0)v3@n~c{ClxjF8gk`8zO*z$^1h$>TTio7~@J6hJR!sZCjrEbU4Dd z!rdQCq#6qZ5Rcx%FSfrNIHG|~!oA3qoVaU=PIarTpW}GNq!-zVv#(a8E5Rr44jHec zBX40Ok@d4!oKX>-{>`80pFjoJ|Ki_;e7NZn%;+&#CV0Uh{&Hdthjt-pNzhvy~DXV`0W+a>P0DWBq&9^XK;7guH@?^-r))a>g#= z@#l&>IzVlPbF$)kIS)i}Zs(jMrRQNN*&~zAL1&s#{EDnaiR1 z+V2&`g3;w9HN?c%9fO#|zSOgFgePqjq*9KH)FH7E$YNxr02 z!uqgUXJV)D@l^xczs&tBxqo%;-wyFVc_^9w8A)=%wW-CTMevwi=(E?Fkg?M_*^x)R z0zxIgWQDBK3$F6%Q2ksx|LY2GT72}Wy5EaKGsLxhl)S7?Z(8dVG#H3qKO@WiF*S|L-@7KMqKY( zH)CW6A6tHp@3>_&;}X@}4aGP@9OJ2Kdd1Z-auONZhTEYHA9Nu zE`hbA-;iRGHvamDmgwKK0I`2lKpEs0qA!d2ULTI0)|UI(1ci{5-MFYyi#jX3Z4s}N zD;<+ha`KVYg~19p5|cE*I%SLZk-i)!mM5O?sv$3lNSA5*$osFlnzFJVQePH*|7l4X zFBZ^xWph(*<&JX~B_77IDQ42LFN2Ui_BN!Q{H-#f1FZH*Bwv^weh+G?M}V%2t=J4D z;a`nplR7+XBLBopqv!MHiMXA3_I<7CR}F|Kca_%k8{&NrZIFif z8QZt*@GQ@6x|=E-NTu2=KE;`YUO$4#F}92`i;9_uC(4fgf8O7X1|KJfN0s{t27R3Q z!;^O?hG48L{R)?P1yz47PDh+G10^5gnQwfHl27-%vuAnTg)I>GKB?7|j%(?PG_ppq z)Ip=0HkoKQBnnCk>w3X#fY+UowXGPtRk_L0NCX;_;JWmADn|FhxKJ+I z?>O3398fIpN|}n52xEb@YR9I&dWr9XEBz$Fq_9P)c-FT|Ri3Ung)QKP`Q|rC?u( z$7QCD$EUI&2XEJl%-ttSSnXbYfy{Tmzk21@*gTb&B`+mZ$UX_J1EF4aV0p|jPw)Kl ze@i$oa=p+GXO!a%8IS2TEnK<6sQS;#*TTJa1jI&t0KEgI zv@lK4q|r4>&9}KKN;pC?Ao>4upxnd*Cx^X}C-VEWpmC3iW^Ex%;T*-#?+>YRlaF>4*tVs?v z`_NFBZ8%wd93fCmDa7}&d#9I%_eOuRWG|5(DQ=`;bd=pP-{Di$q`vC}$%Kgq+|X|G z2(;i6d;Ed)&o?o7(PU0YA~Xw@>b99#&ynv(0A6 znUTdgUMDf_{c68h*Q-EBlBUSon45!ho}Q7`YYZGSL_DuES|2fIBHC4#f7Kz%r>|Vi zZqs@r*05exMG?Xx@X6EM{F3ZuxXP`ktv4dz0inC_x<(UG0|ck}Qd$ak=ybe**^TRY zr4Cw%*&?THlxpInJ@J{`Ci*(%14q4~o==qA?fm6XcXR%-KW}%LVsswXUsFk{E$9CP zd*J)u6KQtv{n&eELz)thJ9|wfHWYr?OBT^llg;G~L`1Y%{>QPn zPrN3MwGOqvr(f-nWn(P=rtA8?L^6s8v0&xo>x0#TlRM+f*k;@}&_fLd5dLd&KSZ0& z%e+Q+Uz$Q(YrbTrOPUMn|9Rm*WAa}wfJ66KH*M+t0`?ecwIqH4ew_GgKkjogWNZ^d zja%OcXJM$(i)!&h?!giD*y;~Q5+q4HZ3%mm7!;ahhTmV@dJV!I&T$)dE#P_(TSmD? zIoELsAjDQRhhhzGEDv97WA#TH4QD5XaLp!u^iDtGSXX@T;WQe2h)db)t8H0ZS_1Fi zAfs23x4Y>8yMAmXO07~tblcB@4<)3@ZupAEMT}!yOXvmQzcywN6l%+QT|-5>7+o?Q zrW>3?v6i`aTK|Z{R4`+bUsaZi)TWN>F(T${+6qiL>jt0Ty7*cBnz;G-c8VML(Jaih zH$d+;`23yW1>(C0gc1KkE8R68*W@z+eNUk-%daBZv@PD*^Kw)=CG3yl=MI?(dS@Z? zo0M+q+*$+^yUFdOg0;P_oJ_E4f>krqJ=ziND|qhtkvM>A!K}VN#eb*Fl1aZ2V)_&L zw^49Bl=+tW%SKW%?R7CO$hHf|2Y$;u>)-_D46bq>PeHENGrgye&mj(#9Vn__3rlG7 z^MyC+qqk`wdD5@J%NONyur+j3Ny>?P_?v@sTr|3M0dj%xe~UjOuo2Kkyw84tz=Xkm z?-N%qK;}`Cvy&Q8?*J(pSZRxn${b#0gE2#LfNtuFUxwFw#Yk(5WD}|M;~x&b497B` z7+&Hs_|$H%+!(`FV~XDp5ADd3mvIUsdA9$M0@7!YllQ=?I2-9L0>PV1*!|ZEZRCx^NB)@V6(b@X$?RtifRw)45%glXf!>c z_d`U_!B)`%=L?tDTrcjcKVdVVcvG^n&x1q-!l8%f`*bh>emQii2kZ7}QU5xoZ?iJ9 zEcu8^yJuxVw8qd$i(baX+cjuDCQ~8zacTOUZ*2#?`OxHOw+7Gc$Z~n<973_T)??0z z8OI&CW|vyVY`(p0U4X|HENW8^kboU1&UDSM%}j)^^%->mo!tvpszwyC5zr(avT%zn zz*Uvhu3C+DT96AsqZHi2XYHT!Fc!NE4x|Xsl-(!WHINv!5utd_McQv_0_m_MZMge& z`gGVC*ThnQ8fPNz$fcOEjWYpmMj_JW}dE=3tJ ztUn1?g)RWdNccIuSe^5J(LnbbA1_+)P=3B1Ack=#UdgN~ba#Kk33d*Vm=}w^hilrz zy({*b>%I7+EBMtEtl1j1bT_r|m)q@f0Mnl5)8J}9)g!96(n)KUcT;G| zCSjAnu>|08a$$CS@!QPxa;bB$lR(CzGCjBM<9wsw`j0PWwQfoG3|%eBLC^BSOM4hG z1UfC|^QNNFWwm{+9sO-$%P3zT5XW!;kSK+z^BI$LF_Af=uQfc&;q$GN`Igt0P~atK zU{b;T(Gdc<_R9(8T1(91EkcplNXDaMQ3Y(HOvOmsnFQp^!9d|cZ5>!SO)DkQ;qkye zdS^Xo;oWjSQ)jySO3QD2$r=ok936v-idv)=}3nss&F=+JE6;=LO-j~7ezuF=n? zBvCIa6kp!Gx3Lzg{$r>FC;`efQ2TFPOMd9@3p)nHK-^SZDu=DggOSCx z5%QNj$*aM?S_t}|xb)4y>(7-eGE#)mo*GL7hd|*ekTq}1zPoxP*Fq{iqe9#0XEldM zPQGnAE*1qH7D3Nl9RzEQoIOHQ1Sna3O3?${ieYZdvfs9QF$;-W2Gbubq zV!8L9T=b+x(#Fui%jJ_n)$dXJ&;<6|y~|I_d%F-O2m;wjfZ}EyAYcqc&j8Sbd%>3b z#y$n3@SlmK0SI+|!8JbZ*{5T*yRVV89(s>Qna8Z@?=Vzu#a0@&dxdppfSoc_=BQpe zd6mbFrzeu6@yly;BFL`I`c*Xw@pht`UcDGNlf|PkD>I5alyjo33UCRNm^^O#xJ*0+ zta~CS*xzhM&LyvOjfXo!u+|}yP`xP&_I>&EEIs*npH)dytkc+2D2V4c&&$F4!T)*rjR3BoZKQ=Z_H}_}+|r zZO$7{xtlrtfuBG>z&>FuJeYXaw4tAT_u*4VRV&o_w-3j_xMzCSl_~r8mId6q+klKQ zoOX+x(Gr#YcqS5yWsXTDE}NVD!JM6N_u)Fy-3N6#LH+K6oRP3BT{(@jkH5El@Tz`V zH0BT(CM=hc_q=C82)f@gdz_Ve zvYtKES7ZIqgs3mc0sNpX8Kyv4si{^;9|0@gAfdk_^1jAkz-7a4G56K!{=9c1sq~{c z)C9E%dFMM`G@e&flzi8zHC>wW51F0WB^VhB(myOt^l;n}wU7Cd=LlEFg}H;(1QsfT z)FEsydMg1b0oK2w7Lp-u89Q_i-(Fu<5wUIv>8$B)>aaa$>U{Sa`I3$(AXsjQzVuEt z?N>A5P!z1}CEj?kKCstc%x7slZW5VQjX4R^_A(ODcAEP1_6-}^Hn3R;yox!9>MvV7 zy8?b^4Rl*dyXl~_?O1@-?JAEsS35NesJm&vg@NpU8*InIQX)uhu2n5fN{a4qhY0q09T<6^=M* zXv`iey|28-=z-D)E)mHQ_ozi?JQ%|bb}8wV-g|PxE`OJIX*^wf3FW-%BUxUfWdCaB zTn&grQ9KXd_t2HY;df=60xsCL7nI3ekHg5Re$y=RsL%g^dn>!Q=MYP>F&Xmpx(F6* z0)*-T7Y6TzqmQ-rr~sP&@g!Uq*6jAPQ9Hq;MRy?WfI@q;IJ?`m!_hN0o5L6e(w6|`Nrq0ZK%;+VBfZBu&B3RAGxQ_bRyRg zRfsOJ2@-8s==d%$40Kh}J)o?8zD()LE{2_WQnb-_@t$^Or_Wp)V`7eJuRoF`_~^EK z6RG(T)n1y20xM|d`*&PTafVOb7EKNt-5w2VBv1EKey4Nd;d?lBkC7hCk-R!VO|{yU z75{JnZU(JJF1o;fZ!a+Kha4`@1Ht^?#Ny6endpw)6yy)K|}8>qXof$k`y-tW%z z5jRBu1d;GlYzH9!3u?QVuZCy1yi4z7eeeel7XlUqL!}?cd2do$Ek4;jCPopQ%XpqF zOcW;WI<00~lQbo;MK@lg@6^(&iM&!XOfS$bTe02pkbYTuK5p5y$L#UJCZw|P(0RIPX?;Y3F zwyh0=qM(3)xOX$5w z2_Xr|`etV$vM&fZEJ7bF5Ssp70ea+bNt>{O zJx$cb8K|`pZtwqsS9G4<8ho~XwrPJlM2CZt2dZC9&|&$^F`wXJD|Q*D+VAmw8FL-P zKeDNg&rpr&wk7m(Ye^TJ;ubw;vH=N~D(GKu(%d)NW< zG@&vk!8)-})=DJpmSX=+BE1{wsZOM}-@TMC4+SGEx1Ul9>>)h;Pq2ZpTGeECAx(}R zL50OVr>W^2>U?q$897cs^kH#)?z{~q?$cdn)wh+KBDBWHkpz;o3uZ2#%OONmE@J$`o4-xG{jYBGmlyU?Z;L+B`fWq;p6i`aA-7LVxlm--oK zHWN)d|2>JZa3*bjYgg8m(IXcX;!b`kKWNwd@ejoZ$7#ymzdy{!-^?>kEj2r7XSH>X z&hF|}MrG9~#Y*stXK7+PzH=~7)e4%&<@65maPX8`~Jt*{y%V24SA3K$K-D$2WPd$c=eg=OEFqK0s=Qpb^nKc z{V&^qvvm(da1id!p&GL+6A$y5nlem+**axLe5>jJRXhrOD0}?jf-Q)a@NRuole>Gc zH>jerGfX&Z?izR~s}CNezEQZ}Pxm5d;9$w0H#ZO^&B3A0k{VS%cMVP~Og0Yw^!Ia! z%sg{$m2q4;BWlP*L)EgS!#ByJ$JEzzS+A0lj>@TICms%w`0@~4-Od}nW77PM)-xw~ zW@QhvQf)DKLp!3QWy^30W-5L(WJM#VwBoDx=M&_`MPyg}^*lkvT&@{)25)stR+sob z2iAX9y(oRl@Xv3G6)}eXGNHwi2RBu-knNEVg@66y4YAOF?Zcj6Frz(V@8G!CeqBzL zKS}j(R(k97)ajq24gPkn=Wnkh-5}v_cTUX@cKPR5ubpQ-_v<=V?mzD(Texv+`det; zD_}W%QuU-{^j%#+vFm9WE520Rf^*+yW1dg{X}{yIHPZh!Hnob2*Z%1dN>5KL{qw6% z55(^L?K<}pRH2mRV2t!h*y`ON(T+baC=m-&_}h3)Qq@w}P&8*?->c z&Rlrc-v;~Gq9>{Ft`|3KRsLEO2omf(V(TkOuHcv`FbFMozQ2$C)O(k|-Scxbi_AYS z%R#SE`L}yMoS*}j{mTs_UY{HP^PUvXtv3=#18a!j4YBzB&o0HEl2sf-3jg#_j?4eO z>wvjqdcofRZ@_G{%L5O4v7@6yDFX@~MywDGJoKLd){5BEYn>gv2_C1xPqNr*Q>_)N;zm;dj z1u$yO1(jO6@uTAWk1I%ZW$h}Ws0mzCe8h$^7YAE9B5{+$=wONf8@Ssf4z@<>yzbtI zzPr7nOjq+^K;{KWfH`Z$sF%dRzJhL=*)M^JTdY;IAhE4xQ(XS$oQJqqf3HfKtg19b zzCxG9rjZ)(A(^~DPHWm-+{%s@x3$4|Zzd6R8p=#agX&z}i_}|RgM2*l(1;gatj#;I z#~Dz*UFR6EOOCsZNR=KV&Nld}QFJ(te&We~_Q;t_*QzkcZOw`<*LRM&y>sTo_$S4Z z_D_dL<$&iPwp2$#nPjICS<@tdb@q(;P*xCxl#c^gid2Tlol>gjQ zHT{P$1~#ZSHyKhJi^$HPjGc*n&cs#5&a=~)LO+5lfMy7avZ~kh3||}}!pdfq=|nMh z{x6QqjSeC}4VS+SBP$nmcFQtwk?Y{X=^IZk9uYQm9GS0zZuL*izeSP^Lb`QKyfWIe z2L$;QjZ&>*b7)&%b5s-hSH&xjWhCqb>8GR_6?g>?A2C2QB5KIvo_qI3T5AEYwm^F_ zJ-5%H=Eau%_clW3F5)l|=KU&UR}fXA5?@3vB59h_u7dh!mAKSMi|}VDR14FiT-nKe zl>m)IO}*ZCWymZ0dExmSh)w{m!qD-+R!eU+RR?@M`p!Bm>^22vAmg`7~BfmMIg!*32A4wcs zoZD3KYr()qf}Z|iZB$h}F_m!n$!nTX0V1*&T+JgD^=7#F#KSnLV^bk{22UNG$ps^_ z&d^N7F3iq*ub>a52qr|O>+st%5;;*>xnjeRoF`I51snxyH6w@$jQn zH>@(4pbjX??!&?_*)DC9m>ww!*oMDqPfjvfkhm_(ePB&+GmH zI9=xiv`*SU-+F*z&y)X4_6%f4vlyF5DfFFuq<9=$SLDBQ-TAmG<%f+^mR7CC`Z34V zbY5l-=$Hr*2!pjf8_FNjh0LxZ3f3OiJ~P8NpI;9!#fQ?xJeIOAxJ0fO!|?k1)um-B zD>|{QU=~1S2XqOPf=hJuE9Z6BB_w;kyzszZJKr`ayW!D(MN;5g4%B1>Me0H8Eop5` zbEvGw7L$0KJuNNcg&om>-1>y1#1mHQ3B19CNc2%Fy^pK;l=pY?DaHTa%Vp zsFs{Byf*#brg}rvCu^(keKdvcHMQrNyubyLf(n*zjqxcpF{O> zEY}blZE0ktS(GcPb*~V$mN8~l<}_U2zJeG*A(l>DgM6$=WuQ32RJC>CU8rR3o`t90 zC=7)zog9cPAj3+?DuebPzia%|BQ=G)mS4JRJT74j$~&Plj<41_K`#(<&CY8@W)z}d zhgN}b|IA|2;nwex+|t1;=$2H!=d+em!gi`f{TEnkY z`{d)k9O1oAq>UD)DuOPmCEPVjw#^z9x3hNOa6Z4TtSAQUg~GGi4^aLviKE=-L;nf_ z&S{v3DDZq_^k^Qfh1GWEtVQH5;@OdrE1eric0w--x{jxBQ1o`GD2boY7Kyl;Fn;CM z=bV?+r>-USlQVtp`#^GT9o^EogK)@L2Ptiem@@L|)4+&5d8sF=B%6!D)Hd(L)LK)X z(4%9H%VTKUiNpoa;e`4;44vadEdo8guua$|rZvJwv5{P^bB`ogLF=hvFu}FDBjE-0 z!PA1)3mMQ;lB^y{e<0t$I&Q*F4bbI`9+MP3D|k_j+Jw>yIFNARy;HcQY`%0Uky{+(-!jsgeD-DCxu6G3y2 z+2cNFCuct^c6r+{9OKw|`;jPX zwa6d4;HYmC+pFGhqybItnyn=0;Q1OP4dxm7v|e5QEQd-?`;T|_{_#Vyub=ywR^v^& z$%(ZO+(lkTzGsg>xa^0-4{L+F!zjqx{Z)uvHTv8}`mUR6nbWyLrdo~o%Q8N@Td}Z0 z4dlrvjWb32mkw|ytzBBSR4!fm`%shfRw7m6;n7^K;;N`iupjHVCaDP@TRdqcNCG90 zA3>q`P1>}c#=9(mn?EnjNaX(kXoGietoLs#dd7x^|-lK<8{Gb^uf?_*Z*kacQa`J1KXNs;h;(2 zN}!1)(J$Iw*S?laG43Vu_0*u2N{%!$0{_?Hm`w?D@K$yn@{R8NowTUwMnvoZ+`?nB zVTB0n;o3%-_;VlNY$0bhiA5w6r53Ehyb18L-7G{E%d|@wL|FS+0Lr(WD=;h7I1}4T zN)a)} z8MBz{(q6kEUU2-Iou+@(hY0|4Fz#*B@6{H4b7n)jb>mtpzbfuwZV}eGaDM?!vB;HK zd@$tcX4euQJHlVaLSVOaxxe6eL-aDDh*u(z{p<%OrC8TAjfER|fz68EFN@}0@1~y* z<5oD*VVC+eu5%AC3Q0?A={+b4cq-fEa1$4D&T+qA`UQ&n8}na?qq1DlV&_SM--`HW zS_2@R+CicnZ)>@HZiTx7H0lMHxb3h4Ysx4_n-7aEK-3A9Un)crA|ZB3zS zo6^zAk2*3~WrsXp0czk@Ogp8E9f-VxpOAzLX$-si5RO{llEMG|isA zt4PuG)XFm!tA_>xoP|O=uZz?k?+!RqqE0lyhoRT+KUT4R9)ay-OZ~1;&--#Mk`y^W zy^EIoF{{O`~$)nkWg3$fw-bGq!_50bba*R@ZnZT z8z<6v-$_E^ihUls0)U+2tFb+1*PZUOAT?%o*FbvfaZ~(aUGQA3B_+ z_GHbrLidLAe~*Sp8k`GeCQ8%|9@COit`Xxs^Y}})ihk(CB_VO@W+~~9yu#{l_6)ki z9r{1)*yDHXWv&X2hnnKUz%j0)Ttu#2w9JFatTfYBsr{uRWfPSFJW+Ra!a55;oz`CD;lp(|$|lS9$u z^JDZcjHV&52T##3lUr5MwU#H$gzjgSljef9O87=_qo-GM*c}qRujxM1@Hl9Syqi#g^U;AvB0|1Vzi1aE`Xms9R<_!foZ$0|>1ERUlcU%0(fd%Bq zrPexp*>~R+CKOX;b4cu|LHM7Oavkje1rzPZ5H?!MNxbQP6x`g-(q$aH0_gfJ=vYE{ z&n+c7!+9cCM@bR89+SL2l;&)|0@FY7trTdDBPPg;5wYHi$#k0%tz~98USsiCl4h}2 z4U@6E<@Bgvd|*A}THI@!qt7anc=kbGNE1xP2Rsu50g$S>9!F}+^4BW_w>LQMZ1G)g zJGbx$SM@8vS9)A~cV!{o(T8*fs_F3L!W53a!tp!Qirjv5ce%1r%lh5-qcv&$&r8zF zC2c&rJ+iMJQ_GRt7tJoQu~vMa&0Io7^o<0d*bL{A3rz%o)Fi9OYFVHw{ot;2jANC8;YiOWyhtvpl6b?>=&*WOZiVds`q zC2yyU5me#fjzdP_(Y+t;;A>r*Xk|y|#Eru5qwPkTZk)|8=a0KNh|N*Sbe#}{y%kgl z`l9K-=(9kqSfECvAEWY-IPGHC>A~%tSFK9D)b6$J&h71R@Fnv9laTe|(F~Z{dkb%i zI=mkBnnl}iZ?rs%UQJ%MrzddJlH`d8R*eKQS{iP!L~VJRq_X6 z&bsht?(Z>2jG`Xv%FlHEGUP9s&VQJJ4uB??nOF8)ql1DjEvH2Hb+jV|P%6Xk1nDju z8bd5>Fzu7(M9AbFCQR)T`%QA%yDP5OUCh&ebHijxwqJ55z3W_WA#b#u;Bg^&&*XqAF~M1{>4m+D$*r;av|Wg39ctd zp(`~^w5cP-Bh%xxRUv%e;Z9LGw$WeAl=MW^w~r?l!@$yKEn4955gUO8tRbMyfH{5H zCEr3NjHla#pXzuyC8%3rzYe7)9c|S6%m=6=a?((tyGkDmg?=(k2wZ`!{gMAnWBce2 z82?3?fKQe>>_%EK9Ibn;6ov@}scY$+vnYF&)5(D>`gCf4bouZCria_5mdBj3N@}f8 zFCcq3MVKWGhR!!KTVG&Hp^@pRFn1>7>!dJPl;FY|hKnXmd?vj#V&SW~@n8ix{^M*7j?>OOqFD3!>BJn~KVEHc`$~vd#7mE zVZ#Tq%NSJ#OuG;vvjlbP(5AyhIRm*bJg4`y4)`|@Eegjf-#N~|i$2a|t7xP(@($qP z;g%f2Go83ROc)^*`^+_l+%%*f=O|Oa@+Kt~sWn0P8PUN!;k{7V@>UEEqnGC~C3}4x zA7t^0qEO79Zjr8vo{nl3Z(CmxBL0zRKDB<>leZy3=yqV*_ESrzrN??7Jahnb3STP# zFiGx0HHEH&y(aCZeSFN^Ev}?GQNWt1y$k51(&XE+ z7U8cb%+X@~F!=`y@n0PN6HffknQRH`ijafT*!3!}17+K2%K9)1GBqyS;;(x@L)Org zm

    +W2GDyOR^&}%%YpOJmWA(dr&~-mmeG3AHWtQ#4QyTXPDu(_~xuWsWZnxw)tif^Risi#EB?|5O6Bjhm}r#C8dvZEJYAZ13a`{L(Z1 zhq)#q82bLmbatr+sVBc}Y2}P!jrX@1F2_iZJ&M{_`_;}lGhq~I*}~5n+KF#7=QeZe5r~wIHU_Ig0h^> zkQ1-atRtKuOt!D6NIBF@o8>kd; zj}9QKb)l{+IoDGxv%c*LUZ4oaa5v!M8; zg|`Lmmw+$7#5c%wSgt{k?KzUqA56WQOn7)ZP*pbW+z<3MAZT~cSuGFk!Sqz<03RDA zopB_+PPwvc)Atp-fHy?=aHAT3M%?slKRW)CV_^{?5E*yfNo&xS0)O@4YiNnbz>dpj zc_q-S)nD&C;(qf}^_TOON6r!KnB9YOH2s5CztYuvP=&qUqdxd}bzeECV}6BT#c-`s zDwf3ouz$krc4rw*bGI&^ibI;PJY~8FSW97OrLWU(UY)pjqYn*_*D?9%T%d6_qgdpp zo7*xDE!HDo0NW8ORIHK})?A1c2{jx(>yRxFr=3ebX;&}k+h?F#>*~XHB)lx=;Cs{k ztDJg?k0Cv5*9GI}uh%;D1CgR4zo{Kldu@2yXReYh)BB--(v2=SS8$G}_mFDRH3zVR zpdEzE2M)N_Va+$V%E_~YL?Y7|qT7ds76*I&0}wyX3V`zuO)^Rt|4e7ZZJ-u=|ERb) zR@CX3hwranJ9s!KeY`L^$$YI{-;vM1nvG9TK4r`Kl6j36=!V=#R^{!zd)9C^;XAuz zb9{^%1mtLt&?3+u~jDK*tLQBPaixd+weGhHtk9zj(^%(QQnkSU>Sr{Sc_Aj67}%v}8z|%dGqaWZrX|?dBkTmxDk{Al zL;T{qltYWo%9QLRoH9pyTk5iZ5(jaVg3eX1+|bULLG<{*xhsA*tgf0fyzfLjL!*f& zcy=W*(K;s8VOvB&uWJ}csV%;WySjghcetdLHD~JLp|1;G=iG6TJBxHcLtVdYN&n;-CRnAd+@mS_1Fl&w*C?PEA@yhJ+u}8RHF>LQqsfK zIS~BEOZ6yj5qO1xOS1QhI=lLc)SVE$J9$DtjwU#UMjD5y}o|32E}<__j@zFEmYXdsPmE9_DH4(>3r{ zJ(WLm70bY{fQEy7z~nX5M?HO~69#)h3_#RN@*B$)i`UklH{UL%ECT7MMrq0-Af;6h zU4JZN&?Z^CmbI%j)cD|s&s%fz!eeyz(Sy?~Aw0Bqwfd_bKR9~ht<3ka(Z%dbJ1^Rd z!l@NRFI&?GoKDX4O6GMGR>{p_b2Ht3Y-bn~ zxWdp4zQD4b9*o6DSClEVu(`c7lh@?V&G>Dm#D|XLjBWKFFiO-(%Pn-d_Islaf;-4D zO5e!BheU2p0tylm9!*-yspxI{9+r*Lg zZ@M1pgcIMAo!?rUNs(3^@3#Bn%^VXf{xaEC`@scQp-{qc&O=!`QR`mdSPLb(QSK9l zrxcSiv%YiHMB1dTw&XOgEA(4m;%FVL!V8ME>6CtY-Obe&G~c)-aQxJ%MkE$hrb*#p zm-miV>itd=oX9D%T5r`(QKTiDz~LWF>DH5kwt>PwC)ujF6ZF0E);huwilj`bS+W!k z^1g8zfhh8QU_e<0M}_mDPk`focGI)2{X9519CuUl_`~MO3=9;76cMpU>=dk_$M*+D z^8@69w@7(8LWM7jw8;}wzDgWPn#3=TNlJsX%8N{e9;Q`idMu~d8IS=`@ey#W*G!pG9XminR>$vL!-9)L4Fc-MOEU)&QZ zGqt=>V-VMF6W8G4Ih*n2c2vu5@@cQMyx6%u*Jr=$4M-g8Dxw@KJIAsWm3-BsmT8&sdu_+d%tlper3k(1@n1CBmzMfDd+Y2{=9xO{6SS9QmHh z9!7hI>p$ulQ>bDtMm`9zmwWNpnXc~*HY~|-ti%7xk2q(~GiOZFuiG`2DRR!Ggb z0ZR)*n3?JInY4I#>r;Ffq@IP?7_SiZu3~Tl6Xu5li_r-gv zdQMY))fgwct@M}SU=m9C+cBWWXZO3X#Y)MToJl-IG!(gjSwdAu{AlYdBG(vVl1z_- zo4%L@wHYMEBq}Qmcw*pcnj?gLG=cz11y#0gy*NbTw6XEGPx)1|V?I#cQUjR*4FidG z;2WDxc=#ndN$UXd@_oIp>G{D&EXM>E7WT-^Z6;FZZHyJ(r^VSzDa=;M%kha;uKm=H zh|cvsw@PxeF4?2iH0SvR=-#uh;XyT?j(97CsU0ld3RaPMB8Q#6<&B6FkDdI`1l2^^ z>lgJ9Poy`h33nwlpFupgktAuc*>W#O@!VXVpQ=6gv*Y=8ar#KpYBuKh;?ES=x8}%8 z9UBTiBZdJO z4p}|zI)Q-Pm(U3BpSz43`LiB-%b3cGRj8cpQN*All1cG$7M?X(gI*y&P;$y z5xr(U(|i{CQ7sHWJ%AqZxIEWF*4=@Xrqg7!g8zK0L_Z)EvF?+$GoRo&!?TPQ_{ke3 zIwq3@Vw$PIQJMRtiD!$8wz;@+H&b|ynxS&VL>?ZOPgMN^r&aG}(#tMPcqM$O*edtP zG?gh{G~!p?4~hN7%3bc@;y~DRVK2R0d> za%L%zl92}hlwKRt1qh&Wr^XO{mE3%Xaa>*^Q>-+*_YR&A*EX9F{et~X0_B?iiFe&-)wJ< zE@i}`-2fk{Z)J|F8RkQ1?)XsC>gfGF_;e8QErR%Nf1s+&y%+4g4favz@22i64i|4D z!-$y!n#f$Tj~^zp_HUQuqyFud@OoN4WRIW$QUz`-e-Kh|~h zkX0zf6)CwB(x`wWh-TqkLll=J-JRL_`7R8(P3Wvy6Ilmq8dk?-F`OBrbTgFK$P{ms z;kA8TK@NZ`EjWnj5q5y;WDl|51C)pBwAsgHnz|w$ zoMSft{|2gEgP7kx;M#N%2+d@=rzS<=EmcXkJ-Eia*G+~i27kORA08wBj3ANSKt*e1 zp#FzSi}oMac@=RZ70gMW7XCqy*$jyV9RK3n@GVPHQKRnpHCA4daNyptn~!Omch@tK z!?#E>cK)Z|zLXw$1Pj>0I?bCO7YWfl50Pt#iKDQ+qz(wTL9Xc!LK73A-uV*i!BZ`R z;GD_v)-o^nG|n7<+}9)oLLt0HPsy4XcJHR&Y92qP-BgJ2o;E0kZS#LwtZkcRe7OC# zeg)|?HCby>cg&P@_T1@IG>W2?bq_a7Y=h|dpE2~EX8v?gAH()uvKg%hV2B5n&!d(u+ zz26F0L@&Y@djizY3Q?45_%zRF+r&oq*Rg8l2AftGL}IvTiFOa^e~yQyC6 zF8eO?ZJ^jUB$cG}ix)C`J7H3L39xnEvh&p1IM;H*^ZjGE3v>Px^?`As%FTWovA@eC z39TYYFm{9^o&3nuJQD(PlR}}%9>{k#pBJ0YZ0WW!CBOW|2$`n|0E`pUt`MH{|2o+N zw?1|%z@qYqu^Z-S*a-%uR$d{-c8w8!tnUIz(ASa<|WMi4$dvniyadm;BXA%7~vN`!&2I zipv``e5?aCZP>5!{}|$}STs>{*E2}$Y&kSw$I$l#)czk0A&9wU_MZguepr}IjVh_u z7|c0*yTEu%{cQ|Q|8spi|1MId+l+FMG8I!{Ol}CEz%b}t;urYO^qK#YfAHKM!Amm~ z6>aq!8-7g64Muux>LMhi;MJe58RFRT#`4{ZO={QkTyyTvYNBpX@glZ2NTiOWNC<9C z1${^0k@n;nXc0EHp9IZq==N}t$VnY5@cq=is3)77=aQpGDIoeboBHX0BC;iJ>mT?V z?zzqQ|LsH0G5~noUt~ZSgfCisaT9$^l8q|LJrfqCrGCJ(|Mh^9h6wGtGxJBkptI+8 zW?>u8(^f>_#u=Nv%$LaSgN;@Uzx#S?oH=~qV*LaLa7tdp!rqDJelw`>G|5Z=CDkm+ z*_hmKJD9p4&o%c;zYffbd@)~&1{J~ZpaG&)6)0N#j>2cH+Y_$0eek7}J0{7Ycg~JZ za8Q;pWA)E7MAC}qp#5^dt!u@l!|(f_WqmgbAr^W6q5-7yqeVeFLyAt^0D!fgsTid@ z@~_o9e$$&Zk(4~f|i4_4zb;m}C zZ{|`&_w)_bzT-P@w|tyii9AYsVQyw{Bt{3aXpHOUd)mY~B;0=ot0RYbpX34iz<)HX`wTP_UjLsK$&p_Iq zR~LCS;!XUE)CaP^h3FK;Rh^2(wRHN3eFrsyTH_XG9hAoQ4*qicnS6!$lMn7(fD5wb zlI2VGxuDrdDL7&qHsrOW4liVY76l>W?Flz1E(0tDUiXvfrT{)#E_usZtR#I|u_DUP zt!V@9{1ngT8%r0O`TS&!tNYh09n27JEtvTmD=}rFBU^25Sjtl(pNo^=jY&5Ap{1T2 zYajgmZTb65p9ds(drxUD>GRqR@3>eQQ0$@f%LK=N)jWS^{ZmCEiFY%u#dhr5+`iiW zGsX`F?+=b$q?9*X@MTv|<$>TcO?bOvKMu`M%vlaKkfhdOtr9l}k5I%+$|6Eb{b$KA z1T?t;LoIK>xeU-LNu_HCES+;zMsd2^$I#F%!Y=W{Qrw}f&lMQZ><3%@aOT0m+sx>B z2~8N8{GxAbJ5%@kRC^5Q>I=aoVyLchYB78=a9bJU@e|pt^5FA7y%Wrg-+K!qEzQGQ z(P)pE!LhJ*Z85vM^kMu$I&(;JHq!3OhTBy*bJUY43K+NpFin{WhkSNC@yc|abnOPU zj7~zdG>d*B0Ab^xrk~b{H8xaRdUg?c3IRkWDm*?CAB63MJnF9G zQ%n?kcvJgyWpfv*r3~RC#3a-O1k)n4Z}|rQd!_ z$n1UOS&*#yhpHVgJ`oL4I_M^=<~~VLP$hw96UT+*yRGE%C_^RZGYu{_PS_oq@&mi= zE8g-^WJ@$OcjXLU&9Fi@01t*UvsbZv``UU$EuzXRvgdY6i`Ti<_$uWc&xR@ZQFuqk z_W%o(kW6aLT+rv)!J@oxUC0RB8(2eBRy-%ViTJTg`SjcA37M7Tgsz=wjr7X+fY^^D z*UjtHZnnj}o#PXX!4!(8#`Md<;@Ej6pmogHs`@tG4?|3;W~)a6;iS9^$!V2tqG+#A z=6hspTE5qn#rU%j957sLl6#iXL5m4%@70)W+#EkYr_}G|^T}U}&Fw>7(0G^4?4{VW z!1?n-Z-T7mxrKsOQ^|>=a%&AhSN!w62W=F2tYblNxlvPUsI;TKai?@ zZdlve5^sM~aqPznJV?U4ri{X;N6nuUyI$i6op$SdAy6D*p1kQ&4saLZImWdBEHt@y z!riJK4y~Z6pF3|imd#-hYaS<0eqGg7OuC})>;<>WD<8MZ>!OhYmEeurwG$UaLPaxU zJipd=aJ6JhOdufpma1UML|7CcSS&q9Ty4zRcb|_Q9y>cg5$k`fYl81If|3^q3&ou$ zAe_9Nl!Ap~w~>D2xsz7r3uRJQs(RjQR5^Jk`CS4nsH%hR5=CXOcf3|+QH1mUQ(ZA@ zEI-~O_i`EHHXLtnD&%yexQ4UN*kf;5v;1Bnm#$~nKLI*OK&_9(q*S-!&PPqs8`=_C;WG` z<^qyQ7=)KRDRmdQ-+x+$u-E-5<5Tq_25#@|(ln2dn!uk6DO-||?+6vc93Fp=syWzc zjIR%8u4j$?IiubbOE>w5S0~ItV1O>iMA#1 zJ4%{Ww-1360Yi-YyC^9&e;Uz&ehs4E0uiUyC>qczTmOW0t%02I>c*D(#u|2(FF z6*+}VMNS5>YzwZn7#s-8F*>?noYB*(&#)}c5is{$EQ`-T?i%tD1hERWIYVk-k$*~x^1lzE*YRHb$a@e22VkV$* z#GX>}UAO!S58aVa$pnj;3Qp>@Pd6)TtR}yh0&MrF5#(g+SZ$Q(F`o0`%N$1}z)pJY zm~QX2)XlffwI$Mfu)gCE)RiYfW?bL*(B;^`L5B}4ma1hsj0UlRiNwfbQnZ?!_IU=C z&veZA)pyK=vP!XvTjXr} zzTqC%DQR8UpRwtH4MBb6g{d^Zjx<3{8?SdItQ5Je1rn(Wm$higGf2cxgcu@D0F8$D z`||R`?pYA{JuCs=lwK}RO}NT&&+N&!A=U5aQH^`fps;N7rW&sfFKv>+=6tZw3@FEH z&Q+=l3P6Y%9rD&Z5>U97i;pO<_?&1!ze(?TB0yqv|07_WhQ*ocX{py5D(+j}JKlKh z8(GwVbO=%^vKz>Do%U7148BDHHaHP+h~%wNLH!`|k^b)hPFZ>}b~0#-V-Ufzr_0jG zLRt7%_N{dQ4t{TpdLU%up$WkF53B%%nvHA&2&f-yj3Z2+L+{6=`>LG4P!UP_oiYnL zRS?XIg!K6?I@3v_ja}2x~neKDqKx&Es?H$ zNLz%8u%F?Oe3wgQ^u z`sTtwAea7-eXXCT{xy< zGdnR+%16}p-j4me+5C2t?(Kdwc51!}hBpCCUrecl&kijR5~4K6wKAWZ?b~%Zx8%Dk zx3xRrM{5y;=IH(eDVI1@ys!$7!a1t@PNQm#kTd?NP8(uvd2a6pm_W6TdF>)xxp^wQ zV#jXeO5`8A`gt(NU^`ANI|Ce8agyrZ+piw;Z9sv=b>`lPq7qeO{ta;Og=)%iaC$|S z+y8$DUmz*eG^I|TtdZY{*g~(EISJ$pA3Zp2gQWj&eh^8}#|O$S^@3Y8v2DQKE%7Mi z7hoQ8aR5<8EbkYFb;0!CbjC*{!D00m+k#23Z!RO#2x2`Zmi~gh z6i~}yVAXx(RZw^JeG0O41My}X;Q0@@1;?HXT)b7Sb^2{*Uck~;=);0C;r?}+DuCKu zlOjrC_F5f=`QN4YR>hR;gE-s3UYtkZ0i~Cn2|L)PyuY{wewUX6CqVtnmll&P|=Fk&}r< zLy$bcD9E`x32k5Uj=f{)UQJ#A4P6}@>kEn%3v<}`s4#GgF^kO3*y;=H!Nj@y?Z$Ee zSSccAfgLj2%EwObub3{tBx_auDnPgcmDn(-r4eDn5C&zR{YB0W+_hqGKad_KKC?ID zS7^&^t?~{u20 zS?S5B>ByibRGMA$>W+S*_nIH0I|ix3Wp4T))>K803c8T&5iU)wRUms5s=6omP`)wT zWlnR4h_t{5Iz6`K(i9k4ZVzy6Qf60^jL`p3y;j(@EEFH(;$5) z{^x$dUGzRBBZ47_TtV!7gsFKHIUI7`?uFq$?{m+8wi}B|jYK-0N27=#+d&?L;bpUfGo8C`K18G^j%%d%b?rwfg(s>(>!Bo631hg5%Ngn+ z2!d7(4}Cp#Ya6L^gnC9Re@5$M%*7k`3z(~J9I8{grSOgF5Vd7hV$?;dTVECW&<9Q( zCY%>|;u{3)1W=4tM9=lLhbh+qqRgoi3UP?;%)5Tr7?Q_)Wk422v zMi8u%7Gb>AQEynQR-Qr~3eEEn+eLDyk9+tjl6+#E2;uNdLA$8jL{o+Bn|n{H5o9;v z&eat{82tel6sS+tx=+ielKd9UVQ@>;^yQi8qQ|q$8yaPF8@rHMOZ9k25IC%2g3m2F+?w$@1q4K$q z;AGRK!Smgi#d=^bQTyPIt%<3H6ICI({^aXWR=$&$52*x|le}6I+MkN>vO}vI5O!e$ zfqPvgTkoyNwG3m2u;%+kq)5^HEh5A#eN0qQDX52I86C4P;7?dt-_A_r^5{s06)tQ% z@+8LvF?&5cGZ0#Z=8sFflN$?1yd&v!kSm=`Dz4%@te`r+Jzym#6_dw)rk#)gX+K_u zjnB>wK`d^bO+WeGWKvj=RM9$7ZQgN9iSD9%7>SEnDn~ zkY+ph3eEwYw5>kEtB`f-X~=S6`~?d275XbXRjx7ffl3MZHA|AJHO;&C5!Vd(&gj8@ z9=`F8QQ?Npys%&{mt{D&R_~=iYktKQ+6gM5qMLM!tzL8KSiW2qQ!ANyhj3F161Y-R zdj#{XA?UlKs>OZ7`7T2A0Nw4Nqa(5PJqJ0c%%te34d0?7&Cw7&Mdv0YMolmq15lN-i>XQ-k#TRSur2G8S%zTbq&70XSptF&SlDe)J^s#n``@!7hnhH z@JQ=Iu3LEvu%BCw7pG5BKOTO3E@b`vQXus(n{_EkJ$5`!aw6~iA2AaK$`Pa4X^X#X zDpkvH%L}~NKFW&)_bv|jZPVh~C3p~PRrRs9NqQXP&(}o40Q7+v+3s(VERaEZh`)bkO415;^6$_9OH_ z*~r7V`J1*>5~ONpeIkuCm6gcv+nz5%7uC1^fa!_{eSE-%j&$@FD}m=bQS~^Dzckw& ztVrxYztKndF|)ivKvwQ|4+@_=Cwbz*R~s^E9KR6J_|npBlbzW5#$5a$6sX62=!SHv z`f;RCCpm~uK_rdsQK`yV%`kK7Tm@R53k^{z_35V@4t;f0;}42k$Xxz%G}cTi=WF!= z5?hgj1h0ZYPfF;};vs1To5H1YH*KhnuU$|hC0FH* zBB&MOw?i*n^H5togWOy3fZXxsE6BmPh#mB0GP;9ZRsGcT2G#gt`I#TMo5_f=ZApjs zTXKk>Ri0HP^qx1YFj0XO$Bw0h%F?j@WI8TEvJNLnjakT!*ksbzceNyphH~}1Y}M6H z@0`)qb4|v_Cwp~$NiCti))o>btZk!rSjf7L6nSZeOle&%3+Sc+e`P&ppQP5 zXxB%wZl3~N88oEuUhrEyFZL<~^{^cqKaA*KyAcX4fSn2;b@u?`CN?5butSWWF z)uvniS@-`?G4Vgy|1i_<#@1I^txT<|-Ls162Kb=1-ov}-B&(UBFxA^M0&{c%wS4{7fm)l|^EjjD8!uJn$8h!BxpLp4$aL6A0BiI)d~fy_e8ifIuKQH}Ctcd+%D``qus9cmLdLa^_@a?>V#gJkQ<((g_S7Fnq*8 z$D#fui;>{2vif%lD{0JC)3O_%8jDG=aCY7w;_o|DkxR@*LU~R30<2@)FC0_IdDVPK zrI`sXK+y82>IkzE2X<0oxC4#NpF4N|^9q+6pzg$%AgtTweFrx(6*#q9~of5TMvct*~EfQyRCO%dGBd*Bye zs!W!k>d#{A8nIbC>tvzvjIfBPhXuut2@HF{{Jfv;87uy0LaONZkk^_t9MQUVDym^C ze!@Go!e}sa52=O;=N@8S*1JjinlYfP2L;|$BNTGI`Hy9lCRH1OPOXxXr*mdnqe*fkT#9C3!PMHp+)ka8Q~&-^xw7> z9IEuG&`Y18(Nj;d|4dpbe$W_e2t5Dhvn<~F`gNZL<9@FC{P@FJeFC-b1=lHU<1E8v zSzz@aMd7T`G^`P8Fho(mn6FPHl*fdyN4ol)KT$ookFy%fUkBV{$Hfnh{`*J6EnW30 zrj$`hUE;q3&X`|jjkeUX-{+aJk*+KtbBwaih|U%9>vmdkxHlYm9BFkwjE~eyQTb22 zzyuA`no`QMcg@|6WvxdFlXrDFFUndOF4tjl4~zK-uh$;$N{R|`fy#uU)%91c3SbGn zF!Kh4l=53kpQ$NX4!f3eMkQ)zV4yJF(EP(apcqU;TL$J_wAE zw3NI?B&0{fJk*T#{2IghmYx3WBdo4L%3;Ed1$s^6wkuLLWem|eE~bB-C&jp;`-Sl3 z)ZgIH5dSUsvfb&u_yD>7ey51rq4Be@&4UVb(lY@F{LDqix^y+y^6x(4^kQTSy!CQe zEj{C%;~*FenBg}_4dNK;ruR=BY$Sl1D@66t^1t(QPz-h8nV!IrRJ>VtzlYJdqcSty zPo7&^vv{iP^4EXME34~I?Y|aHNmEQ0U+WB;+KOE_X*w_5#L6naAc!79`F#mfNH#c9 z41LQd#GNUR7Nju?YB*2{J002h0f{+#Cx-`ty#! z|1xH={4N4Np+BXh+s11y1}-@4DH#d}s>i`2U7g0S`UEq{4`ZDZ1?4o7SQ%DCvCdUka)~^l;h10%mBecE-6M zN7q$z;Z8|KD{Io2-j!v9iMTWM?1FMKR&x+HOw-Azf4~Y! zj=P=UYkP{u?_A4aPWrPFR))qYko&;feA2GBiuv@icu{2(NAi!so%nMu;PpXam(hk8a*r zO&2yMzwG}wV7hN+>-e6qN4LO6vCBg46<)~e{+|hiZXMkC^^bF&j{Mbpn)P*RVKORL ztN&wot6$c@_`-`X|6?Jji4zjG!Z9V;iRHcUjsE}H+2@rJj`Kt$3|*3Tea$QN?AQ)p z@z|gJBCa$gaAY|#vqVYb&gRo6f16&bvflX>rv;c;17BOtDPT9JKY_CQy&QUe%0KfS zMm*ysV7^!jd93Nl!yEIz3y-grVP|^MY3k;cN}b;Z;sx=#W6AiBE*xeeNs6BgMaTco z1w%5kjcLu~@%&>ehCSZ@rQ${n4NsAhCqooEthO4&V*5P=28mnGHU0;}S2ZD%>aaxN z6G(rh_5R}ptEfL>MH*s~tnTpwOrwj25K1H;ZFB9Hh&t+SNp7JK-H?2ng zk4@u$x2+@tqsFMj`$Ey&%8Djt(E?1Bei|=@67u~i<5ZZ4|34J=e^ljXT^0Odi!75T>P^ziW~ zk5`^qVbJ4n#`ar;<}`c=9Ki}{2Q;a}ReRSlbtba(#S-_^=skw9ZQU*hWcmtewy@nG zYdj%m7I&28Yoe+Jj}OX}@vjJ7;kWN87I1`nSkq%E9vJi6UEcH#8!G*`-_lW>FgIbF zTN22piA;BKw3+o$HrWz20pmwbq0Ws-YW>Z;xq)4%nG925GI@z0q(8X@!ESmi7t?HAA)&RCC%67S_x#EC&%JAn%+h^k+Dhfooz6-#`vPRsDFnYKlC5WN zV}`dB%LLaE1s5?1Hp;B;#_6R$=@L?sX5$Y}k6 zjNZXq!0Ww4q^5X!U5col<y6NtsS?@P-ThQ_M3kBQct+C#zKbT@B5wJ^Jlom%^zt8E zUs+3zru|&8p4z*#jX9?wreBp?Rd=gCZB|x3!?s|N8Kt{7$V6uyvFW8e6u0WDRUR^G zcZXa(PJY9`yVD#ygHv-_z%Dx=-hl&iafkhWYC}b+F2k^Ji9%6X&&>Xe?OxfCBDbkP zBG?$y%MXss+hX*)Kl8eM)AWfTt(!q{O&q=Krnhn~H@~Pbs;j64I|VVCFIU(Uq(wDU zp4wiIEHA<~)E>xjb<=R4TTRa`bmEUoh^nv9zR1iaIApx#Z3OV`)LY&(Z3P2y?}=O#~9rSANZcdl_&mDeoth)C-7gj|FyK-9Nf=bgn2B(%v9lboI>!< zzxLd0ZsnFt>Ua}=mOboHI$IpUoc4R1{yge-6m}=!I=iJewijtvIk__2%72~{RNbW7 z)b1F`^HxAjnIGC?M6WBjP_fW`E7{J-;%C+ONGMt}!|yRYuR||J5MQ)Vyk?-Nqnj>e zPM;P`H5I|TtQVOEvoPQi1=?N8C3!$E?DIN~pN{tLF=v|pz=XuSevY~CVswlGhIGzl zVkis(y4vDkJ>4E^SSsMp^!vIsn6APBI~5QztNrG);7-B{t`(iCFpOo+SokP0+bAbw z)~I?>?y>cVDZv#rg1Agu^0#LmN|8^s(@IsZS0T_oz4&s zda(S=CYOUv1=J?iuR|G|gmzqb4Wx^J)cLq(an3uRwvb~u?+ed+Tf6yRIy}k{bUJdM z3lOqh>YrDtbfOBd7oS;8-KF<{f>hT+9R+N+qbinQcQShmnaN`Ewr6Af=!{T!66K~y z#QDeU0p}#~@!ky{1yC&oWFG!* zK@3`6eWIuPrE_#xd;V|!@-X~O;tPObCBpX!=y8PTuURiE^cE*0F%M7a6Va7pA*=*3XG@0CVk zW6^F``K7=ts?W+NtUY{_lw(Jupc2l;#VyjmcD|H9hn@Oy0ElSF2PXvz<9rW{U@VT zFxmZBZki_#4CwCz-ER~F#fS@;J;cIS4X(b(_1q3imntcSHi#GU@ych*?<#ZJ;1_^3 z?T*~z{;NKSwOiaPAh>f;cH=g)%!ZO`_(xGyVBS`_TmXfD0v%^3eVG#-Bu6^YEaGQq z(wc(%stVXeU&onaU8{!F_rLGj=e&or)9WUcw>tL6<$s*bG3(&N#Z9m&br}_$(yZC1 zO~hZ6)Jak>$wVy$9Pxa4y1q^1mmP9E1p#1=QeP9}S(PP9; zfc!{tC7Sj0N1pmGa1AVmRUgIBVLjY5;2&5g*%>UDjn`+XX_3<4&`9u2s)Io2-K((kC02IU9B zbZq`MLChEJuR;vM?qA;N9ykNPF%H|9=CDEDdQ*t2TF>bGy|)rDlqis+4$=ujz1kd& zi<<-(xRsCpYWuKy%o}Tb7%fr!N&tt=<7yPrG)JOg-xF8MOxgAeb;Q}*VZOiDRV zO%IzHKs##zWUhS8xJ8+jyQ+Px{)`7ThTc4{6+Z;*wuqq?(K}r_3b|_J3~N%gY(-89 zi`zvQlGQ$Ah8}??;P^B}^2qrEU5pXO@Kt;p_99@;Zcj+J;u$`LK%sX1;t(!X$Q3jt zOn8?XsK){^!3xYgd2$yF%}+?`?ZoU{$lCxEE;9fyKf!|QfzljY((+{(vHWr3Hlk6@ zT&8gtMt2Ph#&-2;W!ppBYwlv)yr-=l8qBE=>>iv0^H}JQGsDtxNP&9Wbtcc+V-y@E z?usW6Es4J}Nkzr2-C8>;Ma?RuGmqrtN0eO`J` zYXIgZ+|?tdz?DObePRgwQX)%*u~M=0*WPm7RIQOxKmNd|3_vshJ7bLb(d(~#fWCiQ zu8(Ii>xBY~Ue(u7u8h9R?fhq#=~emy^@Gc%Fb}Fv{x#P+XOkHR;JslS9cu(NO-}rc z1c$t`{RnjF&MXG#LxUM;J{1{=`iecT2g=*9l2XcfII}9*pcx8o&K{2Mw{}#%Y;CY| zy(+bM0KP@yb?c+XLb;|9LQH4MkzM@ZMCL3Q*LX=a4E70Ixq^o9C_8+@)gORz1^m>_ zS`vN3UooFfeh{g32>JZwu*hVRRnN;=z28(DxY~~KEzr)LNR`OZPBN#RNYg)Ci~Lcv zmk_iO(LT-pGE0w?WWWhsVaieJe}>}lyE(lJ+d0_+x%??_Dkfp`9Q;0ca{B&kZtusY zv-W#CnG=gOZL(>cxXk9m-MLK<0qvg1GKm9WwYtr{3MlZj`C@LVDruuw&=#cg=*g2j z_SW(OLyKUx@lDY;*?*QxU-@>AMNAm9HotbPS5d&4Sxa9qJlo|1ep~+5oC6J^vUxrf zgQd?#QYB+4<%%*$t%GqXKDPTX+XlhzRZcI-BB7iJNKC=7p%+2_8UM)TwZ$uJ7geFD zE8=r~dF|&M2~5TJ_z#}HGouk7-biv%#G zNGWsDh7SW1%#t~>M~zeNMKVKl7;BV3-zAIqIKYVDC2msE)y4*4EMA62EP%ugN9qjG z`S|y8i~_D@h$`#M0w0ExHl|r*LK6Sz`<6py<0`^y#M?32S)GB^eEE8{T#50_6dm3o zu$RV^<9iH34ol7;obx@mZ(J6>o8t(`T#x$Oi~qCYHY8G;Y_kSs@8D9Mv7!Wf;MJcP zukjOzjBy)~%MJ_YYsD0FB@3clTW!^v_t)Ok_Vcl@+znNOD~m=Da~A(7Kgz>hFi7O? zP8AbkPBA02KLmO>tl^jn%;z*^!OnAVeTJsrO%KhT-9&rXd%=3MY5jee2kd*my=9iQ zFV~3Q*RiSFmbt#?k-uP<+rK8W`=lJ(Kc;GD7w{hu9S9a8kQ8)90M_*@?j+Y_#h4O8 z5N_9V0Qh2n12k;(55H6#b%-> zxtxpRMZz4uB@JGfCF5Lm>p+(tgN7ZuYUfUeCnl2%dp1r^@(IT`N%Tb)L(?=^@{`Zk z&q}Aa9qt`uZ6)K&^_`$|ou9G!4%M7AtRqNce*LA+iA2mSj^f?n1Mt=nSmI4Ru;%mg z_a4T(d#eLhg{*@=)Nf0Amh@L%H!_9ggT@lG4NU&SuP7?>;a2s!Y2Pv1Ii;chv{mq8 zW4(pEZ1K7JrGO*(6IUFA@bfTXsksDUb86r~581jkdlO-~$evn_WUdABA^3A!z4Zs8 zaoTSGeg67tB!-%m=2L8(E(E@RMeuwe18h|@K(FC}t6GSc+Xt&WkLtRvxT6~8@YaAl zZ7tS)n{ax8uCBPyWGue zaIBJLt9~rfpQE9HNJ!rCrKe8acp9ZGXrJLQX0NlJ z%>h%(q)*;wb8p)>z~fhO(M$@Bjk0A9W7P(yk$(A!D}N02#4pE**P%RNWprfxA5MA< zS4hVg4g_-~Ez&cR%JhC@8t@&0gLH~q`(>aLe@gwLlw+y)d* z9V1qxCVSAx)`~^^Iy;v{Z7K|nl%y$Koq2w+*bi3vFyU}fidF@_Lnd>bD|XdcIIR?mW4VXS z<9*boEzV8_D+XlY|H`iX!elPT$f1DV zJ^m*lw{HB0Pk)svAC&-+AZnVm6%|{`yHtlPPB7s;**BK$vW(8ak{ixpare`x1@R1@ zea5WT{^0tEXP7T=%&+iQavh}07^dN+7fK9|_ptv~_^$2zpX^S(Y>3XbuU^7mgCB8_ zbkBduUhC1*cSCYt%U#USjh6>v^5;A-%fO-Rjt%Q(wm`XbS*D1g&ygAxB?~(ShCMfY zT~jk+l8=S3a%~0CV3r%leyx#KJ;Qj`O~t^3nVNPu*1d`^L_wz}&ZS|I_jTtxGC)Z!*Vo#OZ!< z{zgEzv+M7JJ&yw^hNR#d9RCOJ(|PWz$se)#JXByQx9ATptgWZJrXIlTyM}a{XwtsM zw_O=GTlX>hk)Tan&8%JOcwMV(gv>&gG@RAF&s@b8u>R0R7n7}#AdwXCx6vM&wG3R+ znGt#Q*fNa6eA`i#loE!|tIKX04xoA%*iDgdC+t#*sY=FqG4%x!n!qH+c+83YI#W995)!B~Y40hpu( z@f6^_?_*Q?5iPCJwq84*6TIg#7eQ1IXD+I&#Yx)(=OyXL(Qv|9*Z+e$GPQ#dSTUuak%ZQx&}P6l=V*`S^LGeotemcNOp3}x( z|NZ{ztE3@B-2pm6SvAl6Q?AYBm8?gt=Azv~O63pvK9hkhm;^9gf5q|cFj$%AugFl> z4f4GDJ|rPQIGXe^oYd0)e;vy><4|LaH@NKcCVphf_}Ippu$rOSr`XRXlbC0K ziYlpu;sRlRwRr5)!daq&%g(7j)K7T^i1n>3l^_UAO9u}E z0nB0mZVlv9g^fpwE?6VJHcBrS1VLD9o>KJLOnUU$Y}*W1J@nF*p)C)_IzH$Jwr&g| zaK6HHjdWRF9%aIzQxrN9q?Pkt9`k1lgUS2iH#0;1?v4)SHC04z`y%>YPFcg;*Is$? zyDz<~&E|#n1FT=wtTc}1Y^wPIRZ+bP3UT#|?@h-tO8|Vx0;!FT;l?Ew_KhYcJnkV< zK73lcnGuY>16A~0^5>b7&x&c!7_)s2=D}TJsfuA|>P5PWK^QZ2epcW6UaDZP=m3m# z^HvH=kI34T`pCp{+rPctJ=cF9mb7=anNY_6bAM-UVqPd+Z85`SM#D8FQ zrS*QkKs?=ZI9YE~=l4qLb-x*F&nVUE3X<@;Mn&~=wBYEOfa~if50-2T8tfSgq!0YD z-tOZFzAyBaUT*$6E^=;6LF&$DD0drxi#Qwo1KGx+mq-Xq-!SG6n@gQ$yIcD%kV(FE zU$w#ql+;>e25bSfy?Sqfj1_PSV+!F@A zwv8$v_6*N3calkvw2{2d9*iD2RO`! zVt$5bY6CM>I=U^9vT&Jn*bj@2F~$Vn5GUCzyqy`A0eC-wRMy&Em2}o;`r`?d=^BPQ z@bx;U@Qqa0=%P6&ozTfI%uIh2KmrMqLJ#)3dwwxaOYamPxp|GHy2lZk3$p7REBpAq zt$^iSEzJdg-f~rv?}0Z#)*YGsQG)HW=O^33)|u=&>-?Ro6kSs%IrQ+YDp5m~$2l~y za_X+X#SVJM%yZoiUF!0FI z59e8J{)A)MEHMCdJU?if`svUwI|o}1MB9}8jDKI@Q|7}PZf=}NIAVN@Mu?jru3M}P zkY#tPN$PnPUzzXru3pXkj0)z(?7dA1A}ep`%<}FuoI0mlTz%-sGveN~xDBq4xhZiUVTs)ot#3d)5Bqi<8G9#gHWN)?#FYwj zf%}=@^Rse19}WCLvH@zB$G1852N>Wi#p~ZlPsksW*4mN>gtI;}ufc0v0;s-fNUT7p z-Q?T_E+fr-OC2Nt&-V<($z{Mf8fV(r_$O#J26?0>r7Y0`V6e(H=Qme8%SW-8{Vcn$ zNuF{p8;XwUb&i054MaAO(752ftn%B|FdJD1%aLycbrKg~FT>#cN-FaDQ2JpEi2jdd zTpTOV(bcC+fseAs7=KmuN9!p}i<#9RfrMt@3s2ZN#w~oq@`7CX3G?6pVg6;dyBOC7 z^AkQi5iG6Z)ps_oaeE$s4wFwKZPBKIa&@ZZWu68D)|3Q?R}@TfJ9BwKxy>Y!Wh9pKsY(TDmhl7lo3|BG}SM3$&883&o`q z${TO2{tQ<@V|us$nVunV%(BXjaOwr_m(93{SUf`0wuT zVkDgZUAu)j2u|{|!+zF>@~FNT#IJg8+bmbRf@Karu|U*@s*Z_51LE!?x(%l@dE`SL_iR zh7Pp!*yXnfn_GL^C-PR+#jEAvLiDk%SmbQLk^E|-?spve;y#7~v?p2iD&&HJpQ5~% zbyx<4gb^S^s6Gm0wW5o^fa2Vvx|dl2&{oiwT#-wn$k#pS83p-f-MxQhM$&N;h$1%{ zHt#dCvmO4-ufb?qA`mG=?xVHPE*bJ;Na*T)kJhm7qebNNE-e%k5!Om|P5~eL&O_CN zpO`5wwxF}W=PsnZ!pdTO`BQFoBj0+1M!?r+uVpSPdCUzat;r}@B=T_Rh1EGb%aN#%>ySlHfq63sgsekh4X-6A^= zQ*IN_b68YVQ}1^gN}1X=Bu|tfZ;HtIJ6Apaq>7t%+_)xa>=Ma8j)V^9YNWbqU+>pY ziMzPbzH2%7=QY}KzT+7~+OgZd{4=(C;Cs`^G>!%4^L@*>v9XOMWazp|7u{ND= zguM}0S~}JOvbAtlyM1l|@JTC<1h^sG(jVS`Sb+qBkJ6nd{<|6{}16+pC>i3vI9=y%M`(!F5GypW8z^BCQqJ+e9P>PEX}=^ZQ#ir&g?j z7pEH|ZV$V3+`>$i1KunrI_+0c7|iAThL2%M7DTX~U@RHsQ)W&)TVuxJC$c9OwuxnX^g`7KV`u6G-*QFxB1L**-z!}ohLUoQQ*3{iSlvAW_v2t!Q?6%A5zFHwnSuOJmBY$KJN=`q zf!h9FDP?>~k=m?p88Cn0R`~->=F5+sjZ(Ox#b4^7^7$+gY_)<|`ybU7Nqa1rTym&Z z*PV1GRAqV680Gvs4G4QR%f&69J74Ev1GWBVo4yET=xsLGB>N1AVZzxp==p?wP;}eA zV&Bw!G@nj#g#0PhuE$i(88#O71xws+X~Pp1yzKP%<#zj=Z0}ix3*Z?ImQ}9Yl&WF^ zhA|9y2g$lI=e#hbQM+K-So;7$jUtP!cdMPh6>Bvk8mGP`D_qhDL^A5;q@=CjIXjf! z4c6$@Q1Ok9?HZ6@GOqy;Lby zm9W*JeV}3x!Q~dlIEaK>lQnZ(``365Q$16bQT#)GX$X5|S}PZ8(jd1?k=4|@vIHt+n7LFmU zvgQ4N`8C!qeL7%vWqU{@G_RS!&%uHRx!;}s%jAYwn|<~DMszs<=>Gmz{Idp-TnZ$S zzqmA#;@^k(F8iZAQaj8qFV}S(nQZ`)J`dKQ$yEWY<_T@fVF#oi=Q}SnJ)RxG`tVr< zRRqBcAf!_F_M-2yVzKc%-$HUM@*p`Dk}ML$_pZ)>ms#HFr>X&?LZE&Tsy&FH$i&+a zVn-Hi(^7emFLto#Yx!5manND%1S(Ur5_o|mzRo7au&tD%CTZ@Nxv^2Fp6`yO3%e|G z3)3k-S9q2pd^FxOWGd;s)5}tx?>VgS+K;NtH%uz|&tDEO&?k5Llv{h!`}KE&loM#P z7Zclu8Je>z2Ivbx1E7(gg8|9;9$o7=@k^=exfSG)SC%?GU|8C#%iFMp@=_3m|5!`9 z1uAX}yjeTX^y?(^%WkpO#+rGD$tYL4ECc-&I-Tx9vRV6aV$yGp34i4OQH)}h|0?6X zwyw8;v6tP^WivT9mEtmUQ*urbv3@=};u-Fp*r&Nha>${aE`0PUDFyY>9qZaj!*vLU zguTTE%5|xE$f-=i67w;}{IYy$OJ`!lyxzY{MXLx1JRJdOu=^c@*>{HV=4T45kS?-STGgeWpuNoV<$2&e zYh5RFi(zHv6Jn)uERJveGlDVE^d5GB>feAPGTo&;u?b6;j@X3KikdA8hm8O?) zXrA5BZ~=>d`E}c~5Ol0XP(}82_!7si%(K|63FxmidZ{>D(u11mB|U@pM1w==N*ISj zGpD(YCm37=N1jU`^k6y1)^nG*knxL$^_k}9ZeBGz)tGB4#3-A;mferxz1 zq&?Y^NZq!&-@Wy$bSh+P`<|#XO15Q;>e_-wcgx&$e8V_|i&MCQBEB3|O`yamCVX%X8 zn0K%1*5Vk4>Y#q_D9zpatycLESO&b5mX$GlX)KH~gf8?U9~T9OXtd0QpNZGKw-ERbG%eN%Xo>i(6!gCL14V!T zzPo=AW~Y#7l7sT@f}DHUOhCZ$_zf0X`&Q(<5$E3wo4n7DzljN$ZB%Azt~(<0G6`*E zQa>8TCB{g3f2$QLnx@QM(u{2=z~}NClVV_(JD}#AqZ%>#AmoP0PPy6k{FQ^#@){@n zyq@r|Q#*DdS7(G43!wj8c`Y!ZBR-T3m#Ij4fiqI-Sky-F6%O*2w!t*RbX^$nXg;>a zw6hy*1ID|;dZRW)lB<-PpMU+GxCbSKkm8fV zb(sRIoVi;YJB-lRBl1zvj-}tu!HyyE{{K#|5XI{ikpB3t53`EXn)N_?RA4OHRD>nL z^`&64mFMF(FUVhf4;|NnJtazgM^Ocagc;T6k%D|A6*na0MmAqmi9|mb9~AJ|_L9JL z+;^!Lx4D_%`PtjuEB40dHt2^+;dJx~=*bzh5x@WINwdCwy=B~o;eauk0=?ip1P4m) z+Ry`siny)$Rf;<-QtDx>)e~+V>{--624F3L@A{v{cc$<1z(5#zf#R3g-jxk*WzwH$ z+8X>2%Hz06^7neN6;jvG+iihc%gI`_C70DA$q>`WqD>y`IT}R%|N5Z)vB^`s++iB4 znV`i;R$GHF<%5A~qn&b(S!Jlk3=*5wj2yo6jZkIN@69Ci@`g*>;t~74f{?+xZH=>Q z$f$IgkS-A+SDaA0q0fHVVN7qOG9#bU#Njj6Xc0Ehn~Ut*aAM2plJyI37lU6rpmvZB zBB4;;L)@6N@bboWxtym})LTYeNfoZ01ij-FjNK<4D>LOV2~QgT;V$-E;0tLsMRW!D z3+WgY4OjibfV6UHCuSW^%~0zAdKvT#g0G_t{PMG0A`V*NSm=umxQ{t=xOZ4mAHChY z=bFvmr|^=5!z}4NV)KJDv0eN|BMJ>oHUerLkMvli#E)MB>a5FEY}}m3xEim1TA2oa zmK0f}b+LuDZ?o(1Ei?gB5glKf>S91+QY!Ya=>c?aI`IVB={=12wl#Pa=H!;nRn*0f zxXj!;+jdX*t+?$wU8YY0qId`7D)b(>2Hfws*L0GJ-c0hk6=UHB?U0Gdkgv#-a0`3I z?#QYEYCEP)pZNVbpe@9IMj#t9Ej(Fn&Vsr85xY~_6-$5JqPX>tk~%i#1F1OAwd~Jx zDXewhswO5^% ze-hSj2XB935Qm?UeUi%K>soPy#wByF` zjXnAWq6@-?wB`-I+F_XE81ov&XQuwQGfCp09$yCqCw-b)m-(iOXdr9zIn8byfvE=N1*mwdJMk`PM7l~Aj%na+5Q z>>BKJCJue7Qwu7kTL5VjP3{%XZ};J8A9w17Sa&5t4}~NEstf%6)xB~CkB_uGsXK~X zW}oSMH<)jiR3JJ;xDf+xpipeZZg6tsy$$bsL2nEaxy5y;E=(qH z&}(}55H5^TBL9Va30Z&>b)%7nFa#&sK(XZ&> zOu0@r?Hg=RzZ%CUvHM+YY+S?8-W1!Vy~27A&`?&cUg-dJ*%hr0%SLNq8rC6f=f+>Q%nquGNOq#^4ixbTz2j{54W4iFv zu+AEJ4v~0`WNgh<#L$~Vo@dft56b3Hl1JGluaPrzjW~KsP&gI$zrW$MO1y1WE>uig z_q`YNlB*>ypr%7j=?@k%;RR2T#(?))MJyf{)-6dqWjKUqb;eNpwA$d))FUz<^!ImY zM$jG4qGA^vCtvMt;aWIHp54=6h^%>a=^u{h4!Oiw z$yf0~56b$Dw9C^XwvDQ>3|sw&;F4g#9b$ca^n`y;b;7YoR4^4*sj4mqtVjy&-+DYy zfqZLAwV}j6dz#pU3t*!>5pU3bhb5Dt55sd(R+NbUmpg z#_V3*m3JP!$s|u3ytyXN{>x+@GD1t`x0)ky0O}ICKj8po{nDXL-J>ozjws$k2;q+q z{UGpRw=g4%4`eaahGw&nW?mYu6>kB7vx&Nx3La{vRXnaSo@l!2a4&{*^>r!stJX#h z4NXpyjIvyKu1Ni|gj@G+?o%R4vUl_5kL!a!uv*xym6)%JMBTVe7M&#fS)LQrInT!p zgVCj&t_HX1{|-~yOFDmfM4HL-NlEDUqqd<)cMbb>#>lOq`GISAhJ4GYIzKyvoZ(5{ z50=d63XKz9x32YHeF>KzW*#bF)_&7VQ4(^0$Q}MtRCCK)+tG_28ko`$o@5QGQKr^Z)UXE;EeSD&RyI$VR}P&5>Ut3~1J z6>UoP89^}>`0EPD&*>SS7=k%OUX_Kn<*n|j`KbrcQtbOSB&q2GaO<61X;0v}#fcLJw-LaJ+9!eMhu=5N9Kd1i_y4~$rsbeNiAO4Qe1@A#;O zz4CTlXH0y}oKC6m4ql?~Ig)azk|mbrUGPPLzMG2iW)1ko&ygP_VxRQHSWEn(RH%E&FF z$TgjbP78u`@)jQ(Cf;SJU4c{6h2rEdX3{PGJfOJ~L%nv{SrD@CNgG2QN=%hsQr_(I z8H=1-uzx?FMrE(-uS&3TwuoMy5Ga($A5j40>;RyX%%+(K3gM4D z|FVVV8w`!eraK+I7B#F<9Ud@i#DZayrbhlTUr=-eRyt@BZq(Dqdfhz3a=*81dz#BA zA1Q?A9Fk#0(04y0);~v#_P}jkF@q9kLb612*x{(#54GCe@7JvawvU&$of9>Cj_y_C zd>8%6o7<38UdK4uiD?up*D|+|7UJ`^?W>!d-@z{lsZYh9w(aL^_epPC0W3P%1$f5( zPN?+qL1IPx~6bqua78AN3-U&^IOpi^dsbvj)dG6XN^nJ7E>MW3?tE#hC$jAU0FN}0TX#NJ?WKF!7#;XLYcXMx`7bhoH!=7|@#IJ^Dt z8oUl1UbE0X6qWU(=a@%lAqF1E~3{tk3bhewtmoE238)Gidzu*YHS&2Vd-jvW4mIMf&zssE z#mixZoXvI^x-ARMeXxxb_nUQeMIurRUZ5#fDoA0wj#xX1;0Xg9CGE<>qLX_NZY!~M zoy^*mn~#fUWGC3Pk$vkOc*ikjIFzs>ajaL>YzlUubL?pc%c3V{pVUj1&JXNbLCe13fx$#A?< zb-`dO*jO~f;`%$CJ?K=xpXT^jMa8kf{A7HB@9C1eFYLo*wun9@h&wZc=T8?8WMVYC zYeQ`>*E)RF<@lu@=BSa*dvy48Q*d-*{rOlIRct{Anj%*SkDbfQV3g+ke!RR1W;

    ); diff --git a/src/plugins/console/public/application/containers/variables.tsx b/src/plugins/console/public/application/containers/variables.tsx new file mode 100644 index 0000000000000..665e2ca4849f0 --- /dev/null +++ b/src/plugins/console/public/application/containers/variables.tsx @@ -0,0 +1,35 @@ +/* + * 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 React from 'react'; +import { DevToolsVariablesFlyout, DevToolsVariable } from '../components'; +import { useServicesContext } from '../contexts'; +import { StorageKeys } from '../../services'; +import { DEFAULT_VARIABLES } from '../../../common/constants'; + +interface VariablesProps { + onClose: () => void; +} + +export function Variables({ onClose }: VariablesProps) { + const { + services: { storage }, + } = useServicesContext(); + + const onSaveVariables = (newVariables: DevToolsVariable[]) => { + storage.set(StorageKeys.VARIABLES, newVariables); + onClose(); + }; + return ( + + ); +} diff --git a/src/plugins/console/public/application/contexts/services_context.tsx b/src/plugins/console/public/application/contexts/services_context.tsx index f133a49ca1fe1..a9fb86175d02c 100644 --- a/src/plugins/console/public/application/contexts/services_context.tsx +++ b/src/plugins/console/public/application/contexts/services_context.tsx @@ -10,7 +10,7 @@ import React, { createContext, useContext, useEffect } from 'react'; import { Observable } from 'rxjs'; import type { NotificationsSetup, CoreTheme, DocLinksStart, HttpSetup } from '@kbn/core/public'; -import { AutocompleteInfo, History, Settings, Storage } from '../../services'; +import type { AutocompleteInfo, History, Settings, Storage } from '../../services'; import { ObjectStorageClient } from '../../../common/types'; import { MetricsTracker } from '../../types'; import { EsHostService } from '../lib'; diff --git a/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.test.tsx b/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.test.tsx index d16dc3f832d3a..0c7e4c46d95a6 100644 --- a/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.test.tsx +++ b/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.test.tsx @@ -12,6 +12,7 @@ jest.mock('../../contexts/editor_context/editor_registry', () => ({ })); jest.mock('./track', () => ({ track: jest.fn() })); jest.mock('../../contexts/request_context', () => ({ useRequestActionContext: jest.fn() })); +jest.mock('../../../lib/utils', () => ({ replaceVariables: jest.fn() })); import React from 'react'; import { renderHook, act } from '@testing-library/react-hooks'; @@ -20,6 +21,7 @@ import { ContextValue, ServicesContextProvider } from '../../contexts'; import { serviceContextMock } from '../../contexts/services_context.mock'; import { useRequestActionContext } from '../../contexts/request_context'; import { instance as editorRegistry } from '../../contexts/editor_context/editor_registry'; +import * as utils from '../../../lib/utils'; import { sendRequest } from './send_request'; import { useSendCurrentRequest } from './use_send_current_request'; @@ -35,6 +37,7 @@ describe('useSendCurrentRequest', () => { mockContextValue = serviceContextMock.create(); dispatch = jest.fn(); (useRequestActionContext as jest.Mock).mockReturnValue(dispatch); + (utils.replaceVariables as jest.Mock).mockReturnValue(['test']); }); afterEach(() => { diff --git a/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.ts b/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.ts index 6cd1eaddc3583..87f72571a63e6 100644 --- a/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.ts +++ b/src/plugins/console/public/application/hooks/use_send_current_request/use_send_current_request.ts @@ -16,10 +16,13 @@ import { useRequestActionContext, useServicesContext } from '../../contexts'; import { StorageQuotaError } from '../../components/storage_quota_error'; import { sendRequest } from './send_request'; import { track } from './track'; +import { replaceVariables } from '../../../lib/utils'; +import { StorageKeys } from '../../../services'; +import { DEFAULT_VARIABLES } from '../../../../common/constants'; export const useSendCurrentRequest = () => { const { - services: { history, settings, notifications, trackUiMetric, http, autocompleteInfo }, + services: { history, settings, notifications, trackUiMetric, http, autocompleteInfo, storage }, theme$, } = useServicesContext(); @@ -28,7 +31,9 @@ export const useSendCurrentRequest = () => { return useCallback(async () => { try { const editor = registry.getInputEditor(); - const requests = await editor.getRequestsInRange(); + const variables = storage.get(StorageKeys.VARIABLES, DEFAULT_VARIABLES); + let requests = await editor.getRequestsInRange(); + requests = replaceVariables(requests, variables); if (!requests.length) { notifications.toasts.add( i18n.translate('console.notification.error.noRequestSelectedTitle', { @@ -128,6 +133,7 @@ export const useSendCurrentRequest = () => { } } }, [ + storage, dispatch, http, settings, diff --git a/src/plugins/console/public/application/models/legacy_core_editor/mode/input_highlight_rules.js b/src/plugins/console/public/application/models/legacy_core_editor/mode/input_highlight_rules.js index 6c188eca0f0cc..bb3efc0834694 100644 --- a/src/plugins/console/public/application/models/legacy_core_editor/mode/input_highlight_rules.js +++ b/src/plugins/console/public/application/models/legacy_core_editor/mode/input_highlight_rules.js @@ -61,21 +61,26 @@ export function InputHighlightRules() { 'start', 'url' ), + addEOL(['whitespace', 'variable.template'], /(\s+)(\${\w+})/, 'start', 'url'), addEOL(['whitespace', 'url.protocol_host'], /(\s+)(https?:\/\/[^?\/,]+)/, 'start', 'url'), addEOL(['whitespace', 'url.slash'], /(\s+)(\/)/, 'start', 'url'), addEOL(['whitespace'], /(\s+)/, 'start', 'url') ), url: mergeTokens( + addEOL(['variable.template'], /(\${\w+})/, 'start'), addEOL(['url.part'], /(_sql)/, 'start-sql', 'url-sql'), addEOL(['url.part'], /([^?\/,\s]+)/, 'start'), addEOL(['url.comma'], /(,)/, 'start'), addEOL(['url.slash'], /(\/)/, 'start'), - addEOL(['url.questionmark'], /(\?)/, 'start', 'urlParams') + addEOL(['url.questionmark'], /(\?)/, 'start', 'urlParams'), + addEOL(['whitespace', 'comment.punctuation', 'comment.line'], /(\s+)(\/\/)(.*$)/, 'start') ), urlParams: mergeTokens( + addEOL(['url.param', 'url.equal', 'variable.template'], /([^&=]+)(=)(\${\w+})/, 'start'), addEOL(['url.param', 'url.equal', 'url.value'], /([^&=]+)(=)([^&]*)/, 'start'), addEOL(['url.param'], /([^&=]+)/, 'start'), - addEOL(['url.amp'], /(&)/, 'start') + addEOL(['url.amp'], /(&)/, 'start'), + addEOL(['whitespace', 'comment.punctuation', 'comment.line'], /(\s+)(\/\/)(.*$)/, 'start') ), 'url-sql': mergeTokens( addEOL(['url.part'], /([^?\/,\s]+)/, 'start-sql'), @@ -129,6 +134,8 @@ export function InputHighlightRules() { // Add comment rules to json rule set this.$rules.json.unshift({ include: 'comments' }); + this.$rules.json.unshift({ token: 'variable.template', regex: /("\${\w+}")/ }); + if (this.constructor === InputHighlightRules) { this.normalizeRules(); } diff --git a/src/plugins/console/public/application/models/sense_editor/sense_editor.ts b/src/plugins/console/public/application/models/sense_editor/sense_editor.ts index 37c3799c05119..50ee1cd1d262a 100644 --- a/src/plugins/console/public/application/models/sense_editor/sense_editor.ts +++ b/src/plugins/console/public/application/models/sense_editor/sense_editor.ts @@ -248,7 +248,7 @@ export class SenseEditor { request.url = ''; - while (t && t.type && t.type.indexOf('url') === 0) { + while (t && t.type && (t.type.indexOf('url') === 0 || t.type === 'variable.template')) { request.url += t.value; t = tokenIter.stepForward(); } @@ -256,6 +256,12 @@ export class SenseEditor { // if the url row ends with some spaces, skip them. t = this.parser.nextNonEmptyToken(tokenIter); } + + // If the url row ends with a comment, skip it + while (this.parser.isCommentToken(t)) { + t = tokenIter.stepForward(); + } + let bodyStartLineNumber = (t ? 0 : 1) + tokenIter.getCurrentPosition().lineNumber; // artificially increase end of docs. let dataEndPos: Position; while ( @@ -291,7 +297,6 @@ export class SenseEditor { } const expandedRange = await this.expandRangeToRequestEdges(range); - if (!expandedRange) { return []; } diff --git a/src/plugins/console/public/lib/row_parser.ts b/src/plugins/console/public/lib/row_parser.ts index 5faca5ffc4a7d..55014345ae3cc 100644 --- a/src/plugins/console/public/lib/row_parser.ts +++ b/src/plugins/console/public/lib/row_parser.ts @@ -29,10 +29,10 @@ export default class RowParser { return MODE.BETWEEN_REQUESTS; } const mode = this.editor.getLineState(lineNumber); + if (!mode) { return MODE.BETWEEN_REQUESTS; } // shouldn't really happen - // If another "start" mode is added here because we want to allow for new language highlighting // please see https://github.com/elastic/kibana/pull/51446 for a discussion on why // should consider a different approach. @@ -40,6 +40,19 @@ export default class RowParser { return MODE.IN_REQUEST; } let line = (this.editor.getLineValue(lineNumber) || '').trim(); + + // Check if the line has variables, depending on the request type, (e.g. single line, multi doc requests) return the correct mode + if (line && /(\${\w+})/.test(line)) { + lineNumber++; + line = (this.editor.getLineValue(lineNumber) || '').trim(); + + if (line.startsWith('{')) { + return MODE.REQUEST_START; + } + // next line is another request + // eslint-disable-next-line no-bitwise + return MODE.REQUEST_START | MODE.REQUEST_END; + } if (!line || line.startsWith('#') || line.startsWith('//') || line.startsWith('/*')) { return MODE.BETWEEN_REQUESTS; } // empty line or a comment waiting for a new req to start @@ -140,4 +153,14 @@ export default class RowParser { t = tokenIter.stepBackward(); return t; } + + isCommentToken(token: Token | null) { + return ( + token && + token.type && + (token.type === 'comment.punctuation' || + token.type === 'comment.line' || + token.type === 'comment.block') + ); + } } diff --git a/src/plugins/console/public/lib/utils/index.ts b/src/plugins/console/public/lib/utils/index.ts index 1beb13eb6b3d4..2495f63c7614f 100644 --- a/src/plugins/console/public/lib/utils/index.ts +++ b/src/plugins/console/public/lib/utils/index.ts @@ -8,7 +8,11 @@ import _ from 'lodash'; import { XJson } from '@kbn/es-ui-shared-plugin/public'; -import type { RequestResult } from '../../application/hooks/use_send_current_request/send_request'; +import type { + RequestArgs, + RequestResult, +} from '../../application/hooks/use_send_current_request/send_request'; +import type { DevToolsVariable } from '../../application/components'; const { collapseLiteralStrings, expandLiteralStrings } = XJson; @@ -108,3 +112,66 @@ export const getResponseWithMostSevereStatusCode = (requestData: RequestResult[] .pop(); } }; + +export const replaceVariables = ( + requests: RequestArgs['requests'], + variables: DevToolsVariable[] +) => { + const urlRegex = /(\${\w+})/g; + const bodyRegex = /("\${\w+}")/g; + return requests.map((req) => { + if (urlRegex.test(req.url)) { + req.url = req.url.replaceAll(urlRegex, (match) => { + // Sanitize variable name + const key = match.replace('${', '').replace('}', ''); + const variable = variables.find(({ name }) => name === key); + + return variable?.value ?? match; + }); + } + + if (req.data.length) { + if (bodyRegex.test(req.data[0])) { + const data = req.data[0].replaceAll(bodyRegex, (match) => { + // Sanitize variable name + const key = match.replace('"${', '').replace('}"', ''); + const variable = variables.find(({ name }) => name === key); + + if (variable) { + // All values must be stringified to send a successful request to ES. + const { value } = variable; + + const isStringifiedObject = value.startsWith('{') && value.endsWith('}'); + if (isStringifiedObject) { + return value; + } + + const isStringifiedNumber = !isNaN(parseFloat(value)); + if (isStringifiedNumber) { + return value; + } + + const isStringifiedArray = value.startsWith('[') && value.endsWith(']'); + if (isStringifiedArray) { + return value; + } + + const isStringifiedBool = value === 'true' || value === 'false'; + if (isStringifiedBool) { + return value; + } + + // At this point the value must be an unstringified string, so we have to stringify it. + // Example: 'stringValue' -> '"stringValue"' + return JSON.stringify(value); + } + + return match; + }); + req.data = [data]; + } + } + + return req; + }); +}; diff --git a/src/plugins/console/public/lib/utils/utils.test.js b/src/plugins/console/public/lib/utils/utils.test.js index 8cdd93c3b6ed8..406411b7a32bf 100644 --- a/src/plugins/console/public/lib/utils/utils.test.js +++ b/src/plugins/console/public/lib/utils/utils.test.js @@ -193,4 +193,67 @@ describe('Utils class', () => { expect(utils.getResponseWithMostSevereStatusCode(undefined)).toBe(undefined); }); + + describe('replaceVariables', () => { + function testVariables(data, variables, expected) { + const result = utils.replaceVariables([data], [variables]); + expect(result).toEqual([expected]); + } + + it('should replace variables in url and body', () => { + testVariables( + { url: '${v1}/search', data: ['{\n "f": "${v1}"\n}'] }, + { name: 'v1', value: 'test' }, + { + url: 'test/search', + data: ['{\n "f": "test"\n}'], + } + ); + }); + + describe('with booleans as field value', () => { + testVariables( + { url: 'test', data: ['{\n "f": "${v2}"\n}'] }, + { name: 'v2', value: 'true' }, + { + url: 'test', + data: ['{\n "f": true\n}'], + } + ); + }); + + describe('with objects as field values', () => { + testVariables( + { url: 'test', data: ['{\n "f": "${v3}"\n}'] }, + { name: 'v3', value: '{"f": "test"}' }, + { url: 'test', data: ['{\n "f": {"f": "test"}\n}'] } + ); + }); + + describe('with arrays as field values', () => { + testVariables( + { url: 'test', data: ['{\n "f": "${v5}"\n}'] }, + { name: 'v5', value: '[{"t": "test"}]' }, + { url: 'test', data: ['{\n "f": [{"t": "test"}]\n}'] } + ); + }); + + describe('with numbers as field values', () => { + testVariables( + { url: 'test', data: ['{\n "f": "${v6}"\n}'] }, + { name: 'v6', value: '1' }, + { url: 'test', data: ['{\n "f": 1\n}'] } + ); + }); + + describe('with other variables as field values', () => { + // Currently, variables embedded in other variables' values aren't replaced. + // Once we build this feature, this test will fail and need to be updated. + testVariables( + { url: 'test', data: ['{\n "f": "${v4}"\n}'] }, + { name: 'v4', value: '{"v1": "${v1}", "v6": "${v6}"}' }, + { url: 'test', data: ['{\n "f": {"v1": "${v1}", "v6": "${v6}"}\n}'] } + ); + }); + }); }); diff --git a/src/plugins/console/public/services/storage.ts b/src/plugins/console/public/services/storage.ts index 4d5f897b13403..4b4d051607b8d 100644 --- a/src/plugins/console/public/services/storage.ts +++ b/src/plugins/console/public/services/storage.ts @@ -13,6 +13,7 @@ type IStorageEngine = typeof window.localStorage; export enum StorageKeys { WIDTH = 'widths', FOLDS = 'folds', + VARIABLES = 'variables', } export class Storage { diff --git a/test/functional/apps/console/_console.ts b/test/functional/apps/console/_console.ts index 4f7c3664721e8..9d31a09078261 100644 --- a/test/functional/apps/console/_console.ts +++ b/test/functional/apps/console/_console.ts @@ -12,10 +12,11 @@ import { FtrProviderContext } from '../../ftr_provider_context'; const DEFAULT_REQUEST = ` -GET _search +# Click the Variables button, above, to create your own variables. +GET \${exampleVariable1} // _search { "query": { - "match_all": {} + "\${exampleVariable2}": {} // match_all } } @@ -51,6 +52,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { it('default request response should include `"timed_out" : false`', async () => { const expectedResponseContains = `"timed_out": false`; + await PageObjects.console.selectAllRequests(); await PageObjects.console.clickPlay(); await retry.try(async () => { const actualResponse = await PageObjects.console.getResponse(); diff --git a/test/functional/apps/console/_variables.ts b/test/functional/apps/console/_variables.ts new file mode 100644 index 0000000000000..0918cb6fb846d --- /dev/null +++ b/test/functional/apps/console/_variables.ts @@ -0,0 +1,73 @@ +/* + * 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 expect from '@kbn/expect'; +import { FtrProviderContext } from '../../ftr_provider_context'; + +export default ({ getService, getPageObjects }: FtrProviderContext) => { + const retry = getService('retry'); + const log = getService('log'); + const PageObjects = getPageObjects(['common', 'console', 'header']); + + describe('Console variables', function testConsoleVariables() { + this.tags('includeFirefox'); + before(async () => { + log.debug('navigateTo console'); + await PageObjects.common.navigateToApp('console'); + await retry.try(async () => { + await PageObjects.console.collapseHelp(); + await PageObjects.console.clearTextArea(); + }); + }); + + it('should allow creating a new variable', async () => { + await PageObjects.console.addNewVariable({ name: 'index1', value: 'test' }); + const variables = await PageObjects.console.getVariables(); + log.debug(variables); + expect(variables).to.contain('index1'); + }); + + it('should allow removing a variable', async () => { + await PageObjects.console.addNewVariable({ name: 'index2', value: 'test' }); + await PageObjects.console.removeVariables(); + const variables = await PageObjects.console.getVariables(); + expect(variables).to.eql([]); + }); + + describe('with variables in url', () => { + it('should send a successful request', async () => { + await PageObjects.console.addNewVariable({ name: 'index3', value: '_search' }); + await PageObjects.console.enterRequest('\n GET ${index3}'); + await PageObjects.console.clickPlay(); + await PageObjects.header.waitUntilLoadingHasFinished(); + + await retry.try(async () => { + const status = await PageObjects.console.getResponseStatus(); + expect(status).to.eql(200); + }); + }); + }); + + describe('with variables in request body', () => { + it('should send a successful request', async () => { + await PageObjects.console.addNewVariable({ name: 'query1', value: '{"match_all": {}}' }); + await PageObjects.console.enterRequest('\n GET _search'); + await PageObjects.console.pressEnter(); + await PageObjects.console.enterText(`{\n\t"query": "\${query1}"`); + await PageObjects.console.pressEnter(); + await PageObjects.console.clickPlay(); + await PageObjects.header.waitUntilLoadingHasFinished(); + + await retry.try(async () => { + const status = await PageObjects.console.getResponseStatus(); + expect(status).to.eql(200); + }); + }); + }); + }); +}; diff --git a/test/functional/apps/console/index.js b/test/functional/apps/console/index.js index f827a043176a8..6222110ba489e 100644 --- a/test/functional/apps/console/index.js +++ b/test/functional/apps/console/index.js @@ -21,6 +21,7 @@ export default function ({ getService, loadTestFile }) { loadTestFile(require.resolve('./_autocomplete')); loadTestFile(require.resolve('./_vector_tile')); loadTestFile(require.resolve('./_comments')); + loadTestFile(require.resolve('./_variables')); } }); } diff --git a/test/functional/page_objects/console_page.ts b/test/functional/page_objects/console_page.ts index 3a5c8e3d84db4..e242e70b966a1 100644 --- a/test/functional/page_objects/console_page.ts +++ b/test/functional/page_objects/console_page.ts @@ -7,6 +7,7 @@ */ import { Key } from 'selenium-webdriver'; +import { asyncForEach } from '@kbn/std'; import { FtrService } from '../ftr_provider_context'; import { WebElementWrapper } from '../services/lib/web_element_wrapper'; @@ -14,7 +15,6 @@ export class ConsolePageObject extends FtrService { private readonly testSubjects = this.ctx.getService('testSubjects'); private readonly retry = this.ctx.getService('retry'); private readonly find = this.ctx.getService('find'); - log = this.ctx.getService('log'); public async getVisibleTextFromAceEditor(editor: WebElementWrapper) { const lines = await editor.findAllByClassName('ace_line_group'); @@ -48,6 +48,54 @@ export class ConsolePageObject extends FtrService { await this.testSubjects.click('consoleSettingsButton'); } + public async openVariablesModal() { + await this.testSubjects.click('consoleVariablesButton'); + } + + public async closeVariablesModal() { + await this.testSubjects.click('variablesCancelButton'); + } + + public async addNewVariable({ name, value }: { name: string; value: string }) { + await this.openVariablesModal(); + + // while the variables form opens/loads this may fail, so retry for a while + await this.retry.try(async () => { + await this.testSubjects.click('variablesAddButton'); + + const variableNameInputs = await this.testSubjects.findAll('variablesNameInput'); + await variableNameInputs[variableNameInputs.length - 1].type(name); + + const variableValueInputs = await this.testSubjects.findAll('variablesValueInput'); + await variableValueInputs[variableValueInputs.length - 1].type(value); + }); + + await this.testSubjects.click('variablesSaveButton'); + } + + public async removeVariables() { + await this.openVariablesModal(); + + // while the variables form opens/loads this may fail, so retry for a while + await this.retry.try(async () => { + const buttons = await this.testSubjects.findAll('variablesRemoveButton'); + await asyncForEach(buttons, async (button) => { + await button.click(); + }); + }); + await this.testSubjects.click('variablesSaveButton'); + } + + public async getVariables() { + await this.openVariablesModal(); + const inputs = await this.testSubjects.findAll('variablesNameInput'); + const variables = await Promise.all( + inputs.map(async (input) => await input.getAttribute('value')) + ); + await this.closeVariablesModal(); + return variables; + } + public async setFontSizeSetting(newSize: number) { await this.openSettings(); From b552e4219008315b4436e3f19e7872ed9e98efbb Mon Sep 17 00:00:00 2001 From: Angela Chuang <6295984+angorayc@users.noreply.github.com> Date: Mon, 18 Jul 2022 10:58:54 +0100 Subject: [PATCH 077/111] Refactoring network HTTP to use useSearchStrategy (#136115) * Refactoring network HTTP to use useSearchStrategy * fix unit tests Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../containers/network_http/index.test.tsx | 71 +++++++-- .../network/containers/network_http/index.tsx | 149 +++++++----------- 2 files changed, 114 insertions(+), 106 deletions(-) diff --git a/x-pack/plugins/security_solution/public/network/containers/network_http/index.test.tsx b/x-pack/plugins/security_solution/public/network/containers/network_http/index.test.tsx index f35e9fc5c1872..e91af28390736 100644 --- a/x-pack/plugins/security_solution/public/network/containers/network_http/index.test.tsx +++ b/x-pack/plugins/security_solution/public/network/containers/network_http/index.test.tsx @@ -7,26 +7,75 @@ import { act, renderHook } from '@testing-library/react-hooks'; import { TestProviders } from '../../../common/mock'; -import { ID, useNetworkHttp } from '.'; -import { NetworkType } from '../../store/model'; +import { useNetworkHttp, ID } from '.'; +import { useSearchStrategy } from '../../../common/containers/use_search_strategy'; +import { networkModel } from '../../store'; + +jest.mock('../../../common/containers/use_search_strategy', () => ({ + useSearchStrategy: jest.fn(), +})); +const mockUseSearchStrategy = useSearchStrategy as jest.Mock; +const mockSearch = jest.fn(); + +const props = { + endDate: '2020-07-08T08:20:18.966Z', + indexNames: ['auditbeat-*'], + skip: false, + startDate: '2020-07-07T08:20:18.966Z', + type: networkModel.NetworkType.page, + id: ID, +}; describe('useNetworkHttp', () => { + beforeEach(() => { + jest.clearAllMocks(); + mockUseSearchStrategy.mockReturnValue({ + loading: false, + result: { + edges: [], + totalCount: -1, + pageInfo: { + activePage: 0, + fakeTotalCount: 0, + showMorePagesIndicator: false, + }, + }, + search: mockSearch, + refetch: jest.fn(), + inspect: {}, + }); + }); + + it('runs search', () => { + renderHook(() => useNetworkHttp(props), { + wrapper: TestProviders, + }); + + expect(mockSearch).toHaveBeenCalled(); + }); + + it('does not run search when skip = true', () => { + const localProps = { + ...props, + skip: true, + }; + renderHook(() => useNetworkHttp(localProps), { + wrapper: TestProviders, + }); + + expect(mockSearch).not.toHaveBeenCalled(); + }); + it('skip = true will cancel any running request', () => { - const abortSpy = jest.spyOn(AbortController.prototype, 'abort'); const localProps = { - docValueFields: [], - startDate: '2020-07-07T08:20:18.966Z', - endDate: '2020-07-08T08:20:18.966Z', - id: `${ID}-${NetworkType.page}`, - indexNames: ['cool'], - type: NetworkType.page, - skip: false, + ...props, }; const { rerender } = renderHook(() => useNetworkHttp(localProps), { wrapper: TestProviders, }); localProps.skip = true; act(() => rerender()); - expect(abortSpy).toHaveBeenCalledTimes(4); + expect(mockUseSearchStrategy).toHaveBeenCalledTimes(3); + expect(mockUseSearchStrategy.mock.calls[2][0].abort).toEqual(true); }); }); diff --git a/x-pack/plugins/security_solution/public/network/containers/network_http/index.tsx b/x-pack/plugins/security_solution/public/network/containers/network_http/index.tsx index 830209f16d87d..fbfd2e762b672 100644 --- a/x-pack/plugins/security_solution/public/network/containers/network_http/index.tsx +++ b/x-pack/plugins/security_solution/public/network/containers/network_http/index.tsx @@ -5,16 +5,12 @@ * 2.0. */ -import { noop } from 'lodash/fp'; -import { useState, useEffect, useCallback, useMemo, useRef } from 'react'; +import { useState, useEffect, useCallback, useMemo } from 'react'; import deepEqual from 'fast-deep-equal'; -import { Subscription } from 'rxjs'; -import { isCompleteResponse, isErrorResponse } from '@kbn/data-plugin/common'; import type { ESTermQuery } from '../../../../common/typed_json'; import type { inputsModel } from '../../../common/store'; import { useDeepEqualSelector } from '../../../common/hooks/use_selector'; -import { useKibana } from '../../../common/lib/kibana'; import { createFilter } from '../../../common/containers/helpers'; import { generateTablePaginationOptions } from '../../../common/components/paginated_table/helpers'; import type { networkModel } from '../../store'; @@ -23,21 +19,20 @@ import type { NetworkHttpEdges, PageInfoPaginated, NetworkHttpRequestOptions, - NetworkHttpStrategyResponse, SortField, } from '../../../../common/search_strategy'; import { NetworkQueries } from '../../../../common/search_strategy'; import * as i18n from './translations'; import type { InspectResponse } from '../../../types'; -import { getInspectResponse } from '../../../helpers'; -import { useAppToasts } from '../../../common/hooks/use_app_toasts'; + +import { useSearchStrategy } from '../../../common/containers/use_search_strategy'; export const ID = 'networkHttpQuery'; export interface NetworkHttpArgs { id: string; - ip?: string; inspect: InspectResponse; + ip?: string; isInspected: boolean; loadPage: (newActivePage: number) => void; networkHttp: NetworkHttpEdges[]; @@ -47,14 +42,14 @@ export interface NetworkHttpArgs { } interface UseNetworkHttp { + endDate: string; + filterQuery?: ESTermQuery | string; id: string; - ip?: string; indexNames: string[]; - type: networkModel.NetworkType; - filterQuery?: ESTermQuery | string; - endDate: string; - startDate: string; + ip?: string; skip: boolean; + startDate: string; + type: networkModel.NetworkType; } export const useNetworkHttp = ({ @@ -69,11 +64,6 @@ export const useNetworkHttp = ({ }: UseNetworkHttp): [boolean, NetworkHttpArgs] => { const getHttpSelector = useMemo(() => networkSelectors.httpSelector(), []); const { activePage, limit, sort } = useDeepEqualSelector((state) => getHttpSelector(state, type)); - const { data } = useKibana().services; - const refetch = useRef(noop); - const abortCtrl = useRef(new AbortController()); - const searchSubscription$ = useRef(new Subscription()); - const [loading, setLoading] = useState(false); const [networkHttpRequest, setHostRequest] = useState(null); @@ -93,72 +83,51 @@ export const useNetworkHttp = ({ [limit] ); - const [networkHttpResponse, setNetworkHttpResponse] = useState({ - networkHttp: [], - id, - inspect: { - dsl: [], - response: [], + const { + loading, + result: response, + search, + refetch, + inspect, + } = useSearchStrategy({ + factoryQueryType: NetworkQueries.http, + initialResult: { + edges: [], + totalCount: -1, + pageInfo: { + activePage: 0, + fakeTotalCount: 0, + showMorePagesIndicator: false, + }, }, - isInspected: false, - loadPage: wrappedLoadMore, - pageInfo: { - activePage: 0, - fakeTotalCount: 0, - showMorePagesIndicator: false, - }, - refetch: refetch.current, - totalCount: -1, + errorMessage: i18n.FAIL_NETWORK_HTTP, + abort: skip, }); - const { addError, addWarning } = useAppToasts(); - const networkHttpSearch = useCallback( - (request: NetworkHttpRequestOptions | null) => { - if (request == null || skip) { - return; - } - const asyncSearch = async () => { - abortCtrl.current = new AbortController(); - setLoading(true); - searchSubscription$.current = data.search - .search(request, { - strategy: 'securitySolutionSearchStrategy', - abortSignal: abortCtrl.current.signal, - }) - .subscribe({ - next: (response) => { - if (isCompleteResponse(response)) { - setLoading(false); - setNetworkHttpResponse((prevResponse) => ({ - ...prevResponse, - networkHttp: response.edges, - inspect: getInspectResponse(response, prevResponse.inspect), - pageInfo: response.pageInfo, - refetch: refetch.current, - totalCount: response.totalCount, - })); - searchSubscription$.current.unsubscribe(); - } else if (isErrorResponse(response)) { - setLoading(false); - addWarning(i18n.ERROR_NETWORK_HTTP); - searchSubscription$.current.unsubscribe(); - } - }, - error: (msg) => { - setLoading(false); - addError(msg, { - title: i18n.FAIL_NETWORK_HTTP, - }); - searchSubscription$.current.unsubscribe(); - }, - }); - }; - searchSubscription$.current.unsubscribe(); - abortCtrl.current.abort(); - asyncSearch(); - refetch.current = asyncSearch; - }, - [data.search, addError, addWarning, skip] + const networkHttpResponse = useMemo( + () => ({ + endDate, + networkHttp: response.edges, + id, + inspect, + isInspected: false, + loadPage: wrappedLoadMore, + pageInfo: response.pageInfo, + refetch, + startDate, + totalCount: response.totalCount, + }), + [ + endDate, + id, + inspect, + refetch, + response.edges, + response.pageInfo, + response.totalCount, + startDate, + wrappedLoadMore, + ] ); useEffect(() => { @@ -185,20 +154,10 @@ export const useNetworkHttp = ({ }, [activePage, indexNames, endDate, filterQuery, ip, limit, startDate, sort]); useEffect(() => { - networkHttpSearch(networkHttpRequest); - return () => { - searchSubscription$.current.unsubscribe(); - abortCtrl.current.abort(); - }; - }, [networkHttpRequest, networkHttpSearch]); - - useEffect(() => { - if (skip) { - setLoading(false); - searchSubscription$.current.unsubscribe(); - abortCtrl.current.abort(); + if (!skip && networkHttpRequest) { + search(networkHttpRequest); } - }, [skip]); + }, [networkHttpRequest, search, skip]); return [loading, networkHttpResponse]; }; From f9e2ed4d9f38424676a558c34b74f0a031746c9e Mon Sep 17 00:00:00 2001 From: "Lucas F. da Costa" Date: Mon, 18 Jul 2022 11:24:35 +0100 Subject: [PATCH 078/111] fix MTLS settings for synthetics service in Kibana (#136267) Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../service_api_client.test.ts | 61 +++++++++++++++++++ .../synthetics_service/service_api_client.ts | 18 ++++-- .../synthetics_service.test.ts | 2 +- 3 files changed, 74 insertions(+), 7 deletions(-) create mode 100644 x-pack/plugins/synthetics/server/synthetics_service/service_api_client.test.ts diff --git a/x-pack/plugins/synthetics/server/synthetics_service/service_api_client.test.ts b/x-pack/plugins/synthetics/server/synthetics_service/service_api_client.test.ts new file mode 100644 index 0000000000000..3ff7747f554d7 --- /dev/null +++ b/x-pack/plugins/synthetics/server/synthetics_service/service_api_client.test.ts @@ -0,0 +1,61 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { Logger } from '@kbn/core/server'; +import { ServiceAPIClient } from './service_api_client'; +import { UptimeServerSetup } from '../legacy_uptime/lib/adapters'; +import { ServiceConfig } from '../../common/config'; + +jest.mock('@kbn/server-http-tools', () => ({ + SslConfig: jest.fn().mockImplementation(({ certificate, key }) => ({ certificate, key })), +})); + +describe('getHttpsAgent', () => { + it('does not use certs if basic auth is set', () => { + const apiClient = new ServiceAPIClient( + jest.fn() as unknown as Logger, + { username: 'u', password: 'p' }, + { isDev: true } as UptimeServerSetup + ); + const { options: result } = apiClient.getHttpsAgent('https://localhost:10001'); + expect(result).not.toHaveProperty('cert'); + expect(result).not.toHaveProperty('key'); + }); + + it('rejectUnauthorised is true for requests out of localhost even in dev', () => { + const apiClient = new ServiceAPIClient( + jest.fn() as unknown as Logger, + { tls: { certificate: 'crt', key: 'k' } } as ServiceConfig, + { isDev: true } as UptimeServerSetup + ); + + const { options: result } = apiClient.getHttpsAgent('https://example.com'); + expect(result).toEqual(expect.objectContaining({ rejectUnauthorized: true })); + }); + + it('use rejectUnauthorised as true out of dev for localhost', () => { + const apiClient = new ServiceAPIClient( + jest.fn() as unknown as Logger, + { tls: { certificate: 'crt', key: 'k' } } as ServiceConfig, + { isDev: false } as UptimeServerSetup + ); + + const { options: result } = apiClient.getHttpsAgent('https://localhost:10001'); + expect(result).toEqual(expect.objectContaining({ rejectUnauthorized: true })); + }); + + it('uses certs when defined', () => { + const apiClient = new ServiceAPIClient( + jest.fn() as unknown as Logger, + { tls: { certificate: 'crt', key: 'k' } } as ServiceConfig, + { isDev: false } as UptimeServerSetup + ); + + const { options: result } = apiClient.getHttpsAgent('https://localhost:10001'); + expect(result).toEqual(expect.objectContaining({ cert: 'crt', key: 'k' })); + }); +}); diff --git a/x-pack/plugins/synthetics/server/synthetics_service/service_api_client.ts b/x-pack/plugins/synthetics/server/synthetics_service/service_api_client.ts index 235055b8c2b38..1b2def581c22d 100644 --- a/x-pack/plugins/synthetics/server/synthetics_service/service_api_client.ts +++ b/x-pack/plugins/synthetics/server/synthetics_service/service_api_client.ts @@ -55,22 +55,28 @@ export class ServiceAPIClient { this.server = server; } - getHttpsAgent(url: string) { + getHttpsAgent(targetUrl: string) { + const parsedTargetUrl = new URL(targetUrl); + + const rejectUnauthorized = parsedTargetUrl.hostname !== 'localhost' || !this.server.isDev; + const baseHttpsAgent = new https.Agent({ rejectUnauthorized }); + const config = this.config; - if (url !== this.config.devUrl && this.authorization && this.server.isDev) { - return; - } + + // If using basic-auth, ignore certificate configs + if (this.authorization) return baseHttpsAgent; + if (config.tls && config.tls.certificate && config.tls.key) { const tlsConfig = new SslConfig(config.tls); - const rejectUnauthorized = process.env.NODE_ENV === 'production'; - return new https.Agent({ rejectUnauthorized, cert: tlsConfig.certificate, key: tlsConfig.key, }); } + + return baseHttpsAgent; } async post(data: ServiceData) { diff --git a/x-pack/plugins/synthetics/server/synthetics_service/synthetics_service.test.ts b/x-pack/plugins/synthetics/server/synthetics_service/synthetics_service.test.ts index cd93d5e8817b5..dd3bc128f0b51 100644 --- a/x-pack/plugins/synthetics/server/synthetics_service/synthetics_service.test.ts +++ b/x-pack/plugins/synthetics/server/synthetics_service/synthetics_service.test.ts @@ -40,7 +40,7 @@ describe('SyntheticsService', () => { return { id: `loc-${n}`, label: `Location ${n}`, - url: `example.com/${n}`, + url: `https://example.com/${n}`, geo: { lat: 0, lon: 0, From ea711d2dca444ff67d9bdc9da3811abdf2d77cf2 Mon Sep 17 00:00:00 2001 From: Ido Cohen <90558359+CohenIdo@users.noreply.github.com> Date: Mon, 18 Jul 2022 14:48:23 +0300 Subject: [PATCH 079/111] [Cloud Posture] status api (#134356) --- .../common/constants.ts | 2 +- .../cloud_security_posture/common/types.ts | 26 +- .../public/common/api/use_setup_status_api.ts | 6 +- .../compliance_dashboard.test.tsx | 8 +- .../compliance_dashboard.tsx | 2 +- .../server/lib/fleet_util.ts | 76 +++ .../lib/is_latest_findings_index_exists.ts | 30 ++ .../routes/benchmarks/benchmarks.test.ts | 10 +- .../server/routes/benchmarks/benchmarks.ts | 90 +--- .../server/routes/index.ts | 2 +- .../routes/setup_status/setup_status.test.ts | 83 ---- .../routes/setup_status/setup_status.ts | 65 --- .../server/routes/status/status.test.ts | 431 ++++++++++++++++++ .../server/routes/status/status.ts | 174 +++++++ 14 files changed, 763 insertions(+), 242 deletions(-) create mode 100644 x-pack/plugins/cloud_security_posture/server/lib/fleet_util.ts create mode 100644 x-pack/plugins/cloud_security_posture/server/lib/is_latest_findings_index_exists.ts delete mode 100644 x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.test.ts delete mode 100644 x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.ts create mode 100644 x-pack/plugins/cloud_security_posture/server/routes/status/status.test.ts create mode 100644 x-pack/plugins/cloud_security_posture/server/routes/status/status.ts diff --git a/x-pack/plugins/cloud_security_posture/common/constants.ts b/x-pack/plugins/cloud_security_posture/common/constants.ts index 795e90042a545..40abd28670662 100644 --- a/x-pack/plugins/cloud_security_posture/common/constants.ts +++ b/x-pack/plugins/cloud_security_posture/common/constants.ts @@ -5,7 +5,7 @@ * 2.0. */ -export const INFO_ROUTE_PATH = '/internal/cloud_security_posture/setup_status'; +export const STATUS_ROUTE_PATH = '/internal/cloud_security_posture/status'; export const STATS_ROUTE_PATH = '/internal/cloud_security_posture/stats'; export const BENCHMARKS_ROUTE_PATH = '/internal/cloud_security_posture/benchmarks'; export const UPDATE_RULES_CONFIG_ROUTE_PATH = diff --git a/x-pack/plugins/cloud_security_posture/common/types.ts b/x-pack/plugins/cloud_security_posture/common/types.ts index 43269ca39dd31..b218916ea6b66 100644 --- a/x-pack/plugins/cloud_security_posture/common/types.ts +++ b/x-pack/plugins/cloud_security_posture/common/types.ts @@ -47,10 +47,32 @@ export interface ComplianceDashboardData { trend: PostureTrend[]; } -export interface CspSetupStatus { - latestFindingsIndexStatus: 'applicable' | 'inapplicable'; +export type Status = + | 'indexed' // latest findings index exists and has results + | 'indexing' // index timeout was not surpassed since installation, assumes data is being indexed + | 'index-timeout' // index timeout was surpassed since installation + | 'not-deployed' // no healthy agents were deployed + | 'not-installed'; // number of installed csp integrations is 0; + +interface BaseCspSetupStatus { + latestPackageVersion: string; + installedIntegrations: number; + healthyAgents: number; +} + +interface CspSetupNotInstalledStatus extends BaseCspSetupStatus { + status: Extract; } +interface CspSetupInstalledStatus extends BaseCspSetupStatus { + status: Exclude; + // if installedPackageVersion == undefined but status != 'not-installed' it means the integration was installed in the past and findings were found + // status can be `indexed` but return with undefined package information in this case + installedPackageVersion: string | undefined; +} + +export type CspSetupStatus = CspSetupInstalledStatus | CspSetupNotInstalledStatus; + export interface CspRulesStatus { all: number; enabled: number; diff --git a/x-pack/plugins/cloud_security_posture/public/common/api/use_setup_status_api.ts b/x-pack/plugins/cloud_security_posture/public/common/api/use_setup_status_api.ts index c9ca47679942e..611aef07a27c6 100644 --- a/x-pack/plugins/cloud_security_posture/public/common/api/use_setup_status_api.ts +++ b/x-pack/plugins/cloud_security_posture/public/common/api/use_setup_status_api.ts @@ -8,11 +8,11 @@ import { useQuery } from 'react-query'; import { useKibana } from '../hooks/use_kibana'; import { CspSetupStatus } from '../../../common/types'; -import { INFO_ROUTE_PATH } from '../../../common/constants'; +import { STATUS_ROUTE_PATH } from '../../../common/constants'; -const getCspSetupStatusQueryKey = 'csp_info_key'; +const getCspSetupStatusQueryKey = 'csp_status_key'; export const useCspSetupStatusApi = () => { const { http } = useKibana().services; - return useQuery([getCspSetupStatusQueryKey], () => http.get(INFO_ROUTE_PATH)); + return useQuery([getCspSetupStatusQueryKey], () => http.get(STATUS_ROUTE_PATH)); }; diff --git a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx index 71362c2c92525..7f9b405d1c073 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx +++ b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.test.tsx @@ -196,9 +196,9 @@ describe('', () => { ); }; - it('shows noDataConfig when latestFindingsIndexStatus is inapplicable', () => { + it('shows noDataConfig when status is not deployed', () => { (useCspSetupStatusApi as jest.Mock).mockImplementation(() => - createReactQueryResponse({ status: 'success', data: 'inapplicable' }) + createReactQueryResponse({ status: 'success', data: 'not-deployed' }) ); (useComplianceDashboardDataApi as jest.Mock).mockImplementation(() => createReactQueryResponse({ status: 'success', data: undefined }) @@ -210,11 +210,11 @@ describe('', () => { expect(screen.queryByTestId(DASHBOARD_CONTAINER)).not.toBeInTheDocument(); }); - it('shows dashboard when latestFindingsIndexStatus is applicable', () => { + it('shows dashboard when there are findings in latest findings index', () => { (useCspSetupStatusApi as jest.Mock).mockImplementation(() => ({ isLoading: false, isSuccess: true, - data: { latestFindingsIndexStatus: 'applicable' }, + data: { status: 'indexed' }, })); (useComplianceDashboardDataApi as jest.Mock).mockImplementation(() => ({ diff --git a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx index 606d7671125da..41d006e925852 100644 --- a/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx +++ b/x-pack/plugins/cloud_security_posture/public/pages/compliance_dashboard/compliance_dashboard.tsx @@ -57,7 +57,7 @@ const NoData = ({ onClick }: { onClick: () => void }) => ( export const ComplianceDashboard = () => { const getInfo = useCspSetupStatusApi(); - const isFindingsIndexApplicable = getInfo.data?.latestFindingsIndexStatus === 'applicable'; + const isFindingsIndexApplicable = getInfo.data?.status === 'indexed'; const getDashboardData = useComplianceDashboardDataApi({ enabled: isFindingsIndexApplicable, }); diff --git a/x-pack/plugins/cloud_security_posture/server/lib/fleet_util.ts b/x-pack/plugins/cloud_security_posture/server/lib/fleet_util.ts new file mode 100644 index 0000000000000..e482f0af210a4 --- /dev/null +++ b/x-pack/plugins/cloud_security_posture/server/lib/fleet_util.ts @@ -0,0 +1,76 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import { uniq, map } from 'lodash'; +import type { SavedObjectsClientContract } from '@kbn/core/server'; +import type { + PackagePolicyServiceInterface, + AgentPolicyServiceInterface, + AgentService, +} from '@kbn/fleet-plugin/server'; +import type { + GetAgentPoliciesResponseItem, + PackagePolicy, + AgentPolicy, + ListResult, +} from '@kbn/fleet-plugin/common'; +import { + BENCHMARK_PACKAGE_POLICY_PREFIX, + BenchmarksQueryParams, +} from '../../common/schemas/benchmark'; + +export const PACKAGE_POLICY_SAVED_OBJECT_TYPE = 'ingest-package-policies'; + +const getPackageNameQuery = (packageName: string, benchmarkFilter?: string): string => { + const integrationNameQuery = `${PACKAGE_POLICY_SAVED_OBJECT_TYPE}.package.name:${packageName}`; + const kquery = benchmarkFilter + ? `${integrationNameQuery} AND ${PACKAGE_POLICY_SAVED_OBJECT_TYPE}.name: *${benchmarkFilter}*` + : integrationNameQuery; + + return kquery; +}; + +export const addRunningAgentToAgentPolicy = async ( + agentService: AgentService, + agentPolicies: AgentPolicy[] +): Promise => { + if (!agentPolicies.length) return []; + + return Promise.all( + agentPolicies.map((agentPolicy) => + agentService.asInternalUser + .getAgentStatusForAgentPolicy(agentPolicy.id) + .then((agentStatus) => ({ + ...agentPolicy, + agents: agentStatus.total, + })) + ) + ); +}; + +export const getCspAgentPolicies = async ( + soClient: SavedObjectsClientContract, + packagePolicies: PackagePolicy[], + agentPolicyService: AgentPolicyServiceInterface +): Promise => + agentPolicyService.getByIds(soClient, uniq(map(packagePolicies, 'policy_id'))); + +export const getCspPackagePolicies = ( + soClient: SavedObjectsClientContract, + packagePolicyService: PackagePolicyServiceInterface, + packageName: string, + queryParams: Partial +): Promise> => { + const sortField = queryParams.sort_field?.replaceAll(BENCHMARK_PACKAGE_POLICY_PREFIX, ''); + + return packagePolicyService.list(soClient, { + kuery: getPackageNameQuery(packageName, queryParams.benchmark_name), + page: queryParams.page, + perPage: queryParams.per_page, + sortField, + sortOrder: queryParams.sort_order, + }); +}; diff --git a/x-pack/plugins/cloud_security_posture/server/lib/is_latest_findings_index_exists.ts b/x-pack/plugins/cloud_security_posture/server/lib/is_latest_findings_index_exists.ts new file mode 100644 index 0000000000000..3b43bde45184d --- /dev/null +++ b/x-pack/plugins/cloud_security_posture/server/lib/is_latest_findings_index_exists.ts @@ -0,0 +1,30 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { ElasticsearchClient } from '@kbn/core/server'; +import { CspAppContext } from '../plugin'; +import { LATEST_FINDINGS_INDEX_DEFAULT_NS } from '../../common/constants'; + +export const isLatestFindingsIndexExists = async ( + esClient: ElasticsearchClient, + logger: CspAppContext['logger'] +): Promise => { + try { + const queryResult = await esClient.search({ + index: LATEST_FINDINGS_INDEX_DEFAULT_NS, + query: { + match_all: {}, + }, + size: 1, + }); + + return !!queryResult.hits.hits.length; + } catch (e) { + logger.error(e.message); + return false; + } +}; diff --git a/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.test.ts b/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.test.ts index 9f66386eb4144..2d06ce9f394a7 100644 --- a/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.test.ts +++ b/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.test.ts @@ -20,10 +20,12 @@ import { DEFAULT_BENCHMARKS_PER_PAGE, } from '../../../common/schemas/benchmark'; import { - defineGetBenchmarksRoute, PACKAGE_POLICY_SAVED_OBJECT_TYPE, getCspPackagePolicies, - getAgentPolicies, + getCspAgentPolicies, +} from '../../lib/fleet_util'; +import { + defineGetBenchmarksRoute, createBenchmarkEntry, addPackagePolicyCspRules, } from './benchmarks'; @@ -307,7 +309,7 @@ describe('benchmarks API', () => { const agentPolicyService = createMockAgentPolicyService(); const packagePolicies = [createPackagePolicyMock(), createPackagePolicyMock()]; - await getAgentPolicies(mockSoClient, packagePolicies, agentPolicyService); + await getCspAgentPolicies(mockSoClient, packagePolicies, agentPolicyService); expect(agentPolicyService.getByIds.mock.calls[0][1]).toHaveLength(1); }); @@ -320,7 +322,7 @@ describe('benchmarks API', () => { packagePolicy2.policy_id = 'AnotherId'; const packagePolicies = [packagePolicy1, packagePolicy2]; - await getAgentPolicies(mockSoClient, packagePolicies, agentPolicyService); + await getCspAgentPolicies(mockSoClient, packagePolicies, agentPolicyService); expect(agentPolicyService.getByIds.mock.calls[0][1]).toHaveLength(2); }); diff --git a/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.ts b/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.ts index cd635eabe47ec..0bd6996a05590 100644 --- a/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.ts +++ b/x-pack/plugins/cloud_security_posture/server/routes/benchmarks/benchmarks.ts @@ -4,31 +4,15 @@ * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ - -import { uniq, map } from 'lodash'; import type { SavedObjectsClientContract, SavedObjectsFindResponse } from '@kbn/core/server'; import { transformError } from '@kbn/securitysolution-es-utils'; -import type { - PackagePolicyServiceInterface, - AgentPolicyServiceInterface, - AgentService, -} from '@kbn/fleet-plugin/server'; -import type { - GetAgentPoliciesResponseItem, - PackagePolicy, - AgentPolicy, - ListResult, -} from '@kbn/fleet-plugin/common'; +import type { GetAgentPoliciesResponseItem, PackagePolicy } from '@kbn/fleet-plugin/common'; import { BENCHMARKS_ROUTE_PATH, CLOUD_SECURITY_POSTURE_PACKAGE_NAME, CSP_RULE_SAVED_OBJECT_TYPE, } from '../../../common/constants'; -import { - BENCHMARK_PACKAGE_POLICY_PREFIX, - benchmarksQueryParamsSchema, - BenchmarksQueryParams, -} from '../../../common/schemas/benchmark'; +import { benchmarksQueryParamsSchema } from '../../../common/schemas/benchmark'; import { CspAppContext } from '../../plugin'; import type { Benchmark, CspRulesStatus } from '../../../common/types'; import type { CspRule } from '../../../common/schemas'; @@ -37,73 +21,20 @@ import { isNonNullable, } from '../../../common/utils/helpers'; import { CspRouter } from '../../types'; +import { + addRunningAgentToAgentPolicy, + getCspAgentPolicies, + getCspPackagePolicies, +} from '../../lib/fleet_util'; export const PACKAGE_POLICY_SAVED_OBJECT_TYPE = 'ingest-package-policies'; -const getPackageNameQuery = (packageName: string, benchmarkFilter?: string): string => { - const integrationNameQuery = `${PACKAGE_POLICY_SAVED_OBJECT_TYPE}.package.name:${packageName}`; - const kquery = benchmarkFilter - ? `${integrationNameQuery} AND ${PACKAGE_POLICY_SAVED_OBJECT_TYPE}.name: *${benchmarkFilter}*` - : integrationNameQuery; - - return kquery; -}; - -export const getCspPackagePolicies = ( - soClient: SavedObjectsClientContract, - packagePolicyService: PackagePolicyServiceInterface, - packageName: string, - queryParams: Partial -): Promise> => { - if (!packagePolicyService) { - throw new Error('packagePolicyService is undefined'); - } - - const sortField = queryParams.sort_field?.startsWith(BENCHMARK_PACKAGE_POLICY_PREFIX) - ? queryParams.sort_field.substring(BENCHMARK_PACKAGE_POLICY_PREFIX.length) - : queryParams.sort_field; - - return packagePolicyService?.list(soClient, { - kuery: getPackageNameQuery(packageName, queryParams.benchmark_name), - page: queryParams.page, - perPage: queryParams.per_page, - sortField, - sortOrder: queryParams.sort_order, - }); -}; - -export const getAgentPolicies = async ( - soClient: SavedObjectsClientContract, - packagePolicies: PackagePolicy[], - agentPolicyService: AgentPolicyServiceInterface -): Promise => { - const agentPolicyIds = uniq(map(packagePolicies, 'policy_id')); - const agentPolicies = await agentPolicyService.getByIds(soClient, agentPolicyIds); - - return agentPolicies; -}; - -const addRunningAgentToAgentPolicy = async ( - agentService: AgentService, - agentPolicies: AgentPolicy[] -): Promise => { - if (!agentPolicies?.length) return []; - return Promise.all( - agentPolicies.map((agentPolicy) => - agentService.asInternalUser - .getAgentStatusForAgentPolicy(agentPolicy.id) - .then((agentStatus) => ({ - ...agentPolicy, - agents: agentStatus.total, - })) - ) - ); -}; export interface RulesStatusAggregation { enabled_status: { doc_count: number; }; } + export const getCspRulesStatus = ( soClient: SavedObjectsClientContract, packagePolicy: PackagePolicy @@ -125,6 +56,7 @@ export const getCspRulesStatus = ( }, perPage: 0, }); + return cspRules; }; @@ -138,6 +70,7 @@ export const addPackagePolicyCspRules = async ( enabled: rules.aggregations?.enabled_status.doc_count || 0, disabled: rules.total - (rules.aggregations?.enabled_status.doc_count || 0), }; + return packagePolicyRules; }; @@ -191,6 +124,7 @@ const createBenchmarks = ( const benchmark = createBenchmarkEntry(agentPolicy, cspPackage, cspRulesStatus); return benchmark; }); + return benchmarks; }) ); @@ -229,7 +163,7 @@ export const defineGetBenchmarksRoute = (router: CspRouter, cspContext: CspAppCo query ); - const agentPolicies = await getAgentPolicies( + const agentPolicies = await getCspAgentPolicies( soClient, cspPackagePolicies.items, agentPolicyService diff --git a/x-pack/plugins/cloud_security_posture/server/routes/index.ts b/x-pack/plugins/cloud_security_posture/server/routes/index.ts index dab857ab7118a..e332068b8ee93 100755 --- a/x-pack/plugins/cloud_security_posture/server/routes/index.ts +++ b/x-pack/plugins/cloud_security_posture/server/routes/index.ts @@ -8,7 +8,7 @@ import { defineGetComplianceDashboardRoute } from './compliance_dashboard/compliance_dashboard'; import { defineGetBenchmarksRoute } from './benchmarks/benchmarks'; import { defineUpdateRulesConfigRoute } from './configuration/update_rules_configuration'; -import { defineGetCspSetupStatusRoute } from './setup_status/setup_status'; +import { defineGetCspSetupStatusRoute } from './status/status'; import { defineEsPitRoute } from './es_pit/es_pit'; import { CspAppContext } from '../plugin'; import { CspRouter } from '../types'; diff --git a/x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.test.ts b/x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.test.ts deleted file mode 100644 index e796a14cf9d64..0000000000000 --- a/x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.test.ts +++ /dev/null @@ -1,83 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { CspAppService } from '../../lib/csp_app_services'; -import { CspAppContext } from '../../plugin'; -import { defineGetCspSetupStatusRoute } from './setup_status'; -import { httpServerMock, httpServiceMock, loggingSystemMock } from '@kbn/core/server/mocks'; -// eslint-disable-next-line @kbn/eslint/no-restricted-paths -import { elasticsearchClientMock } from '@kbn/core/server/elasticsearch/client/mocks'; -import { ESSearchResponse } from '@kbn/core/types/elasticsearch'; -import { securityMock } from '@kbn/security-plugin/server/mocks'; - -describe('CspSetupStatus route', () => { - const logger: ReturnType = - loggingSystemMock.createLogger(); - const mockResponse = httpServerMock.createResponseFactory(); - const mockRequest = httpServerMock.createKibanaRequest(); - const mockEsClient = elasticsearchClientMock.createElasticsearchClient(); - const mockContext = { - core: { - elasticsearch: { client: { asCurrentUser: mockEsClient } }, - }, - }; - const router = httpServiceMock.createRouter(); - const cspAppContextService = new CspAppService(); - - const cspContext: CspAppContext = { - logger, - service: cspAppContextService, - security: securityMock.createSetup(), - }; - - beforeEach(() => { - jest.clearAllMocks(); - }); - - it('validate the API route path', async () => { - defineGetCspSetupStatusRoute(router, cspContext); - const [config] = router.get.mock.calls[0]; - - expect(config.path).toEqual('/internal/cloud_security_posture/setup_status'); - }); - - it('validate the API result when there are no findings in latest findings index', async () => { - defineGetCspSetupStatusRoute(router, cspContext); - mockEsClient.search.mockResponse({ - hits: { - hits: [], - }, - } as unknown as ESSearchResponse); - - const [_, handler] = router.get.mock.calls[0]; - - await handler(mockContext, mockRequest, mockResponse); - const [call] = mockResponse.ok.mock.calls; - const body = call[0]!.body; - - expect(mockResponse.ok).toHaveBeenCalledTimes(1); - await expect(body).toEqual({ latestFindingsIndexStatus: 'inapplicable' }); - }); - - it('validate the API result when there are findings in latest findings index', async () => { - defineGetCspSetupStatusRoute(router, cspContext); - mockEsClient.search.mockResponse({ - hits: { - hits: [{}], - }, - } as unknown as ESSearchResponse); - - const [_, handler] = router.get.mock.calls[0]; - - await handler(mockContext, mockRequest, mockResponse); - const [call] = mockResponse.ok.mock.calls; - const body = call[0]!.body; - - expect(mockResponse.ok).toHaveBeenCalledTimes(1); - await expect(body).toEqual({ latestFindingsIndexStatus: 'applicable' }); - }); -}); diff --git a/x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.ts b/x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.ts deleted file mode 100644 index e63158db5fe5c..0000000000000 --- a/x-pack/plugins/cloud_security_posture/server/routes/setup_status/setup_status.ts +++ /dev/null @@ -1,65 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { transformError } from '@kbn/securitysolution-es-utils'; -import { ElasticsearchClient } from '@kbn/core/server'; -import { INFO_ROUTE_PATH, LATEST_FINDINGS_INDEX_DEFAULT_NS } from '../../../common/constants'; -import { CspAppContext } from '../../plugin'; -import { CspRouter } from '../../types'; -import { CspSetupStatus } from '../../../common/types'; - -const getLatestFindingsStatus = async ( - esClient: ElasticsearchClient -): Promise => { - try { - const queryResult = await esClient.search({ - index: LATEST_FINDINGS_INDEX_DEFAULT_NS, - query: { - match_all: {}, - }, - size: 1, - }); - const hasLatestFinding = !!queryResult.hits.hits.length; - - return hasLatestFinding ? 'applicable' : 'inapplicable'; - } catch (e) { - return 'inapplicable'; - } -}; - -export const defineGetCspSetupStatusRoute = (router: CspRouter, cspContext: CspAppContext): void => - router.get( - { - path: INFO_ROUTE_PATH, - validate: false, - options: { - tags: ['access:cloud-security-posture-read'], - }, - }, - async (context, _, response) => { - try { - const esClient = (await context.core).elasticsearch.client.asCurrentUser; - const latestFindingsIndexStatus = await getLatestFindingsStatus(esClient); - - const body: CspSetupStatus = { - latestFindingsIndexStatus, - }; - - return response.ok({ - body, - }); - } catch (err) { - const error = transformError(err); - cspContext.logger.error(`Error while fetching findings status: ${err}`); - - return response.customError({ - body: { message: error.message }, - statusCode: error.statusCode, - }); - } - } - ); diff --git a/x-pack/plugins/cloud_security_posture/server/routes/status/status.test.ts b/x-pack/plugins/cloud_security_posture/server/routes/status/status.test.ts new file mode 100644 index 0000000000000..61227275eaea4 --- /dev/null +++ b/x-pack/plugins/cloud_security_posture/server/routes/status/status.test.ts @@ -0,0 +1,431 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { CspAppContext } from '../../plugin'; +import { defineGetCspSetupStatusRoute, INDEX_TIMEOUT_IN_MINUTES } from './status'; +import { httpServerMock, httpServiceMock, loggingSystemMock } from '@kbn/core/server/mocks'; +import type { ESSearchResponse } from '@kbn/core/types/elasticsearch'; +import { securityMock } from '@kbn/security-plugin/server/mocks'; +import { + createMockAgentPolicyService, + createMockAgentService, + createMockPackageService, + createPackagePolicyServiceMock, + xpackMocks, +} from '@kbn/fleet-plugin/server/mocks'; +import { + AgentClient, + AgentPolicyServiceInterface, + AgentService, + PackageClient, + PackagePolicyServiceInterface, + PackageService, +} from '@kbn/fleet-plugin/server'; +import { + AgentPolicy, + GetAgentStatusResponse, + Installation, + RegistryPackage, +} from '@kbn/fleet-plugin/common'; +import { createPackagePolicyMock } from '@kbn/fleet-plugin/common/mocks'; + +const mockCspPackageInfo: Installation = { + verification_status: 'verified', + installed_kibana: [], + installed_kibana_space_id: 'default', + installed_es: [], + package_assets: [], + es_index_patterns: { findings: 'logs-cloud_security_posture.findings-*' }, + name: 'cloud_security_posture', + version: '0.0.14', + install_version: '0.0.14', + install_status: 'installed', + install_started_at: '2022-06-16T15:24:58.281Z', + install_source: 'registry', +}; + +const mockLatestCspPackageInfo: RegistryPackage = { + format_version: 'mock', + name: 'cloud_security_posture', + title: 'CIS Kubernetes Benchmark', + version: '0.0.14', + release: 'experimental', + description: 'Check Kubernetes cluster compliance with the Kubernetes CIS benchmark.', + type: 'integration', + download: '/epr/cloud_security_posture/cloud_security_posture-0.0.14.zip', + path: '/package/cloud_security_posture/0.0.14', + policy_templates: [], + owner: { github: 'elastic/cloud-security-posture' }, + categories: ['containers', 'kubernetes'], +}; + +describe('CspSetupStatus route', () => { + const router = httpServiceMock.createRouter(); + const logger: ReturnType = + loggingSystemMock.createLogger(); + let mockContext: ReturnType; + let mockPackagePolicyService: jest.Mocked; + let mockAgentPolicyService: jest.Mocked; + let mockAgentService: jest.Mocked; + let mockAgentClient: jest.Mocked; + let mockPackageService: PackageService; + let mockPackageClient: jest.Mocked; + let cspContext: CspAppContext; + + beforeEach(() => { + jest.clearAllMocks(); + + mockContext = xpackMocks.createRequestHandlerContext(); + mockPackagePolicyService = createPackagePolicyServiceMock(); + mockAgentPolicyService = createMockAgentPolicyService(); + mockAgentService = createMockAgentService(); + mockPackageService = createMockPackageService(); + + mockAgentClient = mockAgentService.asInternalUser as jest.Mocked; + mockPackageClient = mockPackageService.asInternalUser as jest.Mocked; + + cspContext = { + logger, + service: { + agentService: mockAgentService, + agentPolicyService: mockAgentPolicyService, + packagePolicyService: mockPackagePolicyService, + packageService: mockPackageService, + }, + security: securityMock.createSetup(), + } as unknown as CspAppContext; + }); + + it('validate the API route path', async () => { + defineGetCspSetupStatusRoute(router, cspContext); + const [config, _] = router.get.mock.calls[0]; + + expect(config.path).toEqual('/internal/cloud_security_posture/status'); + }); + + it('Verify the API result when there are findings and no installed policies', async () => { + mockContext.core.elasticsearch.client.asCurrentUser.search.mockResponseOnce({ + hits: { + hits: [{ Findings: 'foo' }], + }, + } as unknown as ESSearchResponse); + mockPackageClient.fetchFindLatestPackage.mockResolvedValueOnce(mockLatestCspPackageInfo); + + mockPackagePolicyService.list.mockResolvedValueOnce({ + items: [], + total: 0, + page: 1, + perPage: 100, + }); + + // Act + defineGetCspSetupStatusRoute(router, cspContext); + const [_, handler] = router.get.mock.calls[0]; + + const mockResponse = httpServerMock.createResponseFactory(); + const mockRequest = httpServerMock.createKibanaRequest(); + await handler(mockContext, mockRequest, mockResponse); + + // Assert + const [call] = mockResponse.ok.mock.calls; + const body = call[0]?.body; + expect(mockResponse.ok).toHaveBeenCalledTimes(1); + + await expect(body).toEqual({ + status: 'indexed', + latestPackageVersion: '0.0.14', + installedIntegrations: 0, + healthyAgents: 0, + installedPackageVersion: undefined, + }); + }); + + it('Verify the API result when there are findings, installed policies, no running agents', async () => { + mockContext.core.elasticsearch.client.asCurrentUser.search.mockResponseOnce({ + hits: { + hits: [{ Findings: 'foo' }], + }, + } as unknown as ESSearchResponse); + + mockPackageClient.fetchFindLatestPackage.mockResolvedValueOnce(mockLatestCspPackageInfo); + mockPackageClient.getInstallation.mockResolvedValueOnce(mockCspPackageInfo); + + mockPackagePolicyService.list.mockResolvedValueOnce({ + items: [], + total: 3, + page: 1, + perPage: 100, + }); + + // Act + defineGetCspSetupStatusRoute(router, cspContext); + const [_, handler] = router.get.mock.calls[0]; + + const mockResponse = httpServerMock.createResponseFactory(); + const mockRequest = httpServerMock.createKibanaRequest(); + await handler(mockContext, mockRequest, mockResponse); + + // Assert + const [call] = mockResponse.ok.mock.calls; + const body = call[0]?.body; + + expect(mockResponse.ok).toHaveBeenCalledTimes(1); + + await expect(body).toEqual({ + status: 'indexed', + latestPackageVersion: '0.0.14', + installedIntegrations: 3, + healthyAgents: 0, + installedPackageVersion: '0.0.14', + }); + }); + + it('Verify the API result when there are findings, installed policies, running agents', async () => { + mockContext.core.elasticsearch.client.asCurrentUser.search.mockResponseOnce({ + hits: { + hits: [{ Findings: 'foo' }], + }, + } as unknown as ESSearchResponse); + + mockPackageClient.fetchFindLatestPackage.mockResolvedValueOnce(mockLatestCspPackageInfo); + mockPackageClient.getInstallation.mockResolvedValueOnce(mockCspPackageInfo); + + mockPackagePolicyService.list.mockResolvedValueOnce({ + items: [], + total: 3, + page: 1, + perPage: 100, + }); + + mockAgentPolicyService.getByIds.mockResolvedValue([ + { package_policies: createPackagePolicyMock() }, + ] as unknown as AgentPolicy[]); + + mockAgentClient.getAgentStatusForAgentPolicy.mockResolvedValue({ + total: 1, + } as unknown as GetAgentStatusResponse['results']); + + // Act + defineGetCspSetupStatusRoute(router, cspContext); + const [_, handler] = router.get.mock.calls[0]; + + const mockResponse = httpServerMock.createResponseFactory(); + const mockRequest = httpServerMock.createKibanaRequest(); + await handler(mockContext, mockRequest, mockResponse); + + // Assert + const [call] = mockResponse.ok.mock.calls; + const body = call[0]!.body; + + expect(mockResponse.ok).toHaveBeenCalledTimes(1); + + await expect(body).toEqual({ + status: 'indexed', + latestPackageVersion: '0.0.14', + installedIntegrations: 3, + healthyAgents: 1, + installedPackageVersion: '0.0.14', + }); + }); + + it('Verify the API result when there are no findings and no installed policies', async () => { + mockContext.core.elasticsearch.client.asCurrentUser.search.mockResponseOnce({ + hits: { + hits: [], + }, + } as unknown as ESSearchResponse); + mockPackageClient.fetchFindLatestPackage.mockResolvedValueOnce(mockLatestCspPackageInfo); + + mockPackagePolicyService.list.mockResolvedValueOnce({ + items: [], + total: 0, + page: 1, + perPage: 100, + }); + + // Act + defineGetCspSetupStatusRoute(router, cspContext); + const [_, handler] = router.get.mock.calls[0]; + + const mockResponse = httpServerMock.createResponseFactory(); + const mockRequest = httpServerMock.createKibanaRequest(); + await handler(mockContext, mockRequest, mockResponse); + + // Assert + const [call] = mockResponse.ok.mock.calls; + const body = call[0]!.body; + + expect(mockResponse.ok).toHaveBeenCalledTimes(1); + + await expect(body).toMatchObject({ + status: 'not-installed', + latestPackageVersion: '0.0.14', + installedIntegrations: 0, + healthyAgents: 0, + }); + }); + + it('Verify the API result when there are no findings, installed agent but no deployed agent', async () => { + mockContext.core.elasticsearch.client.asCurrentUser.search.mockResponseOnce({ + hits: { + hits: [], + }, + } as unknown as ESSearchResponse); + + mockPackageClient.fetchFindLatestPackage.mockResolvedValueOnce(mockLatestCspPackageInfo); + mockPackageClient.getInstallation.mockResolvedValueOnce(mockCspPackageInfo); + + mockPackagePolicyService.list.mockResolvedValueOnce({ + items: [], + total: 1, + page: 1, + perPage: 100, + }); + + mockAgentPolicyService.getByIds.mockResolvedValue([ + { package_policies: createPackagePolicyMock() }, + ] as unknown as AgentPolicy[]); + + mockAgentClient.getAgentStatusForAgentPolicy.mockResolvedValue({ + total: 0, + } as unknown as GetAgentStatusResponse['results']); + + // Act + defineGetCspSetupStatusRoute(router, cspContext); + + const [_, handler] = router.get.mock.calls[0]; + + const mockResponse = httpServerMock.createResponseFactory(); + const mockRequest = httpServerMock.createKibanaRequest(); + await handler(mockContext, mockRequest, mockResponse); + + // Assert + const [call] = mockResponse.ok.mock.calls; + const body = call[0]!.body; + + expect(mockResponse.ok).toHaveBeenCalledTimes(1); + + await expect(body).toMatchObject({ + status: 'not-deployed', + latestPackageVersion: '0.0.14', + installedIntegrations: 1, + healthyAgents: 0, + installedPackageVersion: '0.0.14', + }); + }); + + it('Verify the API result when there are no findings, installed agent, deployed agent, before index timeout', async () => { + mockContext.core.elasticsearch.client.asCurrentUser.search.mockResponseOnce({ + hits: { + hits: [], + }, + } as unknown as ESSearchResponse); + mockPackageClient.fetchFindLatestPackage.mockResolvedValueOnce(mockLatestCspPackageInfo); + + const currentTime = new Date(); + mockCspPackageInfo.install_started_at = new Date( + currentTime.setMinutes(currentTime.getMinutes() - INDEX_TIMEOUT_IN_MINUTES + 1) + ).toUTCString(); + + mockPackageClient.getInstallation.mockResolvedValueOnce(mockCspPackageInfo); + + mockPackagePolicyService.list.mockResolvedValueOnce({ + items: [], + total: 1, + page: 1, + perPage: 100, + }); + + mockAgentPolicyService.getByIds.mockResolvedValue([ + { package_policies: createPackagePolicyMock() }, + ] as unknown as AgentPolicy[]); + + mockAgentClient.getAgentStatusForAgentPolicy.mockResolvedValue({ + total: 1, + } as unknown as GetAgentStatusResponse['results']); + + // Act + defineGetCspSetupStatusRoute(router, cspContext); + + const [_, handler] = router.get.mock.calls[0]; + + const mockResponse = httpServerMock.createResponseFactory(); + const mockRequest = httpServerMock.createKibanaRequest(); + const [context, req, res] = [mockContext, mockRequest, mockResponse]; + + await handler(context, req, res); + + // Assert + const [call] = mockResponse.ok.mock.calls; + const body = call[0]!.body; + + expect(mockResponse.ok).toHaveBeenCalledTimes(1); + + await expect(body).toMatchObject({ + status: 'indexing', + latestPackageVersion: '0.0.14', + installedIntegrations: 1, + healthyAgents: 1, + installedPackageVersion: '0.0.14', + }); + }); + + it('Verify the API result when there are no findings, installed agent, deployed agent, after index timeout', async () => { + mockContext.core.elasticsearch.client.asCurrentUser.search.mockResponseOnce({ + hits: { + hits: [], + }, + } as unknown as ESSearchResponse); + mockPackageClient.fetchFindLatestPackage.mockResolvedValueOnce(mockLatestCspPackageInfo); + + const currentTime = new Date(); + mockCspPackageInfo.install_started_at = new Date( + currentTime.setMinutes(currentTime.getMinutes() - INDEX_TIMEOUT_IN_MINUTES - 1) + ).toUTCString(); + + mockPackageClient.getInstallation.mockResolvedValueOnce(mockCspPackageInfo); + + mockPackagePolicyService.list.mockResolvedValueOnce({ + items: [], + total: 1, + page: 1, + perPage: 100, + }); + + mockAgentPolicyService.getByIds.mockResolvedValue([ + { package_policies: createPackagePolicyMock() }, + ] as unknown as AgentPolicy[]); + + mockAgentClient.getAgentStatusForAgentPolicy.mockResolvedValue({ + total: 1, + } as unknown as GetAgentStatusResponse['results']); + + // Act + defineGetCspSetupStatusRoute(router, cspContext); + + const [_, handler] = router.get.mock.calls[0]; + + const mockResponse = httpServerMock.createResponseFactory(); + const mockRequest = httpServerMock.createKibanaRequest(); + + await handler(mockContext, mockRequest, mockResponse); + + // Assert + const [call] = mockResponse.ok.mock.calls; + const body = call[0]!.body; + + expect(mockResponse.ok).toHaveBeenCalledTimes(1); + + await expect(body).toMatchObject({ + status: 'index-timeout', + latestPackageVersion: '0.0.14', + installedIntegrations: 1, + healthyAgents: 1, + installedPackageVersion: '0.0.14', + }); + }); +}); diff --git a/x-pack/plugins/cloud_security_posture/server/routes/status/status.ts b/x-pack/plugins/cloud_security_posture/server/routes/status/status.ts new file mode 100644 index 0000000000000..63d5d321330bf --- /dev/null +++ b/x-pack/plugins/cloud_security_posture/server/routes/status/status.ts @@ -0,0 +1,174 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { transformError } from '@kbn/securitysolution-es-utils'; +import type { ElasticsearchClient, SavedObjectsClientContract } from '@kbn/core/server'; +import type { + AgentPolicyServiceInterface, + AgentService, + PackagePolicyServiceInterface, + PackageService, +} from '@kbn/fleet-plugin/server'; +import moment, { MomentInput } from 'moment'; +import { PackagePolicy } from '@kbn/fleet-plugin/common'; +import { CLOUD_SECURITY_POSTURE_PACKAGE_NAME, STATUS_ROUTE_PATH } from '../../../common/constants'; +import type { CspAppContext } from '../../plugin'; +import type { CspRouter } from '../../types'; +import type { CspSetupStatus, Status } from '../../../common/types'; +import { + addRunningAgentToAgentPolicy, + getCspAgentPolicies, + getCspPackagePolicies, +} from '../../lib/fleet_util'; +import { isLatestFindingsIndexExists } from '../../lib/is_latest_findings_index_exists'; + +export const INDEX_TIMEOUT_IN_MINUTES = 10; + +// this function currently returns all agents instead of healthy agents only +const getHealthyAgents = async ( + soClient: SavedObjectsClientContract, + installedIntegrations: PackagePolicy[], + agentPolicyService: AgentPolicyServiceInterface, + agentService: AgentService +): Promise => { + const agentPolicies = await getCspAgentPolicies( + soClient, + installedIntegrations, + agentPolicyService + ); + + const enrichedAgentPolicies = await addRunningAgentToAgentPolicy( + agentService, + agentPolicies || [] + ); + + return enrichedAgentPolicies.reduce( + (previousValue, currentValue) => previousValue + (currentValue.agents || 0), + 0 + ); +}; + +const getMinutesPassedSinceMoment = (momentInput: MomentInput): number => + moment().diff(moment(momentInput), 'minutes'); + +const getStatus = ( + findingsIndexExists: boolean, + installedIntegrations: number, + healthyAgents: number, + minutesPassedSinceInstallation: number +): Status => { + if (findingsIndexExists) return 'indexed'; + if (installedIntegrations === 0) return 'not-installed'; + if (healthyAgents === 0) return 'not-deployed'; + if (minutesPassedSinceInstallation <= INDEX_TIMEOUT_IN_MINUTES) return 'indexing'; + if (minutesPassedSinceInstallation > INDEX_TIMEOUT_IN_MINUTES) return 'index-timeout'; + + throw new Error('Could not determine csp setup status'); +}; + +const getCspSetupStatus = async ( + logger: CspAppContext['logger'], + esClient: ElasticsearchClient, + soClient: SavedObjectsClientContract, + packageService: PackageService, + packagePolicyService: PackagePolicyServiceInterface, + agentPolicyService: AgentPolicyServiceInterface, + agentService: AgentService +): Promise => { + const [findingsIndexExists, installationPackageInfo, latestPackageInfo, installedIntegrations] = + await Promise.all([ + isLatestFindingsIndexExists(esClient, logger), + packageService.asInternalUser.getInstallation(CLOUD_SECURITY_POSTURE_PACKAGE_NAME), + packageService.asInternalUser.fetchFindLatestPackage(CLOUD_SECURITY_POSTURE_PACKAGE_NAME), + getCspPackagePolicies(soClient, packagePolicyService, CLOUD_SECURITY_POSTURE_PACKAGE_NAME, { + per_page: 10000, + }), + ]); + + const healthyAgents = await getHealthyAgents( + soClient, + installedIntegrations.items, + agentPolicyService, + agentService + ); + + const installedIntegrationsTotal = installedIntegrations.total; + const latestPackageVersion = latestPackageInfo.version; + + const status = getStatus( + findingsIndexExists, + installedIntegrationsTotal, + healthyAgents, + getMinutesPassedSinceMoment(installationPackageInfo?.install_started_at || 0) + ); + + if (status === 'not-installed') + return { + status, + latestPackageVersion, + healthyAgents, + installedIntegrations: installedIntegrationsTotal, + }; + + return { + status, + latestPackageVersion, + healthyAgents, + installedIntegrations: installedIntegrationsTotal, + installedPackageVersion: installationPackageInfo?.install_version, + }; +}; + +export const defineGetCspSetupStatusRoute = (router: CspRouter, cspContext: CspAppContext): void => + router.get( + { + path: STATUS_ROUTE_PATH, + validate: false, + options: { + tags: ['access:cloud-security-posture-read'], + }, + }, + async (context, _, response) => { + try { + const esClient = (await context.core).elasticsearch.client.asCurrentUser; + const soClient = (await context.core).savedObjects.client; + + const packageService = cspContext.service.packageService; + const agentService = cspContext.service.agentService; + const agentPolicyService = cspContext.service.agentPolicyService; + const packagePolicyService = cspContext.service.packagePolicyService; + + if (!agentPolicyService || !agentService || !packagePolicyService || !packageService) { + throw new Error(`Failed to get Fleet services`); + } + + const cspSetupStatus = await getCspSetupStatus( + cspContext.logger, + esClient, + soClient, + packageService, + packagePolicyService, + agentPolicyService, + agentService + ); + + const body: CspSetupStatus = cspSetupStatus; + + return response.ok({ + body, + }); + } catch (err) { + const error = transformError(err); + cspContext.logger.error(`Error while fetching status: ${err}`); + + return response.customError({ + body: { message: error.message }, + statusCode: error.statusCode, + }); + } + } + ); From 3216912670fead5c91b3974bf261b8cd0b674ad2 Mon Sep 17 00:00:00 2001 From: Maryam Saeidi Date: Mon, 18 Jul 2022 14:19:52 +0200 Subject: [PATCH 080/111] [Actionable Observability] Change actions button and remove extra status from rule details page (#136389) * Change actions button and remove extra status from rule details page * Update and add more functional tests * Fix functional test * Add actionable-observability as owner of rule_details page * Revert codeowner change related to rule_details --- .../public/pages/rule_details/index.tsx | 57 +++++-------------- .../translations/translations/fr-FR.json | 1 - .../translations/translations/ja-JP.json | 1 - .../translations/translations/zh-CN.json | 1 - .../observability/pages/rule_details_page.ts | 22 ++++--- 5 files changed, 30 insertions(+), 52 deletions(-) diff --git a/x-pack/plugins/observability/public/pages/rule_details/index.tsx b/x-pack/plugins/observability/public/pages/rule_details/index.tsx index fe6439f718ab0..b99a20b8db07a 100644 --- a/x-pack/plugins/observability/public/pages/rule_details/index.tsx +++ b/x-pack/plugins/observability/public/pages/rule_details/index.tsx @@ -15,20 +15,15 @@ import { EuiFlexGroup, EuiFlexItem, EuiFlyoutSize, - EuiButtonIcon, EuiPanel, - EuiTitle, EuiPopover, EuiTabbedContent, EuiEmptyPrompt, EuiSuperSelectOption, + EuiButton, } from '@elastic/eui'; import { - enableRule, - disableRule, - snoozeRule, - unsnoozeRule, deleteRules, useLoadRuleTypes, RuleType, @@ -60,7 +55,6 @@ export function RuleDetailsPage() { triggersActionsUi: { alertsTableConfigurationRegistry, ruleTypeRegistry, - getRuleStatusDropdown, getEditAlertFlyout, getRuleEventLogList, getAlertsStateTable, @@ -98,9 +92,10 @@ export function RuleDetailsPage() { loadNotifyWhenOption(); }, []); - const handleClosePopover = useCallback(() => setIsRuleEditPopoverOpen(false), []); + const togglePopover = () => + setIsRuleEditPopoverOpen((pervIsRuleEditPopoverOpen) => !pervIsRuleEditPopoverOpen); - const handleOpenPopover = useCallback(() => setIsRuleEditPopoverOpen(true), []); + const handleClosePopover = () => setIsRuleEditPopoverOpen(false); const handleRemoveRule = useCallback(() => { setIsRuleEditPopoverOpen(false); @@ -233,20 +228,6 @@ export function RuleDetailsPage() { ? ALERT_STATUS_LICENSE_ERROR : rulesStatusesTranslationsMapping[rule.executionStatus.status]; - const getRuleStatusComponent = () => - getRuleStatusDropdown({ - rule, - enableRule: async () => await enableRule({ http, id: rule.id }), - disableRule: async () => await disableRule({ http, id: rule.id }), - onRuleChanged: () => reloadRule(), - hideSnoozeOption: true, - isEditable: hasEditButton, - snoozeRule: async (snoozeSchedule) => { - await snoozeRule({ http, id: rule.id, snoozeSchedule }); - }, - unsnoozeRule: async (scheduleIds) => await unsnoozeRule({ http, id: rule.id, scheduleIds }), - }); - return ( + + {i18n.translate('xpack.observability.ruleDetails.actionsButtonLabel', { + defaultMessage: 'Actions', + })} + } > @@ -305,17 +289,6 @@ export function RuleDetailsPage() { - - - - {i18n.translate('xpack.observability.ruleDetails.triggreAction.status', { - defaultMessage: 'Status', - })} - - - - {getRuleStatusComponent()} - , ] : [], diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index 780ea4fe5f40c..b5e2d8ca9c98b 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -22528,7 +22528,6 @@ "xpack.observability.ruleDetails.rule.eventLogTabText": "Historique d'exécution", "xpack.observability.ruleDetails.ruleLoadError": "Impossible de charger la règle. Raison : {message}", "xpack.observability.ruleDetails.tagsTitle": "Balises", - "xpack.observability.ruleDetails.triggreAction.status": "Statut", "xpack.observability.rules.addRuleButtonLabel": "Créer une règle", "xpack.observability.rules.deleteSelectedIdsConfirmModal.cancelButtonLabel": "Annuler", "xpack.observability.rules.deleteSelectedIdsConfirmModal.deleteButtonLabel": "Supprimer {numIdsToDelete, plural, one {{singleTitle}} other {# {multipleTitle}}} ", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index 5f076322b4917..b354098f75fe4 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -22515,7 +22515,6 @@ "xpack.observability.ruleDetails.rule.eventLogTabText": "実行履歴", "xpack.observability.ruleDetails.ruleLoadError": "ルールを読み込めません。理由:{message}", "xpack.observability.ruleDetails.tagsTitle": "タグ", - "xpack.observability.ruleDetails.triggreAction.status": "ステータス", "xpack.observability.rules.addRuleButtonLabel": "ルールを作成", "xpack.observability.rules.deleteSelectedIdsConfirmModal.cancelButtonLabel": "キャンセル", "xpack.observability.rules.deleteSelectedIdsConfirmModal.deleteButtonLabel": "{numIdsToDelete, plural, one {{singleTitle}} other {# {multipleTitle}}}を削除 ", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index 5f8dc58573275..a329fd0f181dd 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -22541,7 +22541,6 @@ "xpack.observability.ruleDetails.rule.eventLogTabText": "执行历史记录", "xpack.observability.ruleDetails.ruleLoadError": "无法加载规则。原因:{message}", "xpack.observability.ruleDetails.tagsTitle": "标签", - "xpack.observability.ruleDetails.triggreAction.status": "状态", "xpack.observability.rules.addRuleButtonLabel": "创建规则", "xpack.observability.rules.deleteSelectedIdsConfirmModal.cancelButtonLabel": "取消", "xpack.observability.rules.deleteSelectedIdsConfirmModal.deleteButtonLabel": "删除{numIdsToDelete, plural, one {{singleTitle}} other { # 个{multipleTitle}}} ", diff --git a/x-pack/test/observability_functional/apps/observability/pages/rule_details_page.ts b/x-pack/test/observability_functional/apps/observability/pages/rule_details_page.ts index 2b5f0d82e4d1a..3538736499927 100644 --- a/x-pack/test/observability_functional/apps/observability/pages/rule_details_page.ts +++ b/x-pack/test/observability_functional/apps/observability/pages/rule_details_page.ts @@ -141,27 +141,35 @@ export default ({ getService }: FtrProviderContext) => { before(async () => { await observability.alerts.common.navigateToRuleDetailsByRuleId(logThresholdRuleId); }); - it('should show the more (...) button if user has permissions', async () => { + it('should show the actions button if user has permissions', async () => { await retry.waitFor( - 'More button to be visible', - async () => await testSubjects.exists('moreButton') + 'Actions button to be visible', + async () => await testSubjects.exists('actions') ); }); - it('should shows the rule edit and delete button if user has permissions', async () => { - await testSubjects.click('moreButton'); + it('should show the rule edit and delete button if user has permissions', async () => { + await testSubjects.click('actions'); + await testSubjects.existOrFail('editRuleButton'); await testSubjects.existOrFail('deleteRuleButton'); }); - it('should not let user edit/delete the rule if he has no permissions', async () => { + it('should close actions popover correctly', async () => { + await testSubjects.click('actions'); + + // popover should be closed + await testSubjects.missingOrFail('editRuleButton'); + }); + + it('should not show the actions button if user has no permissions', async () => { await observability.users.setTestUserRole( observability.users.defineBasicObservabilityRole({ logs: ['read'], }) ); await observability.alerts.common.navigateToRuleDetailsByRuleId(logThresholdRuleId); - await testSubjects.missingOrFail('moreButton'); + await testSubjects.missingOrFail('actions'); }); }); }); From bfa1968e40f7b880899791b7f741c45eeb613db3 Mon Sep 17 00:00:00 2001 From: Vitalii Dmyterko <92328789+vitaliidm@users.noreply.github.com> Date: Mon, 18 Jul 2022 13:20:20 +0100 Subject: [PATCH 081/111] [Security Solution][Detections] Adds dry_run for bulk edit and UX handle for bulk edit of ML rule index (#134664) ## Summary Addresses: - https://github.com/elastic/kibana/issues/125512 - https://github.com/elastic/kibana/issues/124918 Implemented - Adds new search query parameter `dry_run` to _bulk_action API, that allows simulate bulk action without actually updating rules. More details in the [ticket](https://github.com/elastic/kibana/issues/125512#issuecomment-1164560158) - Changes the way, modal window is displaying before applying bulk edit action(index patterns, timeline, tags). Before displaying modal window, dry_run bulk action request will be send to get information how many rules can be edited. Based on this result, modal window displays how many rules can be edited and how many can't(with displaying error of validation). Users then can proceed to edit rules, that haven't failed during dry run. Validation errors include at this point - immutable rules - index pattern action on ML rule - default error message handle, that displays error message, with which rule failed ### Before Error displayed when user tried to apply index pattern action to ML rule https://user-images.githubusercontent.com/92328789/175342440-39ede444-d90e-4294-a68f-b9f3c83a81d1.mov Screenshot 2022-06-23 at 16 55 52 ### After Modal window is displayed with message that index pattern action can't be applied to ML rule https://user-images.githubusercontent.com/92328789/174799973-8dc28c14-4413-4837-adf9-644bf4c81297.mov Screenshot 2022-06-21 at 13 34 27 ### Follow-ups: Once merged, create PR for Security Solution API documentation ### Checklist Delete any items that are not applicable to this PR. - [x] [Unit or functional tests](https://www.elastic.co/guide/en/kibana/master/development-tests.html) were updated or added to match the most common scenarios - [x] Any UI touched in this PR is usable by keyboard only (learn more about [keyboard accessibility](https://webaim.org/techniques/keyboard/)) - [x] Any UI touched in this PR does not create any new axe failures (run axe in browser: [FF](https://addons.mozilla.org/en-US/firefox/addon/axe-devtools/), [Chrome](https://chrome.google.com/webstore/detail/axe-web-accessibility-tes/lhdoppojpmngadmnindnejefpokejbdd?hl=en-US)) - [x] This renders correctly on smaller devices using a responsive layout. (You can test this [in your browser](https://www.browserstack.com/guide/responsive-testing-on-local-server)) - [x] This was checked for [cross-browser compatibility](https://www.elastic.co/support/matrix#matrix_browsers) ### Release note - adds dry run mode for /detection_engine/rules/_bulk_action API - displays warning modal when user will try to apply index pattern bulk edit action to Machine Learning rule --- .../security_solution/common/constants.ts | 9 + .../request/perform_bulk_action_schema.ts | 6 + .../detection_rules/bulk_edit_rules.spec.ts | 58 +++-- .../security_solution/cypress/objects/rule.ts | 5 +- .../cypress/tasks/api_calls/rules.ts | 23 +- .../cypress/tasks/rules_bulk_edit.ts | 29 +-- .../containers/detection_engine/rules/api.ts | 5 + .../detection_engine/rules/types.ts | 6 + .../detection_engine/rules/utils.test.ts | 9 + .../detection_engine/rules/utils.ts | 9 + .../bulk_actions/bulk_edit_confirmation.tsx | 76 ------ .../bulk_edit_dry_run_confirmation.tsx | 62 +++++ .../bulk_edit_rule_errors_list.test.tsx | 75 ++++++ .../bulk_edit_rule_errors_list.tsx | 84 ++++++ .../all/bulk_actions/use_bulk_actions.tsx | 56 ++-- .../bulk_actions/use_bulk_actions_dry_run.ts | 114 +++++++++ .../bulk_actions/use_custom_rules_count.ts | 51 ---- .../utils/compute_dry_run_payload.test.ts | 44 ++++ .../utils/compute_dry_run_payload.ts | 57 +++++ .../utils/prepare_search_params.test.ts | 111 ++++++++ .../utils/prepare_search_params.ts | 52 ++++ .../rules/all/rules_tables.tsx | 45 ++-- .../detection_engine/rules/translations.ts | 32 ++- .../rules/perform_bulk_action_route.test.ts | 58 ++++- .../routes/rules/perform_bulk_action_route.ts | 105 +++++++- .../action_to_rules_client_operation.test.ts | 0 .../action_to_rules_client_operation.ts | 0 .../rules/bulk_actions/dry_run.ts | 40 +++ .../rule_params_modifier.test.ts | 0 .../rule_params_modifier.ts | 0 .../split_bulk_edit_actions.test.ts | 0 .../split_bulk_edit_actions.ts | 0 .../rules/bulk_actions/utils.ts | 20 ++ .../rules/bulk_actions/validations.ts | 112 ++++++++ .../detection_engine/rules/bulk_edit_rules.ts | 11 +- .../translations/translations/fr-FR.json | 4 - .../translations/translations/ja-JP.json | 4 - .../translations/translations/zh-CN.json | 4 - .../security_and_spaces/group1/index.ts | 1 + .../group1/perform_bulk_action_dry_run.ts | 242 ++++++++++++++++++ 40 files changed, 1358 insertions(+), 261 deletions(-) delete mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_confirmation.tsx create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_dry_run_confirmation.tsx create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.test.tsx create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.tsx create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions_dry_run.ts delete mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_custom_rules_count.ts create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.test.ts create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.ts create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.test.ts create mode 100644 x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.ts rename x-pack/plugins/security_solution/server/lib/detection_engine/rules/{bulk_edit => bulk_actions}/action_to_rules_client_operation.test.ts (100%) rename x-pack/plugins/security_solution/server/lib/detection_engine/rules/{bulk_edit => bulk_actions}/action_to_rules_client_operation.ts (100%) create mode 100644 x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/dry_run.ts rename x-pack/plugins/security_solution/server/lib/detection_engine/rules/{bulk_edit => bulk_actions}/rule_params_modifier.test.ts (100%) rename x-pack/plugins/security_solution/server/lib/detection_engine/rules/{bulk_edit => bulk_actions}/rule_params_modifier.ts (100%) rename x-pack/plugins/security_solution/server/lib/detection_engine/rules/{bulk_edit => bulk_actions}/split_bulk_edit_actions.test.ts (100%) rename x-pack/plugins/security_solution/server/lib/detection_engine/rules/{bulk_edit => bulk_actions}/split_bulk_edit_actions.ts (100%) create mode 100644 x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/utils.ts create mode 100644 x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/validations.ts create mode 100644 x-pack/test/detection_engine_api_integration/security_and_spaces/group1/perform_bulk_action_dry_run.ts diff --git a/x-pack/plugins/security_solution/common/constants.ts b/x-pack/plugins/security_solution/common/constants.ts index 86793045ad0cd..07731d26f7d18 100644 --- a/x-pack/plugins/security_solution/common/constants.ts +++ b/x-pack/plugins/security_solution/common/constants.ts @@ -443,3 +443,12 @@ export const RULES_MANAGEMENT_FEATURE_TOUR_STORAGE_KEY = export const RULE_DETAILS_EXECUTION_LOG_TABLE_SHOW_METRIC_COLUMNS_STORAGE_KEY = 'securitySolution.ruleDetails.ruleExecutionLog.showMetrics.v8.2'; + +/** + * Error codes that can be thrown during _bulk_action API dry_run call and be processed and displayed to end user + */ +export enum BulkActionsDryRunErrCode { + IMMUTABLE = 'IMMUTABLE', + MACHINE_LEARNING_AUTH = 'MACHINE_LEARNING_AUTH', + MACHINE_LEARNING_INDEX_PATTERN = 'MACHINE_LEARNING_INDEX_PATTERN', +} diff --git a/x-pack/plugins/security_solution/common/detection_engine/schemas/request/perform_bulk_action_schema.ts b/x-pack/plugins/security_solution/common/detection_engine/schemas/request/perform_bulk_action_schema.ts index 641c4858df472..fa33e75e236fd 100644 --- a/x-pack/plugins/security_solution/common/detection_engine/schemas/request/perform_bulk_action_schema.ts +++ b/x-pack/plugins/security_solution/common/detection_engine/schemas/request/perform_bulk_action_schema.ts @@ -37,4 +37,10 @@ export const performBulkActionSchema = t.intersection([ ]), ]); +export const performBulkActionQuerySchema = t.exact( + t.partial({ + dry_run: t.union([t.literal('true'), t.literal('false')]), + }) +); + export type PerformBulkActionSchema = t.TypeOf; diff --git a/x-pack/plugins/security_solution/cypress/integration/detection_rules/bulk_edit_rules.spec.ts b/x-pack/plugins/security_solution/cypress/integration/detection_rules/bulk_edit_rules.spec.ts index d9dddd3d54549..d5368f2bc665c 100644 --- a/x-pack/plugins/security_solution/cypress/integration/detection_rules/bulk_edit_rules.spec.ts +++ b/x-pack/plugins/security_solution/cypress/integration/detection_rules/bulk_edit_rules.spec.ts @@ -43,7 +43,8 @@ import { waitForBulkEditActionToFinish, confirmBulkEditForm, clickAddIndexPatternsMenuItem, - waitForElasticRulesBulkEditModal, + checkElasticRulesCannotBeModified, + checkMachineLearningRulesCannotBeModified, waitForMixedRulesBulkEditModal, openBulkEditAddTagsForm, openBulkEditDeleteTagsForm, @@ -54,7 +55,7 @@ import { hasIndexPatterns } from '../../tasks/rule_details'; import { login, visitWithoutDateRange } from '../../tasks/login'; import { SECURITY_DETECTIONS_RULES_URL } from '../../urls/navigation'; -import { createCustomRule } from '../../tasks/api_calls/rules'; +import { createCustomRule, createMachineLearningRule } from '../../tasks/api_calls/rules'; import { cleanKibana, deleteAlertsAndRules } from '../../tasks/common'; import { getExistingRule, @@ -62,6 +63,7 @@ import { getNewRule, getNewThresholdRule, totalNumberOfPrebuiltRules, + getMachineLearningRule, } from '../../objects/rule'; import { esArchiverResetKibana } from '../../tasks/es_archiver'; @@ -78,6 +80,10 @@ const customRule = { name: RULE_NAME, }; +const expectedNumberOfCustomRulesToBeEdited = 6; +const expectedNumberOfMachineLearningRulesToBeEdited = 1; +const numberOfRulesPerPage = 5; + describe('Detection rules, bulk edit', () => { before(() => { cleanKibana(); @@ -96,7 +102,9 @@ describe('Detection rules, bulk edit', () => { waitForRulesTableToBeLoaded(); }); - it('should show modal windows when Elastic rules selected and edit only custom rules', () => { + it('should show warning modal windows when some of the selected rules cannot be edited', () => { + createMachineLearningRule(getMachineLearningRule(), '7'); + cy.get(LOAD_PREBUILT_RULES_ON_PAGE_HEADER_BTN) .pipe(($el) => $el.trigger('click')) .should('not.exist'); @@ -107,17 +115,25 @@ describe('Detection rules, bulk edit', () => { waitForRulesTableToBeRefreshed(); // check modal window for few selected rules - selectNumberOfRules(5); + selectNumberOfRules(numberOfRulesPerPage); clickAddIndexPatternsMenuItem(); - waitForElasticRulesBulkEditModal(5); + checkElasticRulesCannotBeModified(numberOfRulesPerPage); cy.get(MODAL_CONFIRMATION_BTN).click(); - // Select Elastic rules and custom rules, check mixed rules warning modal window, proceed with editing custom rules + // Select all rules(Elastic rules and custom) cy.get(ELASTIC_RULES_BTN).click(); selectAllRules(); clickAddIndexPatternsMenuItem(); - waitForMixedRulesBulkEditModal(totalNumberOfPrebuiltRules, 6); - cy.get(MODAL_CONFIRMATION_BTN).should('have.text', 'Edit custom rules').click(); + waitForMixedRulesBulkEditModal(expectedNumberOfCustomRulesToBeEdited); + + // check rules that cannot be edited for index patterns: immutable and ML + checkElasticRulesCannotBeModified(totalNumberOfPrebuiltRules); + checkMachineLearningRulesCannotBeModified(expectedNumberOfMachineLearningRulesToBeEdited); + + // proceed with custom rule editing + cy.get(MODAL_CONFIRMATION_BTN) + .should('have.text', `Edit ${expectedNumberOfCustomRulesToBeEdited} Custom rules`) + .click(); typeIndexPatterns([CUSTOM_INDEX_PATTERN_1]); confirmBulkEditForm(); @@ -132,15 +148,15 @@ describe('Detection rules, bulk edit', () => { it('should add/delete/overwrite index patterns in rules', () => { cy.log('Adds index patterns'); - // Switch to 5 rules per page, so we can edit all existing rules, not only ones on a page + // Switch to 5(numberOfRulesPerPage) rules per page, so we can edit all existing rules, not only ones on a page // this way we will use underlying bulk edit API with query parameter, which update all rules based on query search results - changeRowsPerPageTo(5); + changeRowsPerPageTo(numberOfRulesPerPage); selectAllRules(); openBulkEditAddIndexPatternsForm(); typeIndexPatterns([CUSTOM_INDEX_PATTERN_1]); confirmBulkEditForm(); - waitForBulkEditActionToFinish({ rulesCount: 6 }); + waitForBulkEditActionToFinish({ rulesCount: expectedNumberOfCustomRulesToBeEdited }); // check if rule has been updated changeRowsPerPageTo(20); @@ -155,7 +171,7 @@ describe('Detection rules, bulk edit', () => { openBulkEditDeleteIndexPatternsForm(); typeIndexPatterns([CUSTOM_INDEX_PATTERN_1]); confirmBulkEditForm(); - waitForBulkEditActionToFinish({ rulesCount: 6 }); + waitForBulkEditActionToFinish({ rulesCount: expectedNumberOfCustomRulesToBeEdited }); // check if rule has been updated goToTheRuleDetailsOf(RULE_NAME); @@ -170,11 +186,11 @@ describe('Detection rules, bulk edit', () => { .click(); cy.get(RULES_BULK_EDIT_INDEX_PATTERNS_WARNING).should( 'have.text', - 'You’re about to overwrite index patterns for 6 selected rules, press Save to apply changes.' + `You’re about to overwrite index patterns for ${expectedNumberOfCustomRulesToBeEdited} selected rules, press Save to apply changes.` ); typeIndexPatterns(OVERWRITE_INDEX_PATTERNS); confirmBulkEditForm(); - waitForBulkEditActionToFinish({ rulesCount: 6 }); + waitForBulkEditActionToFinish({ rulesCount: expectedNumberOfCustomRulesToBeEdited }); // check if rule has been updated goToTheRuleDetailsOf(RULE_NAME); @@ -183,16 +199,16 @@ describe('Detection rules, bulk edit', () => { it('should add/delete/overwrite tags in rules', () => { cy.log('Add tags to all rules'); - // Switch to 5 rules per page, so we can edit all existing rules, not only ones on a page + // Switch to 5(numberOfRulesPerPage) rules per page, so we can edit all existing rules, not only ones on a page // this way we will use underlying bulk edit API with query parameter, which update all rules based on query search results - changeRowsPerPageTo(5); + changeRowsPerPageTo(numberOfRulesPerPage); selectAllRules(); // open add tags form and add 2 new tags openBulkEditAddTagsForm(); typeTags(TAGS); confirmBulkEditForm(); - waitForBulkEditActionToFinish({ rulesCount: 6 }); + waitForBulkEditActionToFinish({ rulesCount: expectedNumberOfCustomRulesToBeEdited }); // check if all rules have been updated with new tags changeRowsPerPageTo(20); @@ -208,7 +224,7 @@ describe('Detection rules, bulk edit', () => { openBulkEditDeleteTagsForm(); typeTags([TAGS[0]]); confirmBulkEditForm(); - waitForBulkEditActionToFinish({ rulesCount: 6 }); + waitForBulkEditActionToFinish({ rulesCount: expectedNumberOfCustomRulesToBeEdited }); testAllTagsBadges(TAGS.slice(1)); cy.get(RULES_TAGS_FILTER_BTN).contains(/Tags1/); @@ -220,11 +236,11 @@ describe('Detection rules, bulk edit', () => { .click(); cy.get(RULES_BULK_EDIT_TAGS_WARNING).should( 'have.text', - 'You’re about to overwrite tags for 6 selected rules, press Save to apply changes.' + `You’re about to overwrite tags for ${expectedNumberOfCustomRulesToBeEdited} selected rules, press Save to apply changes.` ); typeTags(['overwrite-tag']); confirmBulkEditForm(); - waitForBulkEditActionToFinish({ rulesCount: 6 }); + waitForBulkEditActionToFinish({ rulesCount: expectedNumberOfCustomRulesToBeEdited }); testAllTagsBadges(['overwrite-tag']); }); @@ -232,7 +248,7 @@ describe('Detection rules, bulk edit', () => { it('should not lose rules selection after edit action', () => { const rulesCount = 4; // Switch to 5 rules per page, to have few pages in pagination(ideal way to test auto refresh and selection of few items) - changeRowsPerPageTo(5); + changeRowsPerPageTo(numberOfRulesPerPage); selectNumberOfRules(rulesCount); // open add tags form and add 2 new tags diff --git a/x-pack/plugins/security_solution/cypress/objects/rule.ts b/x-pack/plugins/security_solution/cypress/objects/rule.ts index 2e33c8d1c94bd..4ed06d9b25151 100644 --- a/x-pack/plugins/security_solution/cypress/objects/rule.ts +++ b/x-pack/plugins/security_solution/cypress/objects/rule.ts @@ -89,7 +89,7 @@ export interface ThreatIndicatorRule extends CustomRule { export interface MachineLearningRule { machineLearningJobs: string[]; - anomalyScoreThreshold: string; + anomalyScoreThreshold: number; name: string; description: string; severity: string; @@ -102,6 +102,7 @@ export interface MachineLearningRule { note: string; runsEvery: Interval; lookBack: Interval; + interval?: string; } export const getIndexPatterns = (): string[] => [ @@ -326,7 +327,7 @@ export const getMachineLearningRule = (): MachineLearningRule => ({ 'v3_linux_anomalous_process_all_hosts', 'v3_linux_anomalous_network_activity', ], - anomalyScoreThreshold: '20', + anomalyScoreThreshold: 20, name: 'New ML Rule Test', description: 'The new ML rule description.', severity: 'Critical', diff --git a/x-pack/plugins/security_solution/cypress/tasks/api_calls/rules.ts b/x-pack/plugins/security_solution/cypress/tasks/api_calls/rules.ts index 829870fd35f5b..88616063c6c36 100644 --- a/x-pack/plugins/security_solution/cypress/tasks/api_calls/rules.ts +++ b/x-pack/plugins/security_solution/cypress/tasks/api_calls/rules.ts @@ -5,7 +5,28 @@ * 2.0. */ -import type { CustomRule, ThreatIndicatorRule } from '../../objects/rule'; +import type { CustomRule, ThreatIndicatorRule, MachineLearningRule } from '../../objects/rule'; + +export const createMachineLearningRule = (rule: MachineLearningRule, ruleId = 'ml_rule_testing') => + cy.request({ + method: 'POST', + url: 'api/detection_engine/rules', + body: { + rule_id: ruleId, + risk_score: parseInt(rule.riskScore, 10), + description: rule.description, + interval: rule.interval, + name: rule.name, + severity: rule.severity.toLocaleLowerCase(), + type: 'machine_learning', + from: 'now-50000h', + enabled: false, + machine_learning_job_id: rule.machineLearningJobs, + anomaly_threshold: rule.anomalyScoreThreshold, + }, + headers: { 'kbn-xsrf': 'cypress-creds' }, + failOnStatusCode: false, + }); export const createCustomRule = (rule: CustomRule, ruleId = 'rule_testing', interval = '100m') => cy.request({ diff --git a/x-pack/plugins/security_solution/cypress/tasks/rules_bulk_edit.ts b/x-pack/plugins/security_solution/cypress/tasks/rules_bulk_edit.ts index 387fe63cad9cb..0b38036a4fb9d 100644 --- a/x-pack/plugins/security_solution/cypress/tasks/rules_bulk_edit.ts +++ b/x-pack/plugins/security_solution/cypress/tasks/rules_bulk_edit.ts @@ -78,27 +78,24 @@ export const waitForBulkEditActionToFinish = ({ rulesCount }: { rulesCount: numb }; export const waitForElasticRulesBulkEditModal = (rulesCount: number) => { - cy.get(MODAL_CONFIRMATION_TITLE).should( - 'have.text', - `${rulesCount} Elastic rules cannot be edited` - ); - cy.get(MODAL_CONFIRMATION_BODY).should( - 'have.text', - 'Elastic rules are not modifiable. The update action will only be applied to Custom rules.' + cy.get(MODAL_CONFIRMATION_TITLE).should('have.text', `${rulesCount} rules cannot be edited`); +}; + +export const checkElasticRulesCannotBeModified = (rulesCount: number) => { + cy.get(MODAL_CONFIRMATION_BODY).contains( + `${rulesCount} prebuilt Elastic rules (editing prebuilt rules is not supported)` ); }; -export const waitForMixedRulesBulkEditModal = ( - elasticRulesCount: number, - customRulesCount: number -) => { - cy.get(MODAL_CONFIRMATION_TITLE).should( - 'have.text', - `${elasticRulesCount} Elastic rules cannot be edited` +export const checkMachineLearningRulesCannotBeModified = (rulesCount: number) => { + cy.get(MODAL_CONFIRMATION_BODY).contains( + `${rulesCount} custom Machine Learning rule (these rules don't have index patterns)` ); +}; - cy.get(MODAL_CONFIRMATION_BODY).should( +export const waitForMixedRulesBulkEditModal = (customRulesCount: number) => { + cy.get(MODAL_CONFIRMATION_TITLE).should( 'have.text', - `The update action will only be applied to ${customRulesCount} Custom rules you've selected.` + `The action will only be applied to ${customRulesCount} Custom rules you've selected` ); }; diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts index 055cc07aadcc1..217810e343970 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts @@ -207,6 +207,7 @@ export const pureFetchRuleById = async ({ * @param ids string[] rule ids to select rules to perform bulk action with * @param edit BulkEditActionPayload edit action payload * @param action bulk action to perform + * @param isDryRun enables dry run mode for bulk actions * * @throws An error if response is not OK */ @@ -215,6 +216,7 @@ export const performBulkAction = async ({ query, edit, ids, + isDryRun, }: BulkActionProps): Promise> => KibanaServices.get().http.fetch>( DETECTION_ENGINE_RULES_BULK_ACTION, @@ -226,6 +228,9 @@ export const performBulkAction = async ({ ...(ids ? { ids } : {}), ...(query !== undefined ? { query } : {}), }), + query: { + ...(isDryRun ? { dry_run: isDryRun } : {}), + }, } ); diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/types.ts b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/types.ts index a0e8585579402..1cadf793091a6 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/types.ts +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/types.ts @@ -8,6 +8,7 @@ import * as t from 'io-ts'; import { listArray } from '@kbn/securitysolution-io-ts-list-types'; +import type { Type } from '@kbn/securitysolution-io-ts-alerting-types'; import { risk_score_mapping, threat_query, @@ -52,6 +53,8 @@ import type { UpdateRulesSchema, } from '../../../../../common/detection_engine/schemas/request'; +import type { BulkActionsDryRunErrCode } from '../../../../../common/constants'; + /** * Params is an "record", since it is a type of RuleActionParams which is action templates. * @see x-pack/plugins/alerting/common/rule.ts @@ -223,6 +226,7 @@ export interface FilterOptions { showCustomRules: boolean; showElasticRules: boolean; tags: string[]; + excludeRuleTypes?: Type[]; } export interface FetchRulesResponse { @@ -242,6 +246,7 @@ export interface BulkActionProps { query?: string; ids?: string[]; edit?: BulkActionEditPayload[]; + isDryRun?: boolean; } export interface BulkActionSummary { @@ -259,6 +264,7 @@ export interface BulkActionResult { export interface BulkActionAggregatedError { message: string; status_code: number; + err_code?: BulkActionsDryRunErrCode; rules: Array<{ id: string; name?: string }>; } diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.test.ts b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.test.ts index 6e773e3307e4b..1533e0c02fa62 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.test.ts +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.test.ts @@ -78,4 +78,13 @@ describe('convertRulesFilterToKQL', () => { `alert.attributes.params.immutable: true AND alert.attributes.tags:("tag1" AND "tag2") AND (alert.attributes.name: "foo" OR alert.attributes.params.index: "foo" OR alert.attributes.params.threat.tactic.id: "foo" OR alert.attributes.params.threat.tactic.name: "foo" OR alert.attributes.params.threat.technique.id: "foo" OR alert.attributes.params.threat.technique.name: "foo" OR alert.attributes.params.threat.technique.subtechnique.id: "foo" OR alert.attributes.params.threat.technique.subtechnique.name: "foo")` ); }); + + it('handles presence of "excludeRuleTypes" properly', () => { + const kql = convertRulesFilterToKQL({ + ...filterOptions, + excludeRuleTypes: ['machine_learning', 'saved_query'], + }); + + expect(kql).toBe('NOT alert.attributes.params.type: ("machine_learning" OR "saved_query")'); + }); }); diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.ts b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.ts index 07c2210a329bb..083b75a33c70b 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.ts +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/utils.ts @@ -31,6 +31,7 @@ export const convertRulesFilterToKQL = ({ showElasticRules, filter, tags, + excludeRuleTypes = [], }: FilterOptions): string => { const filters: string[] = []; @@ -56,5 +57,13 @@ export const convertRulesFilterToKQL = ({ filters.push(`(${searchQuery})`); } + if (excludeRuleTypes.length) { + filters.push( + `NOT alert.attributes.params.type: (${excludeRuleTypes + .map((ruleType) => `"${escapeKuery(ruleType)}"`) + .join(' OR ')})` + ); + } + return filters.join(' AND '); }; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_confirmation.tsx b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_confirmation.tsx deleted file mode 100644 index f4c8e7f9bf2a0..0000000000000 --- a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_confirmation.tsx +++ /dev/null @@ -1,76 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import React, { useEffect } from 'react'; -import { EuiConfirmModal } from '@elastic/eui'; -import { FormattedMessage } from '@kbn/i18n-react'; - -import * as i18n from '../../translations'; - -interface BulkEditConfirmationProps { - customRulesCount: number; - elasticRulesCount: number; - onCancel: () => void; - onConfirm: () => void; -} -const BulkEditConfirmationComponent = ({ - onCancel, - onConfirm, - customRulesCount, - elasticRulesCount, -}: BulkEditConfirmationProps) => { - useEffect(() => { - if (elasticRulesCount === 0) { - setTimeout(onConfirm, 0); - } - }, [elasticRulesCount, onConfirm]); - - // proceed straight to edit flyout if there is no Elastic rules - if (elasticRulesCount === 0) { - return null; - } - - if (customRulesCount === 0) { - return ( - - - - ); - } - - return ( - - - - ); -}; - -export const BulkEditConfirmation = React.memo(BulkEditConfirmationComponent); - -BulkEditConfirmation.displayName = 'BulkEditConfirmation'; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_dry_run_confirmation.tsx b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_dry_run_confirmation.tsx new file mode 100644 index 0000000000000..85393b679b39a --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_dry_run_confirmation.tsx @@ -0,0 +1,62 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { EuiConfirmModal } from '@elastic/eui'; + +import * as i18n from '../../translations'; +import type { DryRunResult } from './use_bulk_actions_dry_run'; +import { BulkEditRuleErrorsList } from './bulk_edit_rule_errors_list'; + +interface BulkEditDryRunConfirmationProps { + result?: DryRunResult; + onCancel: () => void; + onConfirm: () => void; +} + +const BulkEditDryRunConfirmationComponent = ({ + onCancel, + onConfirm, + result, +}: BulkEditDryRunConfirmationProps) => { + const { failedRulesCount = 0, succeededRulesCount = 0, ruleErrors = [] } = result ?? {}; + + // if no rule can be edited, modal window that denies bulk edit action will be displayed + if (succeededRulesCount === 0) { + return ( + + + + ); + } + + // if there are rules that can and cannot be edited, modal window that propose edit of some the rules will be displayed + return ( + + + + ); +}; + +export const BulkEditDryRunConfirmation = React.memo(BulkEditDryRunConfirmationComponent); + +BulkEditDryRunConfirmation.displayName = 'BulkEditDryRunConfirmation'; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.test.tsx b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.test.tsx new file mode 100644 index 0000000000000..9d2fc6e8dd37c --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.test.tsx @@ -0,0 +1,75 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { FC } from 'react'; +import React from 'react'; +import { __IntlProvider as IntlProvider } from '@kbn/i18n-react'; +import { render, screen } from '@testing-library/react'; + +import type { DryRunResult } from './use_bulk_actions_dry_run'; +import { BulkEditRuleErrorsList } from './bulk_edit_rule_errors_list'; +import { BulkActionsDryRunErrCode } from '../../../../../../../common/constants'; + +const Wrapper: FC = ({ children }) => { + return ( + + <>{children} + + ); +}; + +describe('Component BulkEditRuleErrorsList', () => { + test('should not render component if no errors present', () => { + const { container } = render(, { wrapper: Wrapper }); + + expect(container.childElementCount).toEqual(0); + }); + + test('should render multiple error messages', () => { + const ruleErrors: DryRunResult['ruleErrors'] = [ + { + message: 'test failure', + ruleIds: ['rule:1', 'rule:2'], + }, + { + message: 'another failure', + ruleIds: ['rule:1'], + }, + ]; + render(, { wrapper: Wrapper }); + + expect(screen.getByText("2 rules can't be edited (test failure)")).toBeInTheDocument(); + expect(screen.getByText("1 rule can't be edited (another failure)")).toBeInTheDocument(); + }); + + test.each([ + [ + BulkActionsDryRunErrCode.IMMUTABLE, + '2 prebuilt Elastic rules (editing prebuilt rules is not supported)', + ], + [ + BulkActionsDryRunErrCode.MACHINE_LEARNING_INDEX_PATTERN, + "2 custom Machine Learning rules (these rules don't have index patterns)", + ], + [ + BulkActionsDryRunErrCode.MACHINE_LEARNING_AUTH, + "2 Machine Learning rules can't be edited (test failure)", + ], + [undefined, "2 rules can't be edited (test failure)"], + ])('should render correct message for "%s" errorCode', (errorCode, value) => { + const ruleErrors: DryRunResult['ruleErrors'] = [ + { + message: 'test failure', + errorCode, + ruleIds: ['rule:1', 'rule:2'], + }, + ]; + render(, { wrapper: Wrapper }); + + expect(screen.getByText(value)).toBeInTheDocument(); + }); +}); diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.tsx b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.tsx new file mode 100644 index 0000000000000..1a95332ac61d5 --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/bulk_edit_rule_errors_list.tsx @@ -0,0 +1,84 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { EuiSpacer } from '@elastic/eui'; +import { FormattedMessage } from '@kbn/i18n-react'; + +import type { DryRunResult } from './use_bulk_actions_dry_run'; +import { BulkActionsDryRunErrCode } from '../../../../../../../common/constants'; + +interface BulkEditRuleErrorsListProps { + ruleErrors: DryRunResult['ruleErrors']; +} + +const BulkEditRuleErrorsListComponent = ({ ruleErrors = [] }: BulkEditRuleErrorsListProps) => { + if (ruleErrors.length === 0) { + return null; + } + + return ( + <> + + +
      + {ruleErrors.map(({ message, errorCode, ruleIds }) => { + const rulesCount = ruleIds.length; + switch (errorCode) { + case BulkActionsDryRunErrCode.IMMUTABLE: + return ( +
    • + +
    • + ); + case BulkActionsDryRunErrCode.MACHINE_LEARNING_INDEX_PATTERN: + return ( +
    • + +
    • + ); + case BulkActionsDryRunErrCode.MACHINE_LEARNING_AUTH: + return ( +
    • + +
    • + ); + default: + return ( +
    • + +
    • + ); + } + })} +
    + + ); +}; + +export const BulkEditRuleErrorsList = React.memo(BulkEditRuleErrorsListComponent); + +BulkEditRuleErrorsList.displayName = 'BulkEditRuleErrorsList'; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions.tsx b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions.tsx index a72807352627f..003e40471c8ba 100644 --- a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions.tsx +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions.tsx @@ -7,7 +7,6 @@ /* eslint-disable complexity */ import React, { useCallback } from 'react'; -import { useQueryClient } from 'react-query'; import type { EuiContextMenuPanelDescriptor } from '@elastic/eui'; import { EuiTextColor, EuiFlexGroup, EuiButton, EuiFlexItem } from '@elastic/eui'; import { euiThemeVars } from '@kbn/ui-theme'; @@ -28,10 +27,10 @@ import * as i18n from '../../translations'; import { executeRulesBulkAction } from '../actions'; import { useHasActionsPrivileges } from '../use_has_actions_privileges'; import { useHasMlPermissions } from '../use_has_ml_permissions'; -import { getCustomRulesCountFromCache } from './use_custom_rules_count'; +import type { ExecuteBulkActionsDryRun } from './use_bulk_actions_dry_run'; import { useAppToasts } from '../../../../../../common/hooks/use_app_toasts'; import { convertRulesFilterToKQL } from '../../../../../containers/detection_engine/rules/utils'; - +import { prepareSearchParams } from './utils/prepare_search_params'; import type { FilterOptions } from '../../../../../containers/detection_engine/rules/types'; import { useInvalidateRules, @@ -49,6 +48,7 @@ interface UseBulkActionsArgs { bulkActionEditType: BulkActionEditType ) => Promise; reFetchTags: () => void; + executeBulkActionsDryRun: ExecuteBulkActionsDryRun; } export const useBulkActions = ({ @@ -57,8 +57,8 @@ export const useBulkActions = ({ confirmBulkEdit, completeBulkEditForm, reFetchTags, + executeBulkActionsDryRun, }: UseBulkActionsArgs) => { - const queryClient = useQueryClient(); const hasMlPermissions = useHasMlPermissions(); const rulesTableContext = useRulesTableContext(); const invalidateRules = useInvalidateRules(); @@ -89,7 +89,7 @@ export const useBulkActions = ({ actions: { setLoadingRules, clearRulesSelection }, } = rulesTableContext; - return useCallback( + const getBulkItemsPopoverContent = useCallback( (closePopover: () => void): EuiContextMenuPanelDescriptor[] => { const selectedRules = rules.filter(({ id }) => selectedRuleIds.includes(id)); @@ -174,6 +174,7 @@ export const useBulkActions = ({ } startTransaction({ name: BULK_RULE_ACTIONS.DELETE }); + await executeRulesBulkAction({ visibleRuleIds: selectedRuleIds, action: BulkAction.delete, @@ -190,8 +191,8 @@ export const useBulkActions = ({ const handleExportAction = async () => { closePopover(); - startTransaction({ name: BULK_RULE_ACTIONS.EXPORT }); + await executeRulesBulkAction({ visibleRuleIds: selectedRuleIds, action: BulkAction.export, @@ -208,12 +209,19 @@ export const useBulkActions = ({ // disabling auto-refresh so user's selected rules won't disappear after table refresh closePopover(); - const customSelectedRuleIds = selectedRules - .filter((rule) => rule.immutable === false) - .map((rule) => rule.id); + const dryRunResult = await executeBulkActionsDryRun({ + action: BulkAction.edit, + editAction: bulkEditActionType, + searchParams: isAllSelected + ? { query: convertRulesFilterToKQL(filterOptions) } + : { ids: selectedRuleIds }, + }); + + // show bulk edit confirmation window only if there is at least one failed rule + const hasFailedRules = (dryRunResult?.failedRulesCount ?? 0) > 0; - // User has cancelled edit action or there are no custom rules to proceed - if ((await confirmBulkEdit()) === false) { + if (hasFailedRules && (await confirmBulkEdit()) === false) { + // User has cancelled edit action or there are no custom rules to proceed return; } @@ -230,10 +238,6 @@ export const useBulkActions = ({ } }; - const customRulesCount = isAllSelected - ? getCustomRulesCountFromCache(queryClient) - : customSelectedRuleIds.length; - // show warning toast only if bulk edit action exceeds 5s // if bulkAction already finished, we won't show toast at all (hence flag "isBulkEditFinished") setTimeout(() => { @@ -245,7 +249,11 @@ export const useBulkActions = ({ title: i18n.BULK_EDIT_WARNING_TOAST_TITLE, text: mountReactNode( <> -

    {i18n.BULK_EDIT_WARNING_TOAST_DESCRIPTION(customRulesCount)}

    +

    + {i18n.BULK_EDIT_WARNING_TOAST_DESCRIPTION( + dryRunResult?.succeededRulesCount ?? 0 + )} +

    @@ -268,14 +276,10 @@ export const useBulkActions = ({ toasts, payload: { edit: [editPayload] }, onFinish: () => hideWarningToast(), - search: isAllSelected - ? { - query: convertRulesFilterToKQL({ - ...filterOptions, - showCustomRules: true, // only edit custom rules, as elastic rule are immutable - }), - } - : { ids: customSelectedRuleIds }, + search: prepareSearchParams({ + ...(isAllSelected ? { filterOptions } : { selectedRuleIds }), + dryRunResult, + }), }); isBulkEditFinished = true; @@ -447,12 +451,14 @@ export const useBulkActions = ({ confirmDeletion, confirmBulkEdit, completeBulkEditForm, - queryClient, filterOptions, getIsMounted, resolveTagsRefetch, updateRulesCache, clearRulesSelection, + executeBulkActionsDryRun, ] ); + + return getBulkItemsPopoverContent; }; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions_dry_run.ts b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions_dry_run.ts new file mode 100644 index 0000000000000..cd0caf63b94d4 --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_bulk_actions_dry_run.ts @@ -0,0 +1,114 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { UseMutateAsyncFunction } from 'react-query'; +import { useMutation } from 'react-query'; + +import type { BulkActionsDryRunErrCode } from '../../../../../../../common/constants'; + +import type { + BulkAction, + BulkActionEditType, +} from '../../../../../../../common/detection_engine/schemas/common/schemas'; +import type { BulkActionResponse } from '../../../../../containers/detection_engine/rules'; +import { performBulkAction } from '../../../../../containers/detection_engine/rules'; +import { computeDryRunPayload } from './utils/compute_dry_run_payload'; + +const BULK_ACTIONS_DRY_RUN_QUERY_KEY = 'bulkActionsDryRun'; + +export interface DryRunResult { + /** + * total number of rules that succeeded validation in dry run + */ + succeededRulesCount?: number; + /** + * total number of rules that failed validation in dry run + */ + failedRulesCount?: number; + /** + * rule failures errors(message and error code) and ids of rules, that failed + */ + ruleErrors: Array<{ + message: string; + errorCode?: BulkActionsDryRunErrCode; + ruleIds: string[]; + }>; +} + +/** + * helper utility that transforms raw BulkActionResponse response to DryRunResult format + * @param response - raw bulk_actions API response ({@link BulkActionResponse}) + * @returns dry run result ({@link DryRunResult}) + */ +const processDryRunResult = (response: BulkActionResponse | undefined): DryRunResult => { + const processed = { + succeededRulesCount: response?.attributes.summary.succeeded, + failedRulesCount: response?.attributes.summary.failed, + ruleErrors: + response?.attributes.errors?.map(({ message, err_code: errorCode, rules }) => ({ + message, + errorCode, + ruleIds: rules.map(({ id }) => id), + })) ?? [], + }; + + return processed; +}; + +export type ExecuteBulkActionsDryRun = UseMutateAsyncFunction< + DryRunResult | undefined, + unknown, + BulkActionsDryRunVariables +>; + +export type UseBulkActionsDryRun = () => { + bulkActionsDryRunResult?: DryRunResult; + isBulkActionsDryRunLoading: boolean; + executeBulkActionsDryRun: ExecuteBulkActionsDryRun; +}; + +interface BulkActionsDryRunVariables { + action?: Exclude; + editAction?: BulkActionEditType; + searchParams: { query?: string } | { ids?: string[] }; +} + +export const useBulkActionsDryRun: UseBulkActionsDryRun = () => { + const { data, mutateAsync, isLoading } = useMutation< + DryRunResult | undefined, + unknown, + BulkActionsDryRunVariables + >([BULK_ACTIONS_DRY_RUN_QUERY_KEY], async ({ searchParams, action, editAction }) => { + if (!action) { + return undefined; + } + + let result: BulkActionResponse; + try { + result = await performBulkAction({ + ...searchParams, + action, + edit: computeDryRunPayload(action, editAction), + isDryRun: true, + }); + } catch (err) { + // if body doesn't have summary data, action failed altogether and no data available for dry run + if ((err.body as BulkActionResponse)?.attributes?.summary?.total === undefined) { + return; + } + result = err.body; + } + + return processDryRunResult(result); + }); + + return { + bulkActionsDryRunResult: data, + isBulkActionsDryRunLoading: isLoading, + executeBulkActionsDryRun: mutateAsync, + }; +}; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_custom_rules_count.ts b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_custom_rules_count.ts deleted file mode 100644 index 11218a6a9bd1f..0000000000000 --- a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/use_custom_rules_count.ts +++ /dev/null @@ -1,51 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import type { QueryClient } from 'react-query'; -import { useQuery } from 'react-query'; - -import { fetchRules } from '../../../../../containers/detection_engine/rules/api'; -import type { FilterOptions } from '../../../../../containers/detection_engine/rules/types'; - -const CUSTOM_RULES_COUNT_QUERY_KEY = 'customRulesCount'; -interface CustomRulesCountData { - customRulesCount: number; -} - -export const getCustomRulesCountFromCache = (queryClient: QueryClient) => - queryClient.getQueryData(CUSTOM_RULES_COUNT_QUERY_KEY)?.customRulesCount ?? - 0; - -type UseCustomRulesCount = (arg: { filterOptions: FilterOptions; enabled: boolean }) => { - customRulesCount: number; - isCustomRulesCountLoading: boolean; -}; - -export const useCustomRulesCount: UseCustomRulesCount = ({ filterOptions, enabled }) => { - const { data, isFetching } = useQuery( - [CUSTOM_RULES_COUNT_QUERY_KEY], - async ({ signal }) => { - const res = await fetchRules({ - pagination: { perPage: 1, page: 1 }, - filterOptions: { ...filterOptions, showCustomRules: true }, - signal, - }); - - return { - customRulesCount: res.total, - }; - }, - { - enabled, - } - ); - - return { - customRulesCount: data?.customRulesCount ?? 0, - isCustomRulesCountLoading: isFetching, - }; -}; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.test.ts b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.test.ts new file mode 100644 index 0000000000000..cbdb34654a99b --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.test.ts @@ -0,0 +1,44 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { + BulkAction, + BulkActionEditType, +} from '../../../../../../../../common/detection_engine/schemas/common/schemas'; + +import { computeDryRunPayload } from './compute_dry_run_payload'; + +describe('computeDryRunPayload', () => { + test.each([ + [BulkAction.export], + [BulkAction.duplicate], + [BulkAction.delete], + [BulkAction.enable], + [BulkAction.disable], + ])('should return payload undefined if action is %s', (action) => { + expect(computeDryRunPayload(action)).toBeUndefined(); + }); + + test('should return payload undefined if bulkEdit action is not defined', () => { + expect(computeDryRunPayload(BulkAction.edit)).toBeUndefined(); + }); + + test.each([ + [BulkActionEditType.set_index_patterns, []], + [BulkActionEditType.delete_index_patterns, []], + [BulkActionEditType.add_index_patterns, []], + [BulkActionEditType.add_tags, []], + [BulkActionEditType.delete_index_patterns, []], + [BulkActionEditType.set_tags, []], + [BulkActionEditType.set_timeline, { timeline_id: '', timeline_title: '' }], + ])('should return correct payload for bulk edit action %s', (editAction, value) => { + const payload = computeDryRunPayload(BulkAction.edit, editAction); + expect(payload).toHaveLength(1); + expect(payload?.[0].type).toEqual(editAction); + expect(payload?.[0].value).toEqual(value); + }); +}); diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.ts b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.ts new file mode 100644 index 0000000000000..d50d6840e899a --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/compute_dry_run_payload.ts @@ -0,0 +1,57 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { BulkActionEditPayload } from '../../../../../../../../common/detection_engine/schemas/common/schemas'; +import { + BulkAction, + BulkActionEditType, +} from '../../../../../../../../common/detection_engine/schemas/common/schemas'; + +/** + * helper utility that creates payload for _bulk_action API in dry mode + * @param {BulkAction} action + * @param {BulkActionEditType | undefined} editAction + * @returns {BulkActionEditPayload[] | undefined} + */ +export const computeDryRunPayload = ( + action: BulkAction, + editAction?: BulkActionEditType +): BulkActionEditPayload[] | undefined => { + if (action !== BulkAction.edit || !editAction) { + return undefined; + } + + switch (editAction) { + case BulkActionEditType.add_index_patterns: + case BulkActionEditType.delete_index_patterns: + case BulkActionEditType.set_index_patterns: + return [ + { + type: editAction, + value: [], + }, + ]; + + case BulkActionEditType.add_tags: + case BulkActionEditType.delete_tags: + case BulkActionEditType.set_tags: + return [ + { + type: editAction, + value: [], + }, + ]; + + case BulkActionEditType.set_timeline: + return [ + { + type: editAction, + value: { timeline_id: '', timeline_title: '' }, + }, + ]; + } +}; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.test.ts b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.test.ts new file mode 100644 index 0000000000000..f86d98670f117 --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.test.ts @@ -0,0 +1,111 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { DryRunResult } from '../use_bulk_actions_dry_run'; +import type { FilterOptions } from '../../../../../../containers/detection_engine/rules/types'; + +import { convertRulesFilterToKQL } from '../../../../../../containers/detection_engine/rules/utils'; +import { BulkActionsDryRunErrCode } from '../../../../../../../../common/constants'; + +import { prepareSearchParams } from './prepare_search_params'; + +jest.mock('../../../../../../containers/detection_engine/rules/utils', () => ({ + convertRulesFilterToKQL: jest.fn().mockReturnValue('str'), +})); + +const mockConvertRulesFilterToKQL = convertRulesFilterToKQL as jest.Mock; + +describe('prepareSearchParams', () => { + test('should remove ids from selectedRuleIds if dryRunResult has failed ids', () => { + const selectedRuleIds = ['rule:1', 'rule:2', 'rule:3']; + const dryRunResult: DryRunResult = { + ruleErrors: [ + { + message: 'test failure', + ruleIds: ['rule:2'], + }, + { + message: 'test failure N2', + ruleIds: ['rule:3'], + }, + ], + }; + const result = prepareSearchParams({ + selectedRuleIds, + dryRunResult, + }); + + expect(result.ids).toEqual(['rule:1']); + }); + + test.each([ + [ + BulkActionsDryRunErrCode.MACHINE_LEARNING_INDEX_PATTERN, + { + filter: '', + tags: [], + showCustomRules: false, + showElasticRules: false, + excludeRuleTypes: ['machine_learning'], + }, + ], + [ + BulkActionsDryRunErrCode.MACHINE_LEARNING_AUTH, + { + filter: '', + tags: [], + showCustomRules: false, + showElasticRules: false, + excludeRuleTypes: ['machine_learning'], + }, + ], + [ + BulkActionsDryRunErrCode.IMMUTABLE, + { + filter: '', + tags: [], + showCustomRules: true, + showElasticRules: false, + }, + ], + [ + undefined, + { + filter: '', + tags: [], + showCustomRules: false, + showElasticRules: false, + }, + ], + ])( + 'should call convertRulesFilterToKQL with correct filter if "%s" errorCode present in dryRunResult', + (errorCode, value) => { + const filterOptions: FilterOptions = { + filter: '', + tags: [], + showCustomRules: false, + showElasticRules: false, + }; + const dryRunResult: DryRunResult = { + ruleErrors: [ + { + message: 'test failure', + errorCode, + ruleIds: ['rule:2'], + }, + ], + }; + const result = prepareSearchParams({ + filterOptions, + dryRunResult, + }); + + expect(mockConvertRulesFilterToKQL).toHaveBeenCalledWith(value); + expect(result.query).toEqual(expect.any(String)); + } + ); +}); diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.ts b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.ts new file mode 100644 index 0000000000000..c7dfdfc129969 --- /dev/null +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/bulk_actions/utils/prepare_search_params.ts @@ -0,0 +1,52 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { DryRunResult } from '../use_bulk_actions_dry_run'; +import type { FilterOptions } from '../../../../../../containers/detection_engine/rules/types'; + +import { convertRulesFilterToKQL } from '../../../../../../containers/detection_engine/rules/utils'; +import { BulkActionsDryRunErrCode } from '../../../../../../../../common/constants'; + +type PrepareSearchFilterProps = + | { selectedRuleIds: string[]; dryRunResult?: DryRunResult } + | { filterOptions: FilterOptions; dryRunResult?: DryRunResult }; + +/** + * helper methods to prepare search params for bulk actions based on results of previous dry run + * It excludes failed rules from search and perform bulk action on possible successfully edited rules + * @param dryRunResult {@link DryRunResult} result of API _bulk_action dry_run + * @param {string[]} selectedRuleIds - list of selected rule ids + * @param filterOptions {@link FilterOptions} find filter + * @returns either list of ids or KQL search query + */ +export const prepareSearchParams = ({ dryRunResult, ...props }: PrepareSearchFilterProps) => { + // if selectedRuleIds present, filter out rules that failed during dry run + if ('selectedRuleIds' in props) { + const failedRuleIdsSet = new Set(dryRunResult?.ruleErrors.flatMap(({ ruleIds }) => ruleIds)); + + return { ids: props.selectedRuleIds.filter((id) => !failedRuleIdsSet.has(id)) }; + } + + // otherwise create filter that excludes failed results based on dry run errors + let modifiedFilterOptions = { ...props.filterOptions }; + dryRunResult?.ruleErrors.forEach(({ errorCode }) => { + switch (errorCode) { + case BulkActionsDryRunErrCode.IMMUTABLE: + modifiedFilterOptions = { ...modifiedFilterOptions, showCustomRules: true }; + break; + case BulkActionsDryRunErrCode.MACHINE_LEARNING_INDEX_PATTERN: + case BulkActionsDryRunErrCode.MACHINE_LEARNING_AUTH: + modifiedFilterOptions = { + ...modifiedFilterOptions, + excludeRuleTypes: [...(modifiedFilterOptions.excludeRuleTypes ?? []), 'machine_learning'], + }; + break; + } + }); + + return { query: convertRulesFilterToKQL(modifiedFilterOptions) }; +}; diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/rules_tables.tsx b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/rules_tables.tsx index 70dc23e3dd237..9dd6ca7529b27 100644 --- a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/rules_tables.tsx +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/all/rules_tables.tsx @@ -5,8 +5,6 @@ * 2.0. */ -/* eslint-disable complexity */ - import { EuiBasicTable, EuiConfirmModal, @@ -14,8 +12,8 @@ import { EuiLoadingContent, EuiProgress, } from '@elastic/eui'; -import { partition } from 'lodash/fp'; import React, { useCallback, useEffect, useMemo, useRef } from 'react'; +import { AllRulesTabs } from './rules_table_toolbar'; import { RULES_TABLE_PAGE_SIZE_OPTIONS } from '../../../../../../common/constants'; import { Loader } from '../../../../../common/components/loader'; import { useBoolState } from '../../../../../common/hooks/use_bool_state'; @@ -28,18 +26,17 @@ import { useTags } from '../../../../containers/detection_engine/rules/use_tags' import { getPrePackagedRuleStatus } from '../helpers'; import * as i18n from '../translations'; import type { EuiBasicTableOnChange } from '../types'; -import { BulkEditConfirmation } from './bulk_actions/bulk_edit_confirmation'; -import { BulkEditFlyout } from './bulk_actions/bulk_edit_flyout'; -import { useBulkActions } from './bulk_actions/use_bulk_actions'; -import { useBulkEditFormFlyout } from './bulk_actions/use_bulk_edit_form_flyout'; -import { useCustomRulesCount } from './bulk_actions/use_custom_rules_count'; +import { useMonitoringColumns, useRulesColumns } from './use_columns'; import { showRulesTable } from './helpers'; import { useRulesTableContext } from './rules_table/rules_table_context'; import { useAsyncConfirmation } from './rules_table/use_async_confirmation'; import { RulesTableFilters } from './rules_table_filters/rules_table_filters'; -import { AllRulesTabs } from './rules_table_toolbar'; -import { useMonitoringColumns, useRulesColumns } from './use_columns'; import { AllRulesUtilityBar } from './utility_bar'; +import { useBulkActionsDryRun } from './bulk_actions/use_bulk_actions_dry_run'; +import { useBulkEditFormFlyout } from './bulk_actions/use_bulk_edit_form_flyout'; +import { BulkEditDryRunConfirmation } from './bulk_actions/bulk_edit_dry_run_confirmation'; +import { BulkEditFlyout } from './bulk_actions/bulk_edit_flyout'; +import { useBulkActions } from './bulk_actions/use_bulk_actions'; const INITIAL_SORT_FIELD = 'enabled'; @@ -137,11 +134,6 @@ export const RulesTables = React.memo( onFinish: hideBulkEditConfirmation, }); - const { customRulesCount, isCustomRulesCountLoading } = useCustomRulesCount({ - enabled: isBulkEditConfirmationVisible && isAllSelected, - filterOptions, - }); - const { bulkEditActionType, isBulkEditFlyoutVisible, @@ -153,11 +145,8 @@ export const RulesTables = React.memo( const selectedItemsCount = isAllSelected ? pagination.total : selectedRuleIds.length; const hasPagination = pagination.total > pagination.perPage; - const [selectedElasticRuleIds, selectedCustomRuleIds] = useMemo(() => { - const ruleImmutabilityMap = new Map(rules.map((rule) => [rule.id, rule.immutable])); - const predicate = (id: string) => ruleImmutabilityMap.get(id); - return partition(predicate, selectedRuleIds); - }, [rules, selectedRuleIds]); + const { bulkActionsDryRunResult, isBulkActionsDryRunLoading, executeBulkActionsDryRun } = + useBulkActionsDryRun(); const getBulkItemsPopoverContent = useBulkActions({ filterOptions, @@ -165,6 +154,7 @@ export const RulesTables = React.memo( confirmBulkEdit, completeBulkEditForm, reFetchTags, + executeBulkActionsDryRun, }); const paginationMemo = useMemo( @@ -322,21 +312,16 @@ export const RulesTables = React.memo(

    {i18n.DELETE_CONFIRMATION_BODY}

    )} - {isBulkEditConfirmationVisible && !isCustomRulesCountLoading && ( - )} {isBulkEditFlyoutVisible && bulkEditActionType !== undefined && ( ( onRefreshSwitch={handleAutoRefreshSwitch} isAllSelected={isAllSelected} onToggleSelectAll={toggleSelectAll} - isBulkActionInProgress={isCustomRulesCountLoading || loadingRulesAction != null} + isBulkActionInProgress={isBulkActionsDryRunLoading || loadingRulesAction != null} hasDisabledActions={loadingRulesAction != null} hasBulkActions /> diff --git a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/translations.ts b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/translations.ts index cb6345517134b..703e5feb836ca 100644 --- a/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/translations.ts +++ b/x-pack/plugins/security_solution/public/detections/pages/detection_engine/rules/translations.ts @@ -230,13 +230,22 @@ export const BULK_EDIT_WARNING_TOAST_NOTIFY = i18n.translate( } ); -export const BULK_EDIT_CONFIRMATION_TITLE = (elasticRulesCount: number) => +export const BULK_EDIT_CONFIRMATION_DENIED_TITLE = (rulesCount: number) => i18n.translate( - 'xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationTitle', + 'xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationDeniedTitle', { - values: { elasticRulesCount }, + values: { rulesCount }, + defaultMessage: '{rulesCount, plural, =1 {# rule} other {# rules}} cannot be edited', + } + ); + +export const BULK_EDIT_CONFIRMATION_PARTLY_TITLE = (customRulesCount: number) => + i18n.translate( + 'xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationPartlyTitle', + { + values: { customRulesCount }, defaultMessage: - '{elasticRulesCount, plural, =1 {# Elastic rule} other {# Elastic rules}} cannot be edited', + "The action will only be applied to {customRulesCount, plural, =1 {# Custom rule} other {# Custom rules}} you've selected", } ); @@ -247,13 +256,22 @@ export const BULK_EDIT_CONFIRMATION_CANCEL = i18n.translate( } ); -export const BULK_EDIT_CONFIRMATION_CONFIRM = i18n.translate( - 'xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmation.confirmButtonLabel', +export const BULK_EDIT_CONFIRMATION_CLOSE = i18n.translate( + 'xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmationCloseButtonLabel', { - defaultMessage: 'Edit custom rules', + defaultMessage: 'Close', } ); +export const BULK_EDIT_CONFIRMATION_CONFIRM = (customRulesCount: number) => + i18n.translate( + 'xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmation.confirmButtonLabel', + { + values: { customRulesCount }, + defaultMessage: 'Edit {customRulesCount, plural, =1 {# Custom rule} other {# Custom rules}}', + } + ); + export const BULK_EDIT_FLYOUT_FORM_SAVE = i18n.translate( 'xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditFlyoutForm.saveButtonLabel', { diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.test.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.test.ts index c51d82c539db6..1438905a5c079 100644 --- a/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.test.ts +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.test.ts @@ -5,7 +5,10 @@ * 2.0. */ -import { DETECTION_ENGINE_RULES_BULK_ACTION } from '../../../../../common/constants'; +import { + DETECTION_ENGINE_RULES_BULK_ACTION, + BulkActionsDryRunErrCode, +} from '../../../../../common/constants'; import { mlServicesMock, mlAuthzMock as mockMlAuthzFactory } from '../../../machine_learning/mocks'; import { buildMlAuthz } from '../../../machine_learning/authz'; import { @@ -168,6 +171,46 @@ describe('perform_bulk_action', () => { errors: [ { message: 'mocked validation message', + err_code: BulkActionsDryRunErrCode.MACHINE_LEARNING_AUTH, + status_code: 403, + rules: [ + { + id: '04128c15-0d1b-4716-a4c5-46997ac7f3bd', + name: 'Detect Root/Admin Users', + }, + ], + }, + ], + results: someBulkActionResults(), + summary: { + failed: 1, + succeeded: 0, + total: 1, + }, + }, + message: 'Bulk edit failed', + status_code: 500, + }); + }); + + it('returns error if machine learning rule validation fails in dry run mode', async () => { + (buildMlAuthz as jest.Mock).mockReturnValueOnce({ + validateRuleType: jest + .fn() + .mockResolvedValue({ valid: false, message: 'mocked validation message' }), + }); + const response = await server.inject( + { ...getBulkActionRequest(), query: { dry_run: 'true' } }, + requestContextMock.convertContext(context) + ); + + expect(response.status).toEqual(500); + expect(response.body).toEqual({ + attributes: { + errors: [ + { + message: 'mocked validation message', + err_code: BulkActionsDryRunErrCode.MACHINE_LEARNING_AUTH, status_code: 403, rules: [ { @@ -425,6 +468,19 @@ describe('perform_bulk_action', () => { expect.stringContaining('Invalid value "[]" supplied to "edit"') ); }); + + it('rejects payloads if search query dry_run is invalid', async () => { + const request = requestMock.create({ + method: 'patch', + path: DETECTION_ENGINE_RULES_BULK_ACTION, + body: getPerformBulkActionEditSchemaMock(), + query: { dry_run: 'invalid' }, + }); + const result = server.validate(request); + expect(result.badRequest).toHaveBeenCalledWith( + expect.stringContaining('Invalid value "invalid" supplied to "dry_run"') + ); + }); }); it('should process large number of rules, larger than configured concurrency', async () => { diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.ts index 27ad55b7b0179..3c288184e0736 100644 --- a/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.ts +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/routes/rules/perform_bulk_action_route.ts @@ -15,13 +15,17 @@ import type { SanitizedRule } from '@kbn/alerting-plugin/common'; import { AbortError } from '@kbn/kibana-utils-plugin/common'; import type { RuleAlertType } from '../../rules/types'; +import type { BulkActionsDryRunErrCode } from '../../../../../common/constants'; import { DETECTION_ENGINE_RULES_BULK_ACTION, MAX_RULES_TO_UPDATE_IN_PARALLEL, RULES_TABLE_MAX_PAGE_SIZE, } from '../../../../../common/constants'; import { BulkAction } from '../../../../../common/detection_engine/schemas/common/schemas'; -import { performBulkActionSchema } from '../../../../../common/detection_engine/schemas/request/perform_bulk_action_schema'; +import { + performBulkActionSchema, + performBulkActionQuerySchema, +} from '../../../../../common/detection_engine/schemas/request/perform_bulk_action_schema'; import type { SetupPlugins } from '../../../../plugin'; import type { SecuritySolutionPluginRouter } from '../../../../types'; import { buildRouteValidation } from '../../../../utils/build_validation/route_validation'; @@ -29,7 +33,6 @@ import { routeLimitedConcurrencyTag } from '../../../../utils/route_limited_conc import type { PromisePoolError, PromisePoolOutcome } from '../../../../utils/promise_pool'; import { initPromisePool } from '../../../../utils/promise_pool'; import { buildMlAuthz } from '../../../machine_learning/authz'; -import { throwAuthzError } from '../../../machine_learning/validation'; import { deleteRules } from '../../rules/delete_rules'; import { duplicateRule } from '../../rules/duplicate_rule'; import { findRules } from '../../rules/find_rules'; @@ -39,6 +42,13 @@ import { getExportByObjectIds } from '../../rules/get_export_by_object_ids'; import { buildSiemResponse } from '../utils'; import { internalRuleToAPIResponse } from '../../schemas/rule_converters'; import { legacyMigrate } from '../../rules/utils'; +import type { DryRunError } from '../../rules/bulk_actions/dry_run'; +import { + validateBulkEnableRule, + validateBulkDisableRule, + validateBulkDuplicateRule, + dryRunValidateBulkEditRule, +} from '../../rules/bulk_actions/validations'; import type { RuleParams } from '../../schemas/rule_schemas'; const MAX_RULES_TO_PROCESS_TOTAL = 10000; @@ -52,6 +62,7 @@ interface RuleDetailsInError { interface NormalizedRuleError { message: string; status_code: number; + err_code?: BulkActionsDryRunErrCode; rules: RuleDetailsInError[]; } @@ -63,8 +74,8 @@ const normalizeErrorResponse = (errors: BulkActionError[]): NormalizedRuleError[ errors.forEach((errorObj) => { let message: string; let statusCode: number = 500; + let errorCode: BulkActionsDryRunErrCode | undefined; let rule: RuleDetailsInError; - // transform different error types (PromisePoolError | PromisePoolError | BulkEditError) // to one common used in NormalizedRuleError if ('rule' in errorObj) { @@ -77,6 +88,7 @@ const normalizeErrorResponse = (errors: BulkActionError[]): NormalizedRuleError[ ? transformError(error) : { message: String(error), statusCode: 500 }; + errorCode = (error as DryRunError)?.errorCode; message = transformedError.message; statusCode = transformedError.statusCode; // The promise pool item is either a rule ID string or a rule object. We have @@ -91,6 +103,7 @@ const normalizeErrorResponse = (errors: BulkActionError[]): NormalizedRuleError[ errorsMap.set(message, { message: truncate(message, { length: MAX_ERROR_MESSAGE_LENGTH }), status_code: statusCode, + err_code: errorCode, rules: [rule], }); } @@ -102,11 +115,13 @@ const normalizeErrorResponse = (errors: BulkActionError[]): NormalizedRuleError[ const buildBulkResponse = ( response: KibanaResponseFactory, { + isDryRun = false, errors = [], updated = [], created = [], deleted = [], }: { + isDryRun?: boolean; errors?: BulkActionError[]; updated?: RuleAlertType[]; created?: RuleAlertType[]; @@ -121,11 +136,19 @@ const buildBulkResponse = ( total: numSucceeded + numFailed, }; - const results = { - updated: updated.map((rule) => internalRuleToAPIResponse(rule)), - created: created.map((rule) => internalRuleToAPIResponse(rule)), - deleted: deleted.map((rule) => internalRuleToAPIResponse(rule)), - }; + // if response is for dry_run, empty lists of rules returned, as rules are not actually updated and stored within ES + // thus, it's impossible to return reliably updated/duplicated/deleted rules + const results = isDryRun + ? { + updated: [], + created: [], + deleted: [], + } + : { + updated: updated.map((rule) => internalRuleToAPIResponse(rule)), + created: created.map((rule) => internalRuleToAPIResponse(rule)), + deleted: deleted.map((rule) => internalRuleToAPIResponse(rule)), + }; if (numFailed > 0) { return response.custom({ @@ -245,6 +268,9 @@ export const performBulkActionRoute = ( path: DETECTION_ENGINE_RULES_BULK_ACTION, validate: { body: buildRouteValidation(performBulkActionSchema), + query: buildRouteValidation( + performBulkActionQuerySchema + ), }, options: { tags: ['access:securitySolution', routeLimitedConcurrencyTag(MAX_ROUTE_CONCURRENCY)], @@ -271,6 +297,16 @@ export const performBulkActionRoute = ( }); } + const isDryRun = request.query.dry_run === 'true'; + + // dry run is not supported for export, as it doesn't change ES state and has different response format(exported JSON file) + if (isDryRun && body.action === BulkAction.export) { + return siemResponse.error({ + body: `Export action doesn't support dry_run mode`, + statusCode: 400, + }); + } + const abortController = new AbortController(); // subscribing to completed$, because it handles both cases when request was completed and aborted. @@ -301,7 +337,7 @@ export const performBulkActionRoute = ( // handling this action before switch statement as bulkEditRules fetch rules within // rulesClient method, hence there is no need to use fetchRulesByQueryOrIds utility - if (body.action === BulkAction.edit) { + if (body.action === BulkAction.edit && !isDryRun) { const { rules, errors } = await bulkEditRules({ rulesClient, filter: query, @@ -356,6 +392,13 @@ export const performBulkActionRoute = ( concurrency: MAX_RULES_TO_UPDATE_IN_PARALLEL, items: rules, executor: async (rule) => { + await validateBulkEnableRule({ mlAuthz, rule }); + + // during dry run only validation is getting performed and rule is not saved in ES, thus return early + if (isDryRun) { + return rule; + } + const migratedRule = await migrateRuleActions({ rulesClient, savedObjectsClient, @@ -363,7 +406,6 @@ export const performBulkActionRoute = ( }); if (!migratedRule.enabled) { - throwAuthzError(await mlAuthz.validateRuleType(migratedRule.params.type)); await rulesClient.enable({ id: migratedRule.id }); } @@ -383,6 +425,13 @@ export const performBulkActionRoute = ( concurrency: MAX_RULES_TO_UPDATE_IN_PARALLEL, items: rules, executor: async (rule) => { + await validateBulkDisableRule({ mlAuthz, rule }); + + // during dry run only validation is getting performed and rule is not saved in ES, thus return early + if (isDryRun) { + return rule; + } + const migratedRule = await migrateRuleActions({ rulesClient, savedObjectsClient, @@ -390,7 +439,6 @@ export const performBulkActionRoute = ( }); if (migratedRule.enabled) { - throwAuthzError(await mlAuthz.validateRuleType(migratedRule.params.type)); await rulesClient.disable({ id: migratedRule.id }); } @@ -405,11 +453,17 @@ export const performBulkActionRoute = ( .map(({ result }) => result) .filter((rule): rule is RuleAlertType => rule !== null); break; + case BulkAction.delete: bulkActionOutcome = await initPromisePool({ concurrency: MAX_RULES_TO_UPDATE_IN_PARALLEL, items: rules, executor: async (rule) => { + // during dry run return early for delete, as no validations needed for this action + if (isDryRun) { + return null; + } + const migratedRule = await migrateRuleActions({ rulesClient, savedObjectsClient, @@ -430,19 +484,25 @@ export const performBulkActionRoute = ( .map(({ item }) => item) .filter((rule): rule is RuleAlertType => rule !== null); break; + case BulkAction.duplicate: bulkActionOutcome = await initPromisePool({ concurrency: MAX_RULES_TO_UPDATE_IN_PARALLEL, items: rules, executor: async (rule) => { + await validateBulkDuplicateRule({ mlAuthz, rule }); + + // during dry run only validation is getting performed and rule is not saved in ES, thus return early + if (isDryRun) { + return rule; + } + const migratedRule = await migrateRuleActions({ rulesClient, savedObjectsClient, rule, }); - throwAuthzError(await mlAuthz.validateRuleType(migratedRule.params.type)); - const createdRule = await rulesClient.create({ data: duplicateRule(migratedRule), }); @@ -455,6 +515,7 @@ export const performBulkActionRoute = ( .map(({ result }) => result) .filter((rule): rule is RuleAlertType => rule !== null); break; + case BulkAction.export: const exported = await getExportByObjectIds( rulesClient, @@ -473,6 +534,23 @@ export const performBulkActionRoute = ( }, body: responseBody, }); + + // will be processed only when isDryRun === true + // during dry run only validation is getting performed and rule is not saved in ES + case BulkAction.edit: + bulkActionOutcome = await initPromisePool({ + concurrency: MAX_RULES_TO_UPDATE_IN_PARALLEL, + items: rules, + executor: async (rule) => { + await dryRunValidateBulkEditRule({ mlAuthz, rule, edit: body.edit }); + + return rule; + }, + abortSignal: abortController.signal, + }); + updated = bulkActionOutcome.results + .map(({ result }) => result) + .filter((rule): rule is RuleAlertType => rule !== null); } if (abortController.signal.aborted === true) { @@ -484,6 +562,7 @@ export const performBulkActionRoute = ( deleted, created, errors: [...fetchRulesOutcome.errors, ...bulkActionOutcome.errors], + isDryRun, }); } catch (err) { const error = transformError(err); diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/action_to_rules_client_operation.test.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/action_to_rules_client_operation.test.ts similarity index 100% rename from x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/action_to_rules_client_operation.test.ts rename to x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/action_to_rules_client_operation.test.ts diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/action_to_rules_client_operation.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/action_to_rules_client_operation.ts similarity index 100% rename from x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/action_to_rules_client_operation.ts rename to x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/action_to_rules_client_operation.ts diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/dry_run.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/dry_run.ts new file mode 100644 index 0000000000000..608324e5bb280 --- /dev/null +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/dry_run.ts @@ -0,0 +1,40 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { BulkActionsDryRunErrCode } from '../../../../../common/constants'; + +/** + * Error instance that has properties: errorCode & statusCode to use within run_dry + * errorCode({@link BulkActionsDryRunErrCode}) is used to categorize error and make possible to handle it later + */ +export class DryRunError extends Error { + public readonly errorCode: BulkActionsDryRunErrCode; + public readonly statusCode: number; + + constructor(message: string, errorCode: BulkActionsDryRunErrCode, statusCode?: number) { + super(message); + this.name = 'BulkActionDryRunError'; + this.errorCode = errorCode; + this.statusCode = statusCode ?? 500; + } +} + +/** + * executes function, if error thrown, wraps this error into {@link DryRunError} + * @param executor - function that can be executed + * @param errorCode - enum error code {@link BulkActionsDryRunErrCode} to use in DryRunError wrapper + */ +export const throwDryRunError = async ( + executor: () => void, + errorCode: BulkActionsDryRunErrCode +) => { + try { + await executor(); + } catch (e) { + throw new DryRunError(e.message, errorCode, e.statusCode); + } +}; diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/rule_params_modifier.test.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/rule_params_modifier.test.ts similarity index 100% rename from x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/rule_params_modifier.test.ts rename to x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/rule_params_modifier.test.ts diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/rule_params_modifier.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/rule_params_modifier.ts similarity index 100% rename from x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/rule_params_modifier.ts rename to x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/rule_params_modifier.ts diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/split_bulk_edit_actions.test.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/split_bulk_edit_actions.test.ts similarity index 100% rename from x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/split_bulk_edit_actions.test.ts rename to x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/split_bulk_edit_actions.test.ts diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/split_bulk_edit_actions.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/split_bulk_edit_actions.ts similarity index 100% rename from x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit/split_bulk_edit_actions.ts rename to x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/split_bulk_edit_actions.ts diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/utils.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/utils.ts new file mode 100644 index 0000000000000..65a4af2308e0e --- /dev/null +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/utils.ts @@ -0,0 +1,20 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import { BulkActionEditType } from '../../../../../common/detection_engine/schemas/common/schemas'; + +/** + * helper utility that defines whether bulk edit action is related to index patterns, i.e. one of: + * 'add_index_patterns', 'delete_index_patterns', 'set_index_patterns' + * @param editAction {@link BulkActionEditType} + * @returns {boolean} + */ +export const isIndexPatternsBulkEditAction = (editAction: BulkActionEditType) => + [ + BulkActionEditType.add_index_patterns, + BulkActionEditType.delete_index_patterns, + BulkActionEditType.set_index_patterns, + ].includes(editAction); diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/validations.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/validations.ts new file mode 100644 index 0000000000000..28793f9fe9c88 --- /dev/null +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_actions/validations.ts @@ -0,0 +1,112 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { Type as RuleType } from '@kbn/securitysolution-io-ts-alerting-types'; +import { invariant } from '../../../../../common/utils/invariant'; +import { isMlRule } from '../../../../../common/machine_learning/helpers'; +import { BulkActionsDryRunErrCode } from '../../../../../common/constants'; +import type { BulkActionEditPayload } from '../../../../../common/detection_engine/schemas/common/schemas'; +import type { RuleAlertType } from '../types'; +import { isIndexPatternsBulkEditAction } from './utils'; +import { throwDryRunError } from './dry_run'; +import type { MlAuthz } from '../../../machine_learning/authz'; +import { throwAuthzError } from '../../../machine_learning/validation'; + +interface BulkActionsValidationArgs { + rule: RuleAlertType; + mlAuthz: MlAuthz; +} + +interface BulkEditBulkActionsValidationArgs { + ruleType: RuleType; + mlAuthz: MlAuthz; +} + +interface DryRunBulkEditBulkActionsValidationArgs { + rule: RuleAlertType; + mlAuthz: MlAuthz; + edit: BulkActionEditPayload[]; +} + +/** + * throws ML authorization error wrapped with MACHINE_LEARNING_AUTH error code + * @param mlAuthz - {@link MlAuthz} + * @param ruleType - {@link RuleType} + */ +const throwMlAuthError = (mlAuthz: MlAuthz, ruleType: RuleType) => + throwDryRunError( + async () => throwAuthzError(await mlAuthz.validateRuleType(ruleType)), + BulkActionsDryRunErrCode.MACHINE_LEARNING_AUTH + ); + +/** + * runs validation for bulk enable for a single rule + * @param params - {@link BulkActionsValidationArgs} + */ +export const validateBulkEnableRule = async ({ rule, mlAuthz }: BulkActionsValidationArgs) => { + if (!rule.enabled) { + await throwMlAuthError(mlAuthz, rule.params.type); + } +}; + +/** + * runs validation for bulk disable for a single rule + * @param params - {@link BulkActionsValidationArgs} + */ +export const validateBulkDisableRule = async ({ rule, mlAuthz }: BulkActionsValidationArgs) => { + if (rule.enabled) { + await throwMlAuthError(mlAuthz, rule.params.type); + } +}; + +/** + * runs validation for bulk duplicate for a single rule + * @param params - {@link BulkActionsValidationArgs} + */ +export const validateBulkDuplicateRule = async ({ rule, mlAuthz }: BulkActionsValidationArgs) => { + await throwMlAuthError(mlAuthz, rule.params.type); +}; + +/** + * runs validation for bulk edit for a single rule + * @param params - {@link BulkActionsValidationArgs} + */ +export const validateBulkEditRule = async ({ + ruleType, + mlAuthz, +}: BulkEditBulkActionsValidationArgs) => { + await throwMlAuthError(mlAuthz, ruleType); +}; + +/** + * executes dry run validations for bulk edit of a single rule + * @param params - {@link DryRunBulkEditBulkActionsValidationArgs} + */ +export const dryRunValidateBulkEditRule = async ({ + rule, + edit, + mlAuthz, +}: DryRunBulkEditBulkActionsValidationArgs) => { + await validateBulkEditRule({ ruleType: rule.params.type, mlAuthz }); + + // if rule is immutable, it can't be edited + await throwDryRunError( + () => invariant(rule.params.immutable === false, "Elastic rule can't be edited"), + BulkActionsDryRunErrCode.IMMUTABLE + ); + + // if rule is machine_learning, index pattern action can't be applied to it + await throwDryRunError( + () => + invariant( + !isMlRule(rule.params.type) || + !edit.some((action) => isIndexPatternsBulkEditAction(action.type)), + "Machine learning rule doesn't have index patterns" + ), + BulkActionsDryRunErrCode.MACHINE_LEARNING_INDEX_PATTERN + ); +}; diff --git a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit_rules.ts b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit_rules.ts index 1592a8e58972b..587d7d539caa6 100644 --- a/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit_rules.ts +++ b/x-pack/plugins/security_solution/server/lib/detection_engine/rules/bulk_edit_rules.ts @@ -9,11 +9,11 @@ import type { RulesClient } from '@kbn/alerting-plugin/server'; import type { BulkActionEditPayload } from '../../../../common/detection_engine/schemas/common'; import { enrichFilterWithRuleTypeMapping } from './enrich_filter_with_rule_type_mappings'; import type { MlAuthz } from '../../machine_learning/authz'; -import { throwAuthzError } from '../../machine_learning/validation'; -import { ruleParamsModifier } from './bulk_edit/rule_params_modifier'; -import { splitBulkEditActions } from './bulk_edit/split_bulk_edit_actions'; -import { bulkEditActionToRulesClientOperation } from './bulk_edit/action_to_rules_client_operation'; +import { ruleParamsModifier } from './bulk_actions/rule_params_modifier'; +import { splitBulkEditActions } from './bulk_actions/split_bulk_edit_actions'; +import { validateBulkEditRule } from './bulk_actions/validations'; +import { bulkEditActionToRulesClientOperation } from './bulk_actions/action_to_rules_client_operation'; import type { RuleAlertType } from './types'; @@ -45,8 +45,7 @@ export const bulkEditRules = ({ ...(ids ? { ids } : { filter: enrichFilterWithRuleTypeMapping(filter) }), operations: attributesActions.map(bulkEditActionToRulesClientOperation), paramsModifier: async (ruleParams: RuleAlertType['params']) => { - throwAuthzError(await mlAuthz.validateRuleType(ruleParams.type)); - + await validateBulkEditRule({ mlAuthz, ruleType: ruleParams.type }); return ruleParamsModifier(ruleParams, paramsActions); }, }); diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index b5e2d8ca9c98b..fb05c80689a0b 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -24781,7 +24781,6 @@ "xpack.securitySolution.detectionEngine.alerts.utilityBar.takeActionTitle": "Entreprendre une action", "xpack.securitySolution.detectionEngine.alertTitle": "Alertes", "xpack.securitySolution.detectionEngine.buttonManageRules": "Gérer les règles", - "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmation.confirmButtonLabel": "Modifier les règles personnalisées", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmationCancelButtonLabel": "Annuler", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditFlyoutForm.addIndexPatternsComboboxHelpText": "Sélectionnez les modèles d'indexation par défaut des index Elasticsearch à partir de la liste déroulante. Vous pouvez ajouter des modèles d'indexation personnalisés, puis appuyer sur Entrée pour en ajouter un nouveau.", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditFlyoutForm.addIndexPatternsComboboxLabel": "Ajouter des modèles d'indexation pour les règles sélectionnées", @@ -25703,9 +25702,6 @@ "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.addIndexPatternsTitle": "Ajouter des modèles d'indexation", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.addTagsTitle": "Ajouter des balises", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.applyTimelineTemplateTitle": "Appliquer le modèle de chronologie", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationDescription": "L'action de mise à jour sera appliquée uniquement à {customRulesCount, plural, =1 {# règle personnalisée que vous avez sélectionnée} other {# règles personnalisées que vous avez sélectionnées}}.", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationTitle": "Impossible de modifier {elasticRulesCount, plural, =1 {# règle Elastic} other {# règles Elastic}}", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditRejectionDescription": "Les règles Elastic ne sont pas modifiables. L'action de mise à jour sera appliquée uniquement aux règles personnalisées.", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastDescription": "{rulesCount, plural, =1 {# règle est} other {# règles sont}} en cours de mise à jour.", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastNotifyButtonLabel": "M'envoyer une notification à la fin", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastTitle": "Les mises à jour des règles sont en cours", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index b354098f75fe4..05d2624262465 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -24766,7 +24766,6 @@ "xpack.securitySolution.detectionEngine.alerts.utilityBar.takeActionTitle": "アクションを実行", "xpack.securitySolution.detectionEngine.alertTitle": "アラート", "xpack.securitySolution.detectionEngine.buttonManageRules": "ルールの管理", - "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmation.confirmButtonLabel": "カスタムルールの編集", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmationCancelButtonLabel": "キャンセル", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditFlyoutForm.addIndexPatternsComboboxHelpText": "Elasticsearchインデックスのデフォルトインデックスパターンをドロップダウンから選択します。カスタムインデックスパターンを追加し、Enterを押すと、新しいインデックスパターンを開始できます。", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditFlyoutForm.addIndexPatternsComboboxLabel": "選択したルールのインデックスパターンを追加", @@ -25688,9 +25687,6 @@ "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.addIndexPatternsTitle": "インデックスパターンを追加", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.addTagsTitle": "タグを追加", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.applyTimelineTemplateTitle": "タイムラインテンプレートを適用", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationDescription": "更新アクションは、選択した{customRulesCount, plural, other {#個のカスタムルール}}にのみ適用されます。", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationTitle": "{elasticRulesCount, plural, other {#個のElasticルール}}を編集できません", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditRejectionDescription": "Elasticルールは変更できません。更新アクションはカスタムルールにのみ適用されます。", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastDescription": "{rulesCount, plural, other {#個のルール}}を更新しています。", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastNotifyButtonLabel": "完了時に通知", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastTitle": "ルールを更新しています", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index a329fd0f181dd..5157f316e9940 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -24792,7 +24792,6 @@ "xpack.securitySolution.detectionEngine.alerts.utilityBar.takeActionTitle": "采取操作", "xpack.securitySolution.detectionEngine.alertTitle": "告警", "xpack.securitySolution.detectionEngine.buttonManageRules": "管理规则", - "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmation.confirmButtonLabel": "编辑定制规则", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditConfirmationCancelButtonLabel": "取消", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditFlyoutForm.addIndexPatternsComboboxHelpText": "从下拉列表中选择 Elasticsearch 索引的默认索引模式。您可以添加定制索引模式,然后按 Enter 键以开始新索引。", "xpack.securitySolution.detectionEngine.components.allRules.bulkActions.bulkEditFlyoutForm.addIndexPatternsComboboxLabel": "为选定规则添加索引模式", @@ -25714,9 +25713,6 @@ "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.addIndexPatternsTitle": "添加索引模式", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.addTagsTitle": "添加标签", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.applyTimelineTemplateTitle": "应用时间线模板", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationDescription": "将仅对您选定的 {customRulesCount, plural, other {# 个定制规则}}应用更新操作。", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditConfirmationTitle": "无法编辑 {elasticRulesCount, plural, other {# 个 Elastic 规则}}", - "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditRejectionDescription": "无法修改 Elastic 规则。将仅对定制规则应用更新操作。", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastDescription": "{rulesCount, plural, other {# 个规则}}正在更新。", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastNotifyButtonLabel": "在完成时通知我", "xpack.securitySolution.detectionEngine.rules.allRules.bulkActions.bulkEditWarningToastTitle": "正在进行规则更新", diff --git a/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/index.ts b/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/index.ts index f7a96c2f496d8..cb61f90aec33c 100644 --- a/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/index.ts +++ b/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/index.ts @@ -41,6 +41,7 @@ export default ({ loadTestFile }: FtrProviderContext): void => { loadTestFile(require.resolve('./update_rules_bulk')); loadTestFile(require.resolve('./patch_rules_bulk')); loadTestFile(require.resolve('./perform_bulk_action')); + loadTestFile(require.resolve('./perform_bulk_action_dry_run')); loadTestFile(require.resolve('./patch_rules')); loadTestFile(require.resolve('./read_privileges')); loadTestFile(require.resolve('./open_close_signals')); diff --git a/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/perform_bulk_action_dry_run.ts b/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/perform_bulk_action_dry_run.ts new file mode 100644 index 0000000000000..429b34f3f0a54 --- /dev/null +++ b/x-pack/test/detection_engine_api_integration/security_and_spaces/group1/perform_bulk_action_dry_run.ts @@ -0,0 +1,242 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import expect from 'expect'; + +import { + DETECTION_ENGINE_RULES_BULK_ACTION, + DETECTION_ENGINE_RULES_URL, +} from '@kbn/security-solution-plugin/common/constants'; +import { + BulkAction, + BulkActionEditType, +} from '@kbn/security-solution-plugin/common/detection_engine/schemas/common/schemas'; +import { FtrProviderContext } from '../../common/ftr_provider_context'; +import { + createRule, + createSignalsIndex, + deleteAllAlerts, + deleteSignalsIndex, + getSimpleRule, + installPrePackagedRules, + getSimpleMlRule, +} from '../../utils'; + +// eslint-disable-next-line import/no-default-export +export default ({ getService }: FtrProviderContext): void => { + const supertest = getService('supertest'); + const log = getService('log'); + + const postDryRunBulkAction = () => + supertest + .post(DETECTION_ENGINE_RULES_BULK_ACTION) + .set('kbn-xsrf', 'true') + .query({ dry_run: true }); + + const fetchRule = (ruleId: string) => + supertest.get(`${DETECTION_ENGINE_RULES_URL}?rule_id=${ruleId}`).set('kbn-xsrf', 'true'); + + const findRules = () => + supertest.get(`${DETECTION_ENGINE_RULES_URL}/_find`).set('kbn-xsrf', 'true'); + + describe('perform_bulk_action dry_run', () => { + beforeEach(async () => { + await createSignalsIndex(supertest, log); + }); + + afterEach(async () => { + await deleteSignalsIndex(supertest, log); + await deleteAllAlerts(supertest, log); + }); + + it('should not support export action', async () => { + await createRule(supertest, log, getSimpleRule()); + + const { body } = await postDryRunBulkAction().send({ action: BulkAction.export }).expect(400); + + expect(body).toEqual({ + message: "Export action doesn't support dry_run mode", + status_code: 400, + }); + }); + + it('should handle delete action', async () => { + const ruleId = 'ruleId'; + const testRule = getSimpleRule(ruleId); + await createRule(supertest, log, testRule); + + const { body } = await postDryRunBulkAction().send({ action: BulkAction.delete }).expect(200); + + expect(body.attributes.summary).toEqual({ failed: 0, succeeded: 1, total: 1 }); + // dry_run mode shouldn't return any rules in results + expect(body.attributes.results).toEqual({ updated: [], created: [], deleted: [] }); + + // Check that rule wasn't deleted + await fetchRule(ruleId).expect(200); + }); + + it('should handle enable action', async () => { + const ruleId = 'ruleId'; + await createRule(supertest, log, getSimpleRule(ruleId)); + + const { body } = await postDryRunBulkAction().send({ action: BulkAction.enable }).expect(200); + + expect(body.attributes.summary).toEqual({ failed: 0, succeeded: 1, total: 1 }); + // dry_run mode shouldn't return any rules in results + expect(body.attributes.results).toEqual({ updated: [], created: [], deleted: [] }); + + // Check that the updates have not been persisted + const { body: ruleBody } = await fetchRule(ruleId).expect(200); + expect(ruleBody.enabled).toBe(false); + }); + + it('should handle disable action', async () => { + const ruleId = 'ruleId'; + await createRule(supertest, log, getSimpleRule(ruleId, true)); + + const { body } = await postDryRunBulkAction() + .send({ action: BulkAction.disable }) + .expect(200); + + expect(body.attributes.summary).toEqual({ failed: 0, succeeded: 1, total: 1 }); + // dry_run mode shouldn't return any rules in results + expect(body.attributes.results).toEqual({ updated: [], created: [], deleted: [] }); + + // Check that the updates have not been persisted + const { body: ruleBody } = await fetchRule(ruleId).expect(200); + expect(ruleBody.enabled).toBe(true); + }); + + it('should handle duplicate action', async () => { + const ruleId = 'ruleId'; + const ruleToDuplicate = getSimpleRule(ruleId); + await createRule(supertest, log, ruleToDuplicate); + + const { body } = await postDryRunBulkAction() + .send({ action: BulkAction.disable }) + .expect(200); + + expect(body.attributes.summary).toEqual({ failed: 0, succeeded: 1, total: 1 }); + // dry_run mode shouldn't return any rules in results + expect(body.attributes.results).toEqual({ updated: [], created: [], deleted: [] }); + + // Check that the rule wasn't duplicated + const { body: rulesResponse } = await findRules().expect(200); + + expect(rulesResponse.total).toBe(1); + }); + + describe('edit action', () => { + it('should handle edit action', async () => { + const ruleId = 'ruleId'; + const tags = ['tag1', 'tag2']; + await createRule(supertest, log, { ...getSimpleRule(ruleId), tags }); + + const { body } = await postDryRunBulkAction() + .send({ + action: BulkAction.edit, + [BulkAction.edit]: [ + { + type: BulkActionEditType.set_tags, + value: ['reset-tag'], + }, + ], + }) + .expect(200); + + expect(body.attributes.summary).toEqual({ failed: 0, succeeded: 1, total: 1 }); + // dry_run mode shouldn't return any rules in results + expect(body.attributes.results).toEqual({ updated: [], created: [], deleted: [] }); + + // Check that the updates have not been persisted + const { body: ruleBody } = await fetchRule(ruleId).expect(200); + expect(ruleBody.tags).toEqual(tags); + }); + + it('should validate immutable rule edit', async () => { + await installPrePackagedRules(supertest, log); + const { body: findBody } = await findRules() + .query({ per_page: 1, filter: 'alert.attributes.params.immutable: true' }) + .send() + .expect(200); + + const immutableRule = findBody.data[0]; + + const { body } = await postDryRunBulkAction() + .send({ + ids: [immutableRule.id], + action: BulkAction.edit, + [BulkAction.edit]: [ + { + type: BulkActionEditType.set_tags, + value: ['reset-tag'], + }, + ], + }) + .expect(500); + + expect(body.attributes.summary).toEqual({ failed: 1, succeeded: 0, total: 1 }); + expect(body.attributes.results).toEqual({ updated: [], created: [], deleted: [] }); + + expect(body.attributes.errors).toHaveLength(1); + expect(body.attributes.errors[0]).toEqual({ + err_code: 'IMMUTABLE', + message: "Elastic rule can't be edited", + status_code: 500, + rules: [ + { + id: immutableRule.id, + name: immutableRule.name, + }, + ], + }); + }); + + describe('validate updating index pattern for machine learning rule', () => { + const actions = [ + BulkActionEditType.add_index_patterns, + BulkActionEditType.set_index_patterns, + BulkActionEditType.delete_index_patterns, + ]; + + actions.forEach((editAction) => { + it(`should return error if ${editAction} action is applied to machine learning rule`, async () => { + const mlRule = await createRule(supertest, log, getSimpleMlRule()); + + const { body } = await postDryRunBulkAction() + .send({ + ids: [mlRule.id], + action: BulkAction.edit, + [BulkAction.edit]: [ + { + type: editAction, + value: [], + }, + ], + }) + .expect(500); + + expect(body.attributes.summary).toEqual({ failed: 1, succeeded: 0, total: 1 }); + expect(body.attributes.results).toEqual({ updated: [], created: [], deleted: [] }); + + expect(body.attributes.errors).toHaveLength(1); + expect(body.attributes.errors[0]).toEqual({ + err_code: 'MACHINE_LEARNING_INDEX_PATTERN', + message: "Machine learning rule doesn't have index patterns", + status_code: 500, + rules: [ + { + id: mlRule.id, + name: mlRule.name, + }, + ], + }); + }); + }); + }); + }); + }); +}; From 7fa68136b434100adba9820034775a4559b240be Mon Sep 17 00:00:00 2001 From: Peter Pisljar Date: Mon, 18 Jul 2022 14:29:58 +0200 Subject: [PATCH 082/111] dataviews.clearCache cleanup (#136256) --- .../index_pattern_table.tsx | 2 +- .../common/data_views/data_views.test.ts | 2 +- .../common/data_views/data_views.ts | 22 ++++++++++++++----- .../application/main/discover_main_route.tsx | 2 +- .../dataview_picker/change_dataview.tsx | 4 +++- 5 files changed, 22 insertions(+), 10 deletions(-) diff --git a/src/plugins/data_view_management/public/components/index_pattern_table/index_pattern_table.tsx b/src/plugins/data_view_management/public/components/index_pattern_table/index_pattern_table.tsx index 23ecb5657ae36..20dd75aff49c7 100644 --- a/src/plugins/data_view_management/public/components/index_pattern_table/index_pattern_table.tsx +++ b/src/plugins/data_view_management/public/components/index_pattern_table/index_pattern_table.tsx @@ -267,7 +267,7 @@ export const IndexPatternTable = ({ id={dataView.id} title={dataView.title} refresh={() => { - dataViews.clearCache(dataView.id); + dataViews.clearInstanceCache(dataView.id); loadDataViews(); }} /> diff --git a/src/plugins/data_views/common/data_views/data_views.test.ts b/src/plugins/data_views/common/data_views/data_views.test.ts index ac4fc71414cb3..827592f7fd31a 100644 --- a/src/plugins/data_views/common/data_views/data_views.test.ts +++ b/src/plugins/data_views/common/data_views/data_views.test.ts @@ -210,7 +210,7 @@ describe('IndexPatterns', () => { // Create a normal index patterns const pattern = await indexPatterns.get('foo'); - indexPatterns.clearCache(); + indexPatterns.clearInstanceCache(); // Create the same one - we're going to handle concurrency const samePattern = await indexPatterns.get('foo'); diff --git a/src/plugins/data_views/common/data_views/data_views.ts b/src/plugins/data_views/common/data_views/data_views.ts index 12a06b9a98fa7..85de6f2d5667e 100644 --- a/src/plugins/data_views/common/data_views/data_views.ts +++ b/src/plugins/data_views/common/data_views/data_views.ts @@ -123,10 +123,15 @@ export interface DataViewsServiceDeps { */ export interface DataViewsServicePublicMethods { /** - * Clear the cache of data views. - * @param id + * Clear the cache of data view saved objects. */ - clearCache: (id?: string | undefined) => void; + clearCache: () => void; + + /** + * Clear the cache of data view instances. + */ + clearInstanceCache: (id?: string) => void; + /** * Create data view based on the provided spec. * @param spec - Data view spec. @@ -396,11 +401,16 @@ export class DataViewsService { }; /** - * Clear index pattern list cache. - * @param id optionally clear a single id + * Clear index pattern saved objects cache. */ - clearCache = (id?: string) => { + clearCache = () => { this.savedObjectsCache = null; + }; + + /** + * Clear index pattern instance cache + */ + clearInstanceCache = (id?: string) => { if (id) { this.dataViewCache.clear(id); } else { diff --git a/src/plugins/discover/public/application/main/discover_main_route.tsx b/src/plugins/discover/public/application/main/discover_main_route.tsx index 213910bf37be2..6818ab3c12cde 100644 --- a/src/plugins/discover/public/application/main/discover_main_route.tsx +++ b/src/plugins/discover/public/application/main/discover_main_route.tsx @@ -102,7 +102,7 @@ export function DiscoverMainRoute(props: Props) { const ipList = ip.list as Array>; const indexPatternData = resolveIndexPattern(ip, searchSource, toastNotifications); - + await data.dataViews.refreshFields(indexPatternData); setIndexPatternList(ipList); return indexPatternData; diff --git a/src/plugins/unified_search/public/dataview_picker/change_dataview.tsx b/src/plugins/unified_search/public/dataview_picker/change_dataview.tsx index c217b8c52b06f..c7e19429c66e3 100644 --- a/src/plugins/unified_search/public/dataview_picker/change_dataview.tsx +++ b/src/plugins/unified_search/public/dataview_picker/change_dataview.tsx @@ -166,7 +166,9 @@ export function ChangeDataView({ panelItems.push( { + onChangeDataView={async (newId) => { + const dataView = await data.dataViews.get(newId); + await data.dataViews.refreshFields(dataView); onChangeDataView(newId); setPopoverIsOpen(false); }} From d217e2cdfd13c0d594382f31f1625a613b118b91 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alejandro=20Fern=C3=A1ndez=20Haro?= Date: Mon, 18 Jul 2022 14:54:30 +0200 Subject: [PATCH 083/111] Flaky test 133800 (#136518) --- .../from_the_browser/click.ts | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/test/analytics/tests/instrumented_events/from_the_browser/click.ts b/test/analytics/tests/instrumented_events/from_the_browser/click.ts index dcf405825e90b..08027a6158761 100644 --- a/test/analytics/tests/instrumented_events/from_the_browser/click.ts +++ b/test/analytics/tests/instrumented_events/from_the_browser/click.ts @@ -13,12 +13,14 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { const ebtUIHelper = getService('kibana_ebt_ui'); const { common } = getPageObjects(['common']); - // FLAKY: https://github.com/elastic/kibana/issues/133800 - describe.skip('General "click"', () => { + describe('General "click"', () => { beforeEach(async () => { - await common.navigateToApp('home'); - // Just clicking the top-nav-button and expecting it's still there... we're just testing the click event generation - await common.clickAndValidate('toggleNavButton', 'toggleNavButton'); + // Navigating to `home` with the Welcome prompt because some runs were flaky + // as we handle the Welcome screen only if the login prompt pops up. + // Otherwise, it stays in the Welcome screen :/ + await common.navigateToApp('home', { disableWelcomePrompt: false }); + // Clicking the button skipWelcomeScreen. + await common.clickAndValidate('skipWelcomeScreen', 'headerGlobalNav'); }); it('should emit a "click" event', async () => { @@ -27,10 +29,10 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { expect(event.properties.target).to.be.an('array'); const targets = event.properties.target as string[]; expect(targets.includes('DIV')).to.be(true); - expect(targets.includes('id=kibana-body')).to.be(true); - expect(targets.includes('data-test-subj=kibanaChrome')).to.be(true); + expect(targets.includes('class=homWelcome')).to.be(true); + expect(targets.includes('data-test-subj=homeWelcomeInterstitial')).to.be(true); expect(targets.includes('BUTTON')).to.be(true); - expect(targets.includes('data-test-subj=toggleNavButton')).to.be(true); + expect(targets.includes('data-test-subj=skipWelcomeScreen')).to.be(true); }); }); } From 70b38ff178a72dc467d5f1fd74c766d9eff3cb07 Mon Sep 17 00:00:00 2001 From: Stratoula Kalafateli Date: Mon, 18 Jul 2022 15:59:53 +0300 Subject: [PATCH 084/111] [Lens] Advanced options as accordion (#136276) * [Lens] Change advanced options to accordion * Further changes * Fix jest tests * [CI] Auto-commit changed files from 'node scripts/precommit_hook.js --ref HEAD~1..HEAD --fix' * Fix functional tests * Fix functional tests * Disable filtering auto focus Co-authored-by: kibanamachine <42973632+kibanamachine@users.noreply.github.com> --- .../dimension_panel/advanced_options.tsx | 78 ++----- .../dimension_panel/dimension_editor.tsx | 105 +++------- .../dimension_panel/dimension_panel.test.tsx | 195 +++--------------- .../dimension_panel/filtering.tsx | 23 +-- .../dimension_panel/time_scaling.tsx | 40 ++-- .../dimension_panel/time_shift.tsx | 35 +--- .../operations/definitions/cardinality.tsx | 52 +++-- .../operations/definitions/count.tsx | 52 +++-- .../definitions/filters/filters.tsx | 12 +- .../operations/definitions/index.ts | 4 - .../operations/definitions/metrics.tsx | 52 +++-- .../operations/definitions/terms/index.tsx | 15 +- .../translations/translations/fr-FR.json | 4 - .../translations/translations/ja-JP.json | 4 - .../translations/translations/zh-CN.json | 4 - .../test/functional/page_objects/lens_page.ts | 9 +- 16 files changed, 193 insertions(+), 491 deletions(-) diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/advanced_options.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/advanced_options.tsx index 3d1928edf27dc..598bc5f4658b5 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/advanced_options.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/advanced_options.tsx @@ -5,72 +5,32 @@ * 2.0. */ -import { EuiLink, EuiText, EuiPopover, EuiButtonEmpty, EuiSpacer } from '@elastic/eui'; +import { EuiSpacer, EuiAccordion, EuiText, useEuiTheme } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; -import React, { useState } from 'react'; +import React from 'react'; import { AdvancedOption } from '../operations/definitions'; export function AdvancedOptions(props: { options: AdvancedOption[] }) { - const [popoverOpen, setPopoverOpen] = useState(false); - const popoverOptions = props.options.filter((option) => option.showInPopover); - const inlineOptions = props.options.filter((option) => option.inlineElement); - + const { euiTheme } = useEuiTheme(); return ( - <> - {popoverOptions.length > 0 && ( - - { - setPopoverOpen(!popoverOpen); - }} - > - {i18n.translate('xpack.lens.indexPattern.advancedSettings', { - defaultMessage: 'Add advanced options', - })} - - } - isOpen={popoverOpen} - closePopover={() => { - setPopoverOpen(false); - }} - > - {popoverOptions.map(({ dataTestSubj, onClick, title, optionElement }, index) => ( - - {optionElement ? ( - optionElement - ) : ( - - { - setPopoverOpen(false); - onClick(); - }} - > - {title} - - - )} - {popoverOptions.length - 1 !== index && } - - ))} - + + {i18n.translate('xpack.lens.indexPattern.advancedSettings', { + defaultMessage: 'Advanced', + })} - )} - {inlineOptions.map((option) => ( - + } + > + {props.options.map(({ dataTestSubj, inlineElement }) => ( +
    - {option.inlineElement} - + {inlineElement} +
    ))} - + ); } diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_editor.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_editor.tsx index 4e667e2aa30d6..413f40279a3ce 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_editor.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_editor.tsx @@ -30,7 +30,6 @@ import { resetIncomplete, FieldBasedIndexPatternColumn, canTransition, - DEFAULT_TIME_SCALE, adjustColumnReferencesForChangedColumn, } from '../operations'; import { mergeLayer } from '../state_helpers'; @@ -41,10 +40,10 @@ import type { IndexPattern, IndexPatternField, IndexPatternLayer } from '../type import { trackUiEvent } from '../../lens_ui_telemetry'; import { FormatSelector } from './format_selector'; import { ReferenceEditor } from './reference_editor'; -import { setTimeScaling, TimeScaling } from './time_scaling'; -import { defaultFilter, Filtering, setFilter } from './filtering'; +import { TimeScaling } from './time_scaling'; +import { Filtering } from './filtering'; import { AdvancedOptions } from './advanced_options'; -import { setTimeShift, TimeShift } from './time_shift'; +import { TimeShift } from './time_shift'; import type { LayerType } from '../../../common'; import { quickFunctionsName, @@ -270,8 +269,6 @@ export function DimensionEditor(props: DimensionEditorProps) { .map((def) => def.type); }, [fieldByOperation, operationWithoutField]); - const [filterByOpenInitially, setFilterByOpenInitally] = useState(false); - const [timeShiftedFocused, setTimeShiftFocused] = useState(false); const helpPopoverContainer = useRef(null); useEffect(() => { return () => { @@ -838,23 +835,7 @@ export function DimensionEditor(props: DimensionEditorProps) { { - setStateWrapper( - setTimeScaling(columnId, state.layers[layerId], DEFAULT_TIME_SCALE) - ); - }, - showInPopover: Boolean( - selectedOperationDefinition.timeScalingMode && - selectedOperationDefinition.timeScalingMode !== 'disabled' && - Object.values(state.layers[layerId].columns).some( - (col) => col.operationType === 'date_histogram' - ) && - !selectedColumn.timeScale - ), inlineElement: selectedOperationDefinition.timeScalingMode ? ( { - setFilterByOpenInitally(true); - setStateWrapper(setFilter(columnId, state.layers[layerId], defaultFilter)); - }, - showInPopover: Boolean( - selectedOperationDefinition.filterable && !selectedColumn.filter - ), - inlineElement: - selectedOperationDefinition.filterable && selectedColumn.filter ? ( - - ) : null, + inlineElement: selectedOperationDefinition.filterable ? ( + + ) : null, }, { - title: i18n.translate('xpack.lens.indexPattern.timeShift.label', { - defaultMessage: 'Time shift', - }), dataTestSubj: 'indexPattern-time-shift-enable', - onClick: () => { - setTimeShiftFocused(true); - setStateWrapper(setTimeShift(columnId, state.layers[layerId], '')); - }, - showInPopover: Boolean( + inlineElement: Boolean( selectedOperationDefinition.shiftable && - selectedColumn.timeShift === undefined && (currentIndexPattern.timeFieldName || Object.values(state.layers[layerId].columns).some( (col) => col.operationType === 'date_histogram' )) - ), - inlineElement: - selectedOperationDefinition.shiftable && - selectedColumn.timeShift !== undefined ? ( - - ) : null, + ) ? ( + + ) : null, }, ...(operationDefinitionMap[selectedColumn.operationType].getAdvancedOptions?.( paramEditorProps diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_panel.test.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_panel.test.tsx index 0fa2f171890bf..a2d83da5d89e2 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_panel.test.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/dimension_panel.test.tsx @@ -6,7 +6,7 @@ */ import { ReactWrapper, ShallowWrapper } from 'enzyme'; -import React from 'react'; +import React, { ChangeEvent } from 'react'; import { act } from 'react-dom/test-utils'; import { EuiComboBox, @@ -14,7 +14,6 @@ import { EuiListGroup, EuiRange, EuiSelect, - EuiButtonIcon, } from '@elastic/eui'; import { unifiedSearchPluginMock } from '@kbn/unified-search-plugin/public/mocks'; import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; @@ -1117,37 +1116,21 @@ describe('IndexPatternDimensionEditorPanel', () => { }; } - it('should not show custom options if time scaling is not available', () => { - wrapper = mount( - - ); - wrapper - .find('[data-test-subj="indexPattern-advanced-popover"]') - .hostNodes() - .simulate('click'); - expect( - wrapper.find('[data-test-subj="indexPattern-time-scaling-enable"]').hostNodes() - ).toHaveLength(0); - }); - - it('should show custom options if time scaling is available', () => { + it('should default to None if time scaling is not set', () => { wrapper = mount(); - wrapper - .find('[data-test-subj="indexPattern-advanced-popover"]') - .hostNodes() - .simulate('click'); + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').first().simulate('click'); + expect(wrapper.find('[data-test-subj="indexPattern-time-scaling-enable"]')).toHaveLength(1); expect( - wrapper.find('[data-test-subj="indexPattern-time-scaling-enable"]').hostNodes() - ).toHaveLength(1); + wrapper + .find('[data-test-subj="indexPattern-time-scaling-unit"]') + .find(EuiSelect) + .prop('value') + ).toBe(''); }); it('should show current time scaling if set', () => { wrapper = mount(); + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').first().simulate('click'); expect( wrapper .find('[data-test-subj="indexPattern-time-scaling-unit"]') @@ -1159,14 +1142,13 @@ describe('IndexPatternDimensionEditorPanel', () => { it('should allow to set time scaling initially', () => { const props = getProps({}); wrapper = mount(); + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').first().simulate('click'); wrapper - .find('[data-test-subj="indexPattern-advanced-popover"]') - .hostNodes() - .simulate('click'); - wrapper - .find('[data-test-subj="indexPattern-time-scaling-enable"]') - .hostNodes() - .simulate('click'); + .find('[data-test-subj="indexPattern-time-scaling-unit"]') + .find(EuiSelect) + .prop('onChange')!({ + target: { value: 's' }, + } as ChangeEvent); expect(setState.mock.calls[0]).toEqual([expect.any(Function), { isDimensionComplete: true }]); expect(setState.mock.calls[0][0](props.state)).toEqual({ ...props.state, @@ -1244,10 +1226,7 @@ describe('IndexPatternDimensionEditorPanel', () => { it('should allow to change time scaling', () => { const props = getProps({ timeScale: 's', label: 'Count of records per second' }); wrapper = mount(); - wrapper - .find('button[data-test-subj="indexPattern-advanced-popover"]') - .hostNodes() - .simulate('click'); + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').first().simulate('click'); wrapper.find('[data-test-subj="indexPattern-time-scaling-unit"] select').simulate('change', { target: { value: 'h' }, @@ -1294,28 +1273,6 @@ describe('IndexPatternDimensionEditorPanel', () => { }, }); }); - - it('should allow to remove time scaling', () => { - const props = getProps({ timeScale: 's', label: 'Count of records per second' }); - wrapper = mount(); - wrapper.find('[data-test-subj="indexPattern-time-scaling-remove"] button').simulate('click'); - expect(setState.mock.calls[0]).toEqual([expect.any(Function), { isDimensionComplete: true }]); - expect(setState.mock.calls[0][0](props.state)).toEqual({ - ...props.state, - layers: { - first: { - ...props.state.layers.first, - columns: { - ...props.state.layers.first.columns, - col2: expect.objectContaining({ - timeScale: undefined, - label: 'Count of records', - }), - }, - }, - }, - }); - }); }); describe('time shift', () => { @@ -1347,7 +1304,7 @@ describe('IndexPatternDimensionEditorPanel', () => { }; } - it('should not show custom options if time shift is not available', () => { + it('should not show the TimeShift component if time shift is not available', () => { const props = { ...defaultProps, state: getStateWithColumns({ @@ -1361,7 +1318,7 @@ describe('IndexPatternDimensionEditorPanel', () => { }), columnId: 'col2', }; - wrapper = shallow( + wrapper = mount( { }} /> ); - expect( - wrapper - .find(DimensionEditor) - .dive() - .find(AdvancedOptions) - .dive() - .find('[data-test-subj="indexPattern-time-shift-enable"]') - ).toHaveLength(0); + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').first().simulate('click'); + expect(wrapper.find('[data-test-subj="indexPattern-time-shift-enable"]')).toHaveLength(1); + expect(wrapper.find(TimeShift)).toHaveLength(0); }); it('should show custom options if time shift is available', () => { @@ -1406,14 +1358,9 @@ describe('IndexPatternDimensionEditorPanel', () => { it('should allow to set time shift initially', () => { const props = getProps({}); - wrapper = shallow(); - wrapper - .find(DimensionEditor) - .dive() - .find(AdvancedOptions) - .dive() - .find('[data-test-subj="indexPattern-time-shift-enable"]') - .simulate('click'); + wrapper = mount(); + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').first().simulate('click'); + wrapper.find(TimeShift).find(EuiComboBox).prop('onChange')!([{ value: '1h', label: '' }]); expect((props.setState as jest.Mock).mock.calls[0][0](props.state)).toEqual({ ...props.state, layers: { @@ -1422,7 +1369,7 @@ describe('IndexPatternDimensionEditorPanel', () => { columns: { ...props.state.layers.first.columns, col2: expect.objectContaining({ - timeShift: '', + timeShift: '1h', }), }, }, @@ -1479,31 +1426,6 @@ describe('IndexPatternDimensionEditorPanel', () => { }); }); - it('should allow to time shift', () => { - const props = getProps({ - timeShift: '1h', - }); - wrapper = mount(); - wrapper - .find('[data-test-subj="indexPattern-time-shift-remove"]') - .find(EuiButtonIcon) - .simulate('click'); - expect((props.setState as jest.Mock).mock.calls[0][0](props.state)).toEqual({ - ...props.state, - layers: { - first: { - ...props.state.layers.first, - columns: { - ...props.state.layers.first.columns, - col2: expect.objectContaining({ - timeShift: undefined, - }), - }, - }, - }, - }); - }); - it('should report a generic error for invalid shift string', () => { const props = getProps({ timeShift: '5 months', @@ -1566,16 +1488,13 @@ describe('IndexPatternDimensionEditorPanel', () => { /> ); expect( - wrapper.find('[data-test-subj="indexPattern-advanced-popover"]').hostNodes() + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').hostNodes() ).toHaveLength(0); }); it('should show custom options if filtering is available', () => { wrapper = mount(); - wrapper - .find('[data-test-subj="indexPattern-advanced-popover"]') - .hostNodes() - .simulate('click'); + wrapper.find('[data-test-subj="indexPattern-advanced-accordion"]').first().simulate('click'); expect( wrapper.find('[data-test-subj="indexPattern-filter-by-enable"]').hostNodes() ).toHaveLength(1); @@ -1596,37 +1515,6 @@ describe('IndexPatternDimensionEditorPanel', () => { ).toBe(`a: b`); }); - it('should allow to set filter initially', () => { - const props = getProps({}); - wrapper = mount(); - wrapper - .find('[data-test-subj="indexPattern-advanced-popover"]') - .hostNodes() - .simulate('click'); - wrapper - .find('[data-test-subj="indexPattern-filter-by-enable"]') - .hostNodes() - .simulate('click'); - expect(setState.mock.calls[0]).toEqual([expect.any(Function), { isDimensionComplete: true }]); - expect(setState.mock.calls[0][0](props.state)).toEqual({ - ...props.state, - layers: { - first: { - ...props.state.layers.first, - columns: { - ...props.state.layers.first.columns, - col2: expect.objectContaining({ - filter: { - language: 'kuery', - query: '', - }, - }), - }, - }, - }, - }); - }); - it('should carry over filter to other operation if possible', () => { const props = getProps({ filter: { language: 'kuery', query: 'a: b' }, @@ -1684,33 +1572,6 @@ describe('IndexPatternDimensionEditorPanel', () => { }, }); }); - - it('should allow to remove filter', () => { - const props = getProps({ - filter: { language: 'kuery', query: 'a: b' }, - }); - wrapper = mount(); - wrapper - .find('[data-test-subj="indexPattern-filter-by-remove"]') - .find(EuiButtonIcon) - .simulate('click'); - - expect(setState.mock.calls[0]).toEqual([expect.any(Function), { isDimensionComplete: true }]); - expect(setState.mock.calls[0][0](props.state)).toEqual({ - ...props.state, - layers: { - first: { - ...props.state.layers.first, - columns: { - ...props.state.layers.first.columns, - col2: expect.objectContaining({ - filter: undefined, - }), - }, - }, - }, - }); - }); }); it('should render invalid field if field reference is broken', () => { diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/filtering.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/filtering.tsx index d478267092606..80e369526c8e4 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/filtering.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/filtering.tsx @@ -8,7 +8,6 @@ import React, { useState, useCallback } from 'react'; import { i18n } from '@kbn/i18n'; import { isEqual } from 'lodash'; import { - EuiButtonIcon, EuiLink, EuiPanel, EuiPopover, @@ -54,7 +53,6 @@ export function Filtering({ layer, updateLayer, indexPattern, - isInitiallyOpen, helpMessage, }: { selectedColumn: GenericIndexPatternColumn; @@ -62,7 +60,6 @@ export function Filtering({ columnId: string; layer: IndexPatternLayer; updateLayer: (newLayer: IndexPatternLayer) => void; - isInitiallyOpen: boolean; helpMessage: string | null; }) { const inputFilter = selectedColumn.filter; @@ -79,7 +76,7 @@ export function Filtering({ value: inputFilter ?? defaultFilter, onChange, }); - const [filterPopoverOpen, setFilterPopoverOpen] = useState(isInitiallyOpen); + const [filterPopoverOpen, setFilterPopoverOpen] = useState(false); const onClosePopup: EuiPopoverProps['closePopover'] = useCallback(() => { setFilterPopoverOpen(false); @@ -90,7 +87,7 @@ export function Filtering({ const selectedOperation = operationDefinitionMap[selectedColumn.operationType]; - if (!selectedOperation.filterable || !inputFilter) { + if (!selectedOperation.filterable) { return null; } @@ -143,25 +140,12 @@ export function Filtering({ defaultMessage: 'Click to edit', })} > - {inputFilter.query || + {inputFilter?.query || i18n.translate('xpack.lens.indexPattern.filterBy.emptyFilterQuery', { defaultMessage: '(empty)', })}
    - - { - updateLayer(setFilter(columnId, layer, undefined)); - }} - iconType="cross" - /> -
    } @@ -175,6 +159,7 @@ export function Filtering({ > ({ - value: unit, - text, - }))} + options={[ + { + value: '', + text: i18n.translate('xpack.lens.timeScale.normalizeNone', { + defaultMessage: 'None', + }), + }, + ...Object.entries(unitSuffixesLong).map(([unit, text]) => ({ + value: unit, + text, + })), + ]} data-test-subj="indexPattern-time-scaling-unit" - value={selectedColumn.timeScale} + value={selectedColumn.timeScale ?? ''} onChange={(e) => { - updateLayer(setTimeScaling(columnId, layer, e.target.value as TimeScaleUnit)); + const value = e.target.value || undefined; + updateLayer(setTimeScaling(columnId, layer, value as TimeScaleUnit)); }} /> - {selectedOperation.timeScalingMode === 'optional' && ( - - { - updateLayer(setTimeScaling(columnId, layer, undefined)); - }} - iconType="cross" - /> - - )} ); diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/time_shift.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/time_shift.tsx index b74e26cb24895..6620a2259f3ac 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/time_shift.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/dimension_panel/time_shift.tsx @@ -5,11 +5,10 @@ * 2.0. */ -import { EuiButtonIcon } from '@elastic/eui'; import { EuiFormRow, EuiFlexItem, EuiFlexGroup } from '@elastic/eui'; import { EuiComboBox } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; -import React, { useEffect, useRef, useState } from 'react'; +import React, { useEffect, useState } from 'react'; import type { Query } from '@kbn/es-query'; import { DatatableUtilitiesService, parseTimeShift } from '@kbn/data-plugin/common'; @@ -68,7 +67,6 @@ export function TimeShift({ layer, updateLayer, indexPattern, - isFocused, activeData, layerId, }: { @@ -78,17 +76,15 @@ export function TimeShift({ columnId: string; layer: IndexPatternLayer; updateLayer: (newLayer: IndexPatternLayer) => void; - isFocused: boolean; activeData: IndexPatternDimensionEditorProps['activeData']; layerId: string; }) { - const focusSetRef = useRef(false); const [localValue, setLocalValue] = useState(selectedColumn.timeShift); useEffect(() => { setLocalValue(selectedColumn.timeShift); }, [selectedColumn.timeShift]); const selectedOperation = operationDefinitionMap[selectedColumn.operationType]; - if (!selectedOperation.shiftable || selectedColumn.timeShift === undefined) { + if (!selectedOperation.shiftable) { return null; } @@ -124,17 +120,7 @@ export function TimeShift({ } return ( -
    { - if (r && isFocused) { - const timeShiftInput = r.querySelector('[data-test-subj="comboBoxSearchInput"]'); - if (!focusSetRef.current && timeShiftInput instanceof HTMLInputElement) { - focusSetRef.current = true; - timeShiftInput.focus(); - } - } - }} - > +
    - - { - updateLayer(setTimeShift(columnId, layer, undefined)); - }} - iconType="cross" - /> -
    diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/cardinality.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/cardinality.tsx index 7b3ccf8da067b..017a3580824f8 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/cardinality.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/cardinality.tsx @@ -134,36 +134,30 @@ export const cardinalityOperation: OperationDefinition< return [ { dataTestSubj: 'hide-zero-values', - optionElement: ( - <> - { - paramEditorUpdater( - updateColumnParam({ - layer, - columnId, - paramName: 'emptyAsNull', - value: !currentColumn.params?.emptyAsNull, - }) - ); - }} - compressed - /> - + inlineElement: ( + { + paramEditorUpdater( + updateColumnParam({ + layer, + columnId, + paramName: 'emptyAsNull', + value: !currentColumn.params?.emptyAsNull, + }) + ); + }} + compressed + /> ), - title: '', - showInPopover: true, - inlineElement: null, - onClick: () => {}, }, ]; }, diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/count.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/count.tsx index 014ff0f726cc7..888c992031430 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/count.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/count.tsx @@ -118,36 +118,30 @@ export const countOperation: OperationDefinition - { - paramEditorUpdater( - updateColumnParam({ - layer, - columnId, - paramName: 'emptyAsNull', - value: !currentColumn.params?.emptyAsNull, - }) - ); - }} - compressed - /> - + inlineElement: ( + { + paramEditorUpdater( + updateColumnParam({ + layer, + columnId, + paramName: 'emptyAsNull', + value: !currentColumn.params?.emptyAsNull, + }) + ); + }} + compressed + /> ), - title: '', - showInPopover: true, - inlineElement: null, - onClick: () => {}, }, ]; }, diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/filters/filters.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/filters/filters.tsx index 68798bd11aee5..5f3409602d93e 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/filters/filters.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/filters/filters.tsx @@ -54,15 +54,17 @@ const defaultFilter: Filter = { label: '', }; -export const validateQuery = (input: Query, indexPattern: IndexPattern) => { +export const validateQuery = (input: Query | undefined, indexPattern: IndexPattern) => { let isValid = true; let error: string | undefined; try { - if (input.language === 'kuery') { - toElasticsearchQuery(fromKueryExpression(input.query), indexPattern); - } else { - luceneStringToDsl(input.query); + if (input) { + if (input.language === 'kuery') { + toElasticsearchQuery(fromKueryExpression(input.query), indexPattern); + } else { + luceneStringToDsl(input.query); + } } } catch (e) { isValid = false; diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/index.ts b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/index.ts index b65c946c3b15e..8f3be3a59a836 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/index.ts +++ b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/index.ts @@ -232,11 +232,7 @@ export interface HelpProps { export type TimeScalingMode = 'disabled' | 'mandatory' | 'optional'; export interface AdvancedOption { - title: string; - optionElement?: React.ReactElement; dataTestSubj: string; - onClick: () => void; - showInPopover: boolean; inlineElement: React.ReactElement | null; helpPopup?: string | null; } diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/metrics.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/metrics.tsx index d8b1b48f3756e..5f3973b84e8fd 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/metrics.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/metrics.tsx @@ -158,36 +158,30 @@ function buildMetricOperation>({ return [ { dataTestSubj: 'hide-zero-values', - optionElement: ( - <> - { - paramEditorUpdater( - updateColumnParam({ - layer, - columnId, - paramName: 'emptyAsNull', - value: !currentColumn.params?.emptyAsNull, - }) - ); - }} - compressed - /> - + inlineElement: ( + { + paramEditorUpdater( + updateColumnParam({ + layer, + columnId, + paramName: 'emptyAsNull', + value: !currentColumn.params?.emptyAsNull, + }) + ); + }} + compressed + /> ), - title: '', - showInPopover: true, - inlineElement: null, - onClick: () => {}, }, ]; }, diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/terms/index.tsx b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/terms/index.tsx index 31effec454efd..18c5045b03b16 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/terms/index.tsx +++ b/x-pack/plugins/lens/public/indexpattern_datasource/operations/definitions/terms/index.tsx @@ -17,6 +17,8 @@ import { EuiIconTip, htmlIdGenerator, EuiButtonGroup, + EuiText, + useEuiTheme, } from '@elastic/eui'; import { uniq } from 'lodash'; import { AggFunctionsMapping } from '@kbn/data-plugin/public'; @@ -616,6 +618,8 @@ export const termsOperation: OperationDefinition + {i18n.translate('xpack.lens.indexPattern.terms.advancedSettings', { + defaultMessage: 'Advanced', + })} + + } data-test-subj="indexPattern-terms-advanced" > diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index fb05c80689a0b..cb73b4bb74474 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -293,7 +293,6 @@ "xpack.lens.fieldFormats.suffix.m": "/m", "xpack.lens.fieldFormats.suffix.s": "/s", "xpack.lens.fieldFormats.suffix.title": "Suffixe", - "xpack.lens.filterBy.removeLabel": "Supprimer le filtre", "xpack.lens.fittingFunctionsDescription.carry": "Remplit les blancs avec la dernière valeur", "xpack.lens.fittingFunctionsDescription.linear": "Remplit les blancs avec une ligne", "xpack.lens.fittingFunctionsDescription.lookahead": "Remplit les blancs avec la valeur suivante", @@ -669,7 +668,6 @@ "xpack.lens.indexPattern.termsWithMultipleTermsAndScriptedFields": "Les champs scriptés ne sont pas pris en charge lors de l’utilisation de champs multiples ; {fields} trouvés.", "xpack.lens.indexPattern.time_scale": "indicateur : nombre, unité : s|m|h|d|w|M|y", "xpack.lens.indexPattern.timeScale": "Normaliser par unité", - "xpack.lens.indexPattern.timeScale.enableTimeScale": "Normaliser par unité", "xpack.lens.indexPattern.timeScale.label": "Normaliser par unité", "xpack.lens.indexPattern.timeScale.missingUnit": "Aucune unité spécifiée pour Normaliser par unité.", "xpack.lens.indexPattern.timeScale.tooltip": "Normalisez les valeurs pour qu'elles soient toujours affichées en tant que taux par unité de temps spécifiée, indépendamment de l'intervalle de dates sous-jacent.", @@ -878,8 +876,6 @@ "xpack.lens.table.visualOptionsHeaderRowHeightLabel": "Hauteur de ligne d’en-tête", "xpack.lens.table.visualOptionsPaginateTable": "Paginer le tableau", "xpack.lens.table.visualOptionsPaginateTableTooltip": "La pagination est masquée lorsqu’il y a moins de 10 éléments.", - "xpack.lens.timeScale.removeLabel": "Retirer la normalisation par unité de temps", - "xpack.lens.timeShift.removeLabel": "Retirer le décalage temporel", "xpack.lens.TSVBLabel": "TSVB", "xpack.lens.uniqueLabel": "{label} [{num}]", "xpack.lens.unknownVisType.shortMessage": "Type de visualisation inconnu", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index 05d2624262465..292907d6b096f 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -294,7 +294,6 @@ "xpack.lens.fieldFormats.suffix.m": "/m", "xpack.lens.fieldFormats.suffix.s": "/s", "xpack.lens.fieldFormats.suffix.title": "接尾辞", - "xpack.lens.filterBy.removeLabel": "フィルターを削除", "xpack.lens.fittingFunctionsDescription.carry": "ギャップを最後の値で埋める", "xpack.lens.fittingFunctionsDescription.linear": "ギャップを線で埋める", "xpack.lens.fittingFunctionsDescription.lookahead": "ギャップを次の値で埋める", @@ -670,7 +669,6 @@ "xpack.lens.indexPattern.termsWithMultipleTermsAndScriptedFields": "複数のフィールドを使用するときには、スクリプトフィールドがサポートされていません。{fields}が見つかりました", "xpack.lens.indexPattern.time_scale": "メトリック:数値、単位:s|m|h|d|w|M|y", "xpack.lens.indexPattern.timeScale": "単位で正規化", - "xpack.lens.indexPattern.timeScale.enableTimeScale": "単位で正規化", "xpack.lens.indexPattern.timeScale.label": "単位で正規化", "xpack.lens.indexPattern.timeScale.missingUnit": "単位による正規化の単位が指定されていません。", "xpack.lens.indexPattern.timeScale.tooltip": "基本の日付間隔に関係なく、常に指定された時間単位のレートとして表示されるように値を正規化します。", @@ -879,8 +877,6 @@ "xpack.lens.table.visualOptionsHeaderRowHeightLabel": "ヘッダー行高さ", "xpack.lens.table.visualOptionsPaginateTable": "表のページ制御", "xpack.lens.table.visualOptionsPaginateTableTooltip": "項目が9件以下の場合、ページ制御は非表示です", - "xpack.lens.timeScale.removeLabel": "時間単位で正規化を削除", - "xpack.lens.timeShift.removeLabel": "時間シフトを削除", "xpack.lens.TSVBLabel": "TSVB", "xpack.lens.uniqueLabel": "{label} [{num}]", "xpack.lens.unknownVisType.longMessage": "ビジュアライゼーションタイプ{visType}を解決できませんでした。", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index 5157f316e9940..9fafcf0f11918 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -294,7 +294,6 @@ "xpack.lens.fieldFormats.suffix.m": "/m", "xpack.lens.fieldFormats.suffix.s": "/s", "xpack.lens.fieldFormats.suffix.title": "后缀", - "xpack.lens.filterBy.removeLabel": "移除筛选", "xpack.lens.fittingFunctionsDescription.carry": "使用最后一个值填充空距", "xpack.lens.fittingFunctionsDescription.linear": "使用线填充空距", "xpack.lens.fittingFunctionsDescription.lookahead": "使用下一个值填充空距", @@ -670,7 +669,6 @@ "xpack.lens.indexPattern.termsWithMultipleTermsAndScriptedFields": "使用多个字段时不支持脚本字段,找到 {fields}", "xpack.lens.indexPattern.time_scale": "指标:数字,单位:s|m|h|d|w|M|y", "xpack.lens.indexPattern.timeScale": "按单位标准化", - "xpack.lens.indexPattern.timeScale.enableTimeScale": "按单位标准化", "xpack.lens.indexPattern.timeScale.label": "按单位标准化", "xpack.lens.indexPattern.timeScale.missingUnit": "没有为按单位标准化指定单位。", "xpack.lens.indexPattern.timeScale.tooltip": "将值标准化为始终显示为每指定时间单位速率,无论基础日期时间间隔是多少。", @@ -879,8 +877,6 @@ "xpack.lens.table.visualOptionsHeaderRowHeightLabel": "标题行高", "xpack.lens.table.visualOptionsPaginateTable": "对表分页", "xpack.lens.table.visualOptionsPaginateTableTooltip": "如果小于 10 项,将隐藏分页", - "xpack.lens.timeScale.removeLabel": "删除按时间单位标准化", - "xpack.lens.timeShift.removeLabel": "移除时间偏移", "xpack.lens.TSVBLabel": "TSVB", "xpack.lens.uniqueLabel": "{label} [{num}]", "xpack.lens.unknownVisType.longMessage": "无法解析可视化类型 {visType}。", diff --git a/x-pack/test/functional/page_objects/lens_page.ts b/x-pack/test/functional/page_objects/lens_page.ts index e28fe8f8da8e3..c440c25784290 100644 --- a/x-pack/test/functional/page_objects/lens_page.ts +++ b/x-pack/test/functional/page_objects/lens_page.ts @@ -512,10 +512,7 @@ export function LensPageProvider({ getService, getPageObjects }: FtrProviderCont }, async enableTimeShift() { - await testSubjects.click('indexPattern-advanced-popover'); - await retry.try(async () => { - await testSubjects.click('indexPattern-time-shift-enable'); - }); + await testSubjects.click('indexPattern-advanced-accordion'); }, async setTimeShift(shift: string) { @@ -523,9 +520,9 @@ export function LensPageProvider({ getService, getPageObjects }: FtrProviderCont }, async enableFilter() { - await testSubjects.click('indexPattern-advanced-popover'); + await testSubjects.click('indexPattern-advanced-accordion'); await retry.try(async () => { - await testSubjects.click('indexPattern-filter-by-enable'); + await testSubjects.click('indexPattern-filters-existingFilterTrigger'); }); }, From a9bdfebbe5773f67707eeb98507a51852854813b Mon Sep 17 00:00:00 2001 From: Angela Chuang <6295984+angorayc@users.noreply.github.com> Date: Mon, 18 Jul 2022 14:05:18 +0100 Subject: [PATCH 085/111] Show index pattern in Inspector (#136407) * show index pattern in inspector * clean up * fix unit tests and types * fix unit tests Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../search_source/inspect/inspector_stats.ts | 12 ++ .../data/common/search/search_source/mocks.ts | 2 + .../search_source/search_source.test.ts | 124 ++++++++++++++++++ .../search/search_source/search_source.ts | 60 +++++++++ .../saved_searches/get_saved_searches.test.ts | 2 + 5 files changed, 200 insertions(+) diff --git a/src/plugins/data/common/search/search_source/inspect/inspector_stats.ts b/src/plugins/data/common/search/search_source/inspect/inspector_stats.ts index bd4b0c2066479..4d4f6d4b04f3b 100644 --- a/src/plugins/data/common/search/search_source/inspect/inspector_stats.ts +++ b/src/plugins/data/common/search/search_source/inspect/inspector_stats.ts @@ -23,8 +23,20 @@ import type { ISearchSource } from '../../../../public'; export function getRequestInspectorStats(searchSource: ISearchSource) { const stats: RequestStatistics = {}; const index = searchSource.getField('index'); + const indexFilters = searchSource.getActiveIndexFilter(); if (index) { + if (indexFilters.length > 0) { + stats.indexFilter = { + label: i18n.translate('data.search.searchSource.indexFilterLabel', { + defaultMessage: 'Index Pattern', + }), + value: indexFilters.join(', '), + description: i18n.translate('data.search.searchSource.indexFilterDescription', { + defaultMessage: 'The active index pattern.', + }), + }; + } stats.indexPattern = { label: i18n.translate('data.search.searchSource.dataViewLabel', { defaultMessage: 'Data view', diff --git a/src/plugins/data/common/search/search_source/mocks.ts b/src/plugins/data/common/search/search_source/mocks.ts index e291a9ec27cff..a17ef12484b65 100644 --- a/src/plugins/data/common/search/search_source/mocks.ts +++ b/src/plugins/data/common/search/search_source/mocks.ts @@ -36,6 +36,8 @@ export const searchSourceInstanceMock: MockedKeys = { getSerializedFields: jest.fn(), serialize: jest.fn(), toExpressionAst: jest.fn(), + getActiveIndexFilter: jest.fn(), + parseActiveIndexPatternFromQueryString: jest.fn(), }; export const searchSourceCommonMock: jest.Mocked = { diff --git a/src/plugins/data/common/search/search_source/search_source.test.ts b/src/plugins/data/common/search/search_source/search_source.test.ts index 10f96ec0526f9..7c571eb392540 100644 --- a/src/plugins/data/common/search/search_source/search_source.test.ts +++ b/src/plugins/data/common/search/search_source/search_source.test.ts @@ -117,6 +117,130 @@ describe('SearchSource', () => { }); }); + describe('#getActiveIndexFilter()', () => { + test('pase _index from query', () => { + searchSource.setField('query', { + language: 'kuery', + query: `_INDEX : fakebeat and _index : "mybeat-*"`, + }); + expect(searchSource.getActiveIndexFilter()).toMatchInlineSnapshot( + ['mybeat-*'], + ` + Array [ + "mybeat-*", + ] + ` + ); + }); + + test('pase _index from filter', () => { + const filter = [ + { + query: { match_phrase: { _index: 'auditbeat-*' } }, + meta: { + key: '_index', + alias: null, + disabled: false, + negate: false, + params: { + query: 'auditbeat-*', + }, + type: 'phrase', + }, + }, + { + query: { + bool: { + should: [ + { + match_phrase: { + _index: 'auditbeat-*', + }, + }, + ], + }, + }, + meta: { + key: '_index', + alias: null, + disabled: false, + negate: false, + params: ['auditbeat-*'], + type: 'phrase', + }, + }, + ]; + searchSource.setField('filter', filter); + expect(searchSource.getActiveIndexFilter()).toMatchInlineSnapshot( + ['auditbeat-*'], + ` + Array [ + "auditbeat-*", + ] + ` + ); + }); + + test('pase _index from query and filter with negate equals to true', () => { + const filter = [ + { + query: { + match_phrase: { + _index: 'auditbeat-*', + }, + }, + meta: { + key: '_index', + alias: null, + disabled: false, + negate: true, + params: { query: 'auditbeat-*' }, + type: 'phrase', + }, + }, + ]; + searchSource.setField('filter', filter); + searchSource.setField('query', { + language: 'kuery', + query: '_index : auditbeat-*', + }); + expect(searchSource.getActiveIndexFilter()).toMatchInlineSnapshot([], `Array []`); + }); + + test('pase _index from query and filter with negate equals to true and disabled equals to true', () => { + const filter = [ + { + query: { + match_phrase: { + _index: 'auditbeat-*', + }, + }, + meta: { + key: '_index', + alias: null, + disabled: true, + negate: true, + params: { query: 'auditbeat-*' }, + type: 'phrase', + }, + }, + ]; + searchSource.setField('filter', filter); + searchSource.setField('query', { + language: 'kuery', + query: '_index : auditbeat-*', + }); + expect(searchSource.getActiveIndexFilter()).toMatchInlineSnapshot( + ['auditbeat-*'], + ` + Array [ + "auditbeat-*", + ] + ` + ); + }); + }); + describe('#removeField()', () => { test('remove property', () => { searchSource = new SearchSource({}, searchSourceDependencies); diff --git a/src/plugins/data/common/search/search_source/search_source.ts b/src/plugins/data/common/search/search_source/search_source.ts index 4c7606fea4262..a3f127573644d 100644 --- a/src/plugins/data/common/search/search_source/search_source.ts +++ b/src/plugins/data/common/search/search_source/search_source.ts @@ -81,6 +81,7 @@ import { buildExpression, buildExpressionFunction, } from '@kbn/expressions-plugin/common'; +import _ from 'lodash'; import { normalizeSortRequest } from './normalize_sort_request'; import { AggConfigSerialized, DataViewField, SerializedSearchSourceFields } from '../..'; @@ -252,6 +253,44 @@ export class SearchSource { return parent && parent.getField(field); } + getActiveIndexFilter() { + const { filter: originalFilters, query } = this.getFields(); + + let filters: Filter[] = []; + if (originalFilters) { + filters = this.getFilters(originalFilters); + } + + const queryString = Array.isArray(query) ? query.map((q) => q.query) : query?.query; + + const indexPatternFromQuery = + typeof queryString === 'string' + ? this.parseActiveIndexPatternFromQueryString(queryString) + : queryString?.reduce((acc: string[], currStr: string) => { + return acc.concat(this.parseActiveIndexPatternFromQueryString(currStr)); + }, []) ?? []; + + const activeIndexPattern: string[] = filters?.reduce((acc, f) => { + if (f.meta.key === '_index' && f.meta.disabled === false) { + if (f.meta.negate === false) { + return _.concat(acc, f.meta.params.query ?? f.meta.params); + } else { + if (Array.isArray(f.meta.params)) { + return _.difference(acc, f.meta.params); + } else { + return _.difference(acc, [f.meta.params.query]); + } + } + } else { + return acc; + } + }, indexPatternFromQuery); + + const dedupActiveIndexPattern = new Set([...activeIndexPattern]); + + return [...dedupActiveIndexPattern]; + } + /** * Get the field from our own fields, don't traverse up the chain */ @@ -994,4 +1033,25 @@ export class SearchSource { return ast; } + + parseActiveIndexPatternFromQueryString(queryString: string): string[] { + let m; + const indexPatternSet: Set = new Set(); + const regex = /\s?(_index)\s?:\s?[\'\"]?(\w+\-?\*?)[\'\"]?\s?(\w+)?/g; + + while ((m = regex.exec(queryString)) !== null) { + // This is necessary to avoid infinite loops with zero-width matches + if (m.index === regex.lastIndex) { + regex.lastIndex++; + } + + m.forEach((match, groupIndex) => { + if (groupIndex === 2) { + indexPatternSet.add(match); + } + }); + } + + return [...indexPatternSet]; + } } diff --git a/src/plugins/discover/public/services/saved_searches/get_saved_searches.test.ts b/src/plugins/discover/public/services/saved_searches/get_saved_searches.test.ts index 3e103d6ea3699..c0c4a19ea4e2d 100644 --- a/src/plugins/discover/public/services/saved_searches/get_saved_searches.test.ts +++ b/src/plugins/discover/public/services/saved_searches/get_saved_searches.test.ts @@ -112,6 +112,7 @@ describe('getSavedSearch', () => { "destroy": [MockFunction], "fetch": [MockFunction], "fetch$": [MockFunction], + "getActiveIndexFilter": [MockFunction], "getField": [MockFunction], "getFields": [MockFunction], "getId": [MockFunction], @@ -121,6 +122,7 @@ describe('getSavedSearch', () => { "getSerializedFields": [MockFunction], "history": Array [], "onRequestStart": [MockFunction], + "parseActiveIndexPatternFromQueryString": [MockFunction], "removeField": [MockFunction], "serialize": [MockFunction], "setField": [MockFunction], From e57d1f4ab9f4a6251ee1e1c1a03909b0fb016bf1 Mon Sep 17 00:00:00 2001 From: Cristina Amico Date: Mon, 18 Jul 2022 15:14:55 +0200 Subject: [PATCH 086/111] [Fleet] Pass start_time to actions when rolling upgrades maintenence window is set to immediately (#136384) * [Fleet] Pass start_time to actions when rolling upgrades maintenence window is set to immediately * Break up cases for rolling and scheduled upgrades Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../fleet/server/services/agents/upgrade.ts | 40 +++++++++++---- .../apis/agents/upgrade.ts | 51 ++++++++++++++++++- 2 files changed, 81 insertions(+), 10 deletions(-) diff --git a/x-pack/plugins/fleet/server/services/agents/upgrade.ts b/x-pack/plugins/fleet/server/services/agents/upgrade.ts index 5f9e6bc420b9a..9ec85f1fe69fb 100644 --- a/x-pack/plugins/fleet/server/services/agents/upgrade.ts +++ b/x-pack/plugins/fleet/server/services/agents/upgrade.ts @@ -177,15 +177,10 @@ async function upgradeBatch( source_uri: options.sourceUri, }; - const rollingUpgradeOptions = options?.upgradeDurationSeconds - ? { - start_time: options.startTime ?? now, - minimum_execution_duration: MINIMUM_EXECUTION_DURATION_SECONDS, - expiration: moment(options.startTime ?? now) - .add(options?.upgradeDurationSeconds, 'seconds') - .toISOString(), - } - : {}; + const rollingUpgradeOptions = getRollingUpgradeOptions( + options?.startTime, + options.upgradeDurationSeconds + ); await createAgentAction(esClient, { created_at: now, @@ -351,3 +346,30 @@ async function _getUpgradeActions(esClient: ElasticsearchClient, now = new Date( }, {} as { [k: string]: CurrentUpgrade }) ); } + +const getRollingUpgradeOptions = (startTime?: string, upgradeDurationSeconds?: number) => { + const now = new Date().toISOString(); + // Perform a rolling upgrade + if (upgradeDurationSeconds) { + return { + start_time: startTime ?? now, + minimum_execution_duration: MINIMUM_EXECUTION_DURATION_SECONDS, + expiration: moment(startTime ?? now) + .add(upgradeDurationSeconds, 'seconds') + .toISOString(), + }; + } + // Schedule without rolling upgrade (Immediately after start_time) + if (startTime && !upgradeDurationSeconds) { + return { + start_time: startTime ?? now, + minimum_execution_duration: MINIMUM_EXECUTION_DURATION_SECONDS, + expiration: moment(startTime) + .add(MINIMUM_EXECUTION_DURATION_SECONDS, 'seconds') + .toISOString(), + }; + } else { + // Regular bulk upgrade (non scheduled, non rolling) + return {}; + } +}; diff --git a/x-pack/test/fleet_api_integration/apis/agents/upgrade.ts b/x-pack/test/fleet_api_integration/apis/agents/upgrade.ts index 0499843415e64..03ef3c533dbab 100644 --- a/x-pack/test/fleet_api_integration/apis/agents/upgrade.ts +++ b/x-pack/test/fleet_api_integration/apis/agents/upgrade.ts @@ -400,7 +400,7 @@ export default function (providerContext: FtrProviderContext) { expect(typeof agent2data.body.item.upgrade_started_at).to.be('undefined'); }); - it('should create a .fleet-actions document with the agents, version, and upgrade window', async () => { + it('should create a .fleet-actions document with the agents, version, and upgrade window when rollout_duration_seconds passed', async () => { await es.update({ id: 'agent1', refresh: 'wait_for', @@ -449,6 +449,55 @@ export default function (providerContext: FtrProviderContext) { expect(action.agents).contain('agent1'); expect(action.agents).contain('agent2'); }); + it('should create a .fleet-actions document with the agents, version, and start_time if start_time passed', async () => { + await es.update({ + id: 'agent1', + refresh: 'wait_for', + index: AGENTS_INDEX, + body: { + doc: { + local_metadata: { elastic: { agent: { upgradeable: true, version: '0.0.0' } } }, + }, + }, + }); + await es.update({ + id: 'agent2', + refresh: 'wait_for', + index: AGENTS_INDEX, + body: { + doc: { + local_metadata: { elastic: { agent: { upgradeable: true, version: '0.0.0' } } }, + }, + }, + }); + await supertest + .post(`/api/fleet/agents/bulk_upgrade`) + .set('kbn-xsrf', 'xxx') + .send({ + version: fleetServerVersion, + agents: ['agent1', 'agent2'], + start_time: '2022-07-14T08:54:46.987Z', + }) + .expect(200); + + const actionsRes = await es.search({ + index: '.fleet-actions', + body: { + sort: [{ '@timestamp': { order: 'desc' } }], + }, + }); + + const action: any = actionsRes.hits.hits[0]._source; + + expect(action).to.have.keys( + 'agents', + 'expiration', + 'start_time', + 'minimum_execution_duration' + ); + expect(action.agents).contain('agent1'); + expect(action.agents).contain('agent2'); + }); it('should allow to upgrade multiple upgradeable agents by kuery', async () => { await es.update({ From 46dd8104d3d49bf916dadb6ad545a9c029fd7f33 Mon Sep 17 00:00:00 2001 From: Christos Nasikas Date: Mon, 18 Jul 2022 16:26:49 +0300 Subject: [PATCH 087/111] [Cases] Prevent unregistered attachments from being created (#136383) * Prevent unregistered persistable state attachments from being created * Add external reference registry on the backend * PR feedback Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../external_reference_registry.ts | 15 ++++++++++ .../server/attachment_framework/types.ts | 7 +++++ .../cases/server/client/attachments/add.ts | 29 ++++++++++++++++++- x-pack/plugins/cases/server/client/factory.ts | 4 +++ x-pack/plugins/cases/server/client/types.ts | 4 +++ x-pack/plugins/cases/server/plugin.ts | 7 +++++ .../{cases_client_user => cases}/kibana.json | 2 +- .../{cases_client_user => cases}/package.json | 4 +-- .../server/attachments/external_reference.ts | 12 ++++++++ .../server}/attachments/persistable_state.ts | 2 +- .../server/index.ts | 0 .../server/plugin.ts | 7 +++++ .../security_solution/server/plugin.ts | 7 +---- .../external_references.ts | 14 +++++++++ .../persistable_state.ts | 14 +++++++++ .../server/attachments/external_reference.ts | 12 ++++++++ .../fixtures/plugins/cases/server/plugin.ts | 2 ++ 17 files changed, 131 insertions(+), 11 deletions(-) create mode 100644 x-pack/plugins/cases/server/attachment_framework/external_reference_registry.ts rename x-pack/test/cases_api_integration/common/fixtures/plugins/{cases_client_user => cases}/kibana.json (88%) rename x-pack/test/cases_api_integration/common/fixtures/plugins/{cases_client_user => cases}/package.json (70%) create mode 100644 x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/attachments/external_reference.ts rename x-pack/test/cases_api_integration/common/fixtures/plugins/{security_solution => cases/server}/attachments/persistable_state.ts (92%) rename x-pack/test/cases_api_integration/common/fixtures/plugins/{cases_client_user => cases}/server/index.ts (100%) rename x-pack/test/cases_api_integration/common/fixtures/plugins/{cases_client_user => cases}/server/plugin.ts (83%) create mode 100644 x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/attachments/external_reference.ts diff --git a/x-pack/plugins/cases/server/attachment_framework/external_reference_registry.ts b/x-pack/plugins/cases/server/attachment_framework/external_reference_registry.ts new file mode 100644 index 0000000000000..131f91868e0d9 --- /dev/null +++ b/x-pack/plugins/cases/server/attachment_framework/external_reference_registry.ts @@ -0,0 +1,15 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { AttachmentTypeRegistry } from '../../common/registry'; +import { ExternalReferenceAttachmentType } from './types'; + +export class ExternalReferenceAttachmentTypeRegistry extends AttachmentTypeRegistry { + constructor() { + super('ExternalReferenceAttachmentTypeRegistry'); + } +} diff --git a/x-pack/plugins/cases/server/attachment_framework/types.ts b/x-pack/plugins/cases/server/attachment_framework/types.ts index eb99133149e48..50d9952a807ad 100644 --- a/x-pack/plugins/cases/server/attachment_framework/types.ts +++ b/x-pack/plugins/cases/server/attachment_framework/types.ts @@ -23,7 +23,14 @@ export interface PersistableStateAttachmentTypeSetup id: string; } +export interface ExternalReferenceAttachmentType { + id: string; +} + export interface AttachmentFramework { + registerExternalReference: ( + externalReferenceAttachmentType: ExternalReferenceAttachmentType + ) => void; registerPersistableState: ( persistableStateAttachmentType: PersistableStateAttachmentTypeSetup ) => void; diff --git a/x-pack/plugins/cases/server/client/attachments/add.ts b/x-pack/plugins/cases/server/client/attachments/add.ts index 2c58845ec6d57..979828c35ecdd 100644 --- a/x-pack/plugins/cases/server/client/attachments/add.ts +++ b/x-pack/plugins/cases/server/client/attachments/add.ts @@ -12,6 +12,10 @@ import { identity } from 'fp-ts/lib/function'; import { SavedObjectsUtils } from '@kbn/core/server'; +import { + isCommentRequestTypeExternalReference, + isCommentRequestTypePersistableState, +} from '../../../common/utils/attachments'; import { CaseResponse, CommentRequest, CommentRequestRt, throwErrors } from '../../../common/api'; import { CaseCommentModel } from '../../common/models'; @@ -50,7 +54,12 @@ export const addComment = async ( fold(throwErrors(Boom.badRequest), identity) ); - const { logger, authorization } = clientArgs; + const { + logger, + authorization, + persistableStateAttachmentTypeRegistry, + externalReferenceAttachmentTypeRegistry, + } = clientArgs; decodeCommentRequest(comment); try { @@ -61,6 +70,24 @@ export const addComment = async ( entities: [{ owner: comment.owner, id: savedObjectID }], }); + if ( + isCommentRequestTypeExternalReference(query) && + !externalReferenceAttachmentTypeRegistry.has(query.externalReferenceAttachmentTypeId) + ) { + throw Boom.badRequest( + `Attachment type ${query.externalReferenceAttachmentTypeId} is not registered.` + ); + } + + if ( + isCommentRequestTypePersistableState(query) && + !persistableStateAttachmentTypeRegistry.has(query.persistableStateAttachmentTypeId) + ) { + throw Boom.badRequest( + `Attachment type ${query.persistableStateAttachmentTypeId} is not registered.` + ); + } + const createdDate = new Date().toISOString(); const model = await CaseCommentModel.create(caseId, clientArgs); diff --git a/x-pack/plugins/cases/server/client/factory.ts b/x-pack/plugins/cases/server/client/factory.ts index cbf859e1781ec..5b28ca5ffd21a 100644 --- a/x-pack/plugins/cases/server/client/factory.ts +++ b/x-pack/plugins/cases/server/client/factory.ts @@ -30,6 +30,7 @@ import { import { AuthorizationAuditLogger } from '../authorization'; import { CasesClient, createCasesClient } from '.'; import { PersistableStateAttachmentTypeRegistry } from '../attachment_framework/persistable_state_registry'; +import { ExternalReferenceAttachmentTypeRegistry } from '../attachment_framework/external_reference_registry'; interface CasesClientFactoryArgs { securityPluginSetup?: SecurityPluginSetup; @@ -39,6 +40,7 @@ interface CasesClientFactoryArgs { actionsPluginStart: ActionsPluginStart; lensEmbeddableFactory: LensServerPluginSetup['lensEmbeddableFactory']; persistableStateAttachmentTypeRegistry: PersistableStateAttachmentTypeRegistry; + externalReferenceAttachmentTypeRegistry: ExternalReferenceAttachmentTypeRegistry; } /** @@ -130,6 +132,8 @@ export class CasesClientFactory { lensEmbeddableFactory: this.options.lensEmbeddableFactory, authorization: auth, actionsClient: await this.options.actionsPluginStart.getActionsClientWithRequest(request), + persistableStateAttachmentTypeRegistry: this.options.persistableStateAttachmentTypeRegistry, + externalReferenceAttachmentTypeRegistry: this.options.externalReferenceAttachmentTypeRegistry, }); } } diff --git a/x-pack/plugins/cases/server/client/types.ts b/x-pack/plugins/cases/server/client/types.ts index d071e72099bf9..d1cb9e011f85f 100644 --- a/x-pack/plugins/cases/server/client/types.ts +++ b/x-pack/plugins/cases/server/client/types.ts @@ -19,6 +19,8 @@ import { AttachmentService, AlertService, } from '../services'; +import { PersistableStateAttachmentTypeRegistry } from '../attachment_framework/persistable_state_registry'; +import { ExternalReferenceAttachmentTypeRegistry } from '../attachment_framework/external_reference_registry'; /** * Parameters for initializing a cases client @@ -36,4 +38,6 @@ export interface CasesClientArgs { readonly lensEmbeddableFactory: LensServerPluginSetup['lensEmbeddableFactory']; readonly authorization: PublicMethodsOf; readonly actionsClient: PublicMethodsOf; + readonly persistableStateAttachmentTypeRegistry: PersistableStateAttachmentTypeRegistry; + readonly externalReferenceAttachmentTypeRegistry: ExternalReferenceAttachmentTypeRegistry; } diff --git a/x-pack/plugins/cases/server/plugin.ts b/x-pack/plugins/cases/server/plugin.ts index 89b390c72f338..f01e6c75d10bd 100644 --- a/x-pack/plugins/cases/server/plugin.ts +++ b/x-pack/plugins/cases/server/plugin.ts @@ -50,6 +50,7 @@ import { getExternalRoutes } from './routes/api/get_external_routes'; import { createCasesTelemetry, scheduleCasesTelemetryTask } from './telemetry'; import { getInternalRoutes } from './routes/api/get_internal_routes'; import { PersistableStateAttachmentTypeRegistry } from './attachment_framework/persistable_state_registry'; +import { ExternalReferenceAttachmentTypeRegistry } from './attachment_framework/external_reference_registry'; export interface PluginsSetup { actions: ActionsPluginSetup; @@ -75,12 +76,14 @@ export class CasePlugin { private securityPluginSetup?: SecurityPluginSetup; private lensEmbeddableFactory?: LensServerPluginSetup['lensEmbeddableFactory']; private persistableStateAttachmentTypeRegistry: PersistableStateAttachmentTypeRegistry; + private externalReferenceAttachmentTypeRegistry: ExternalReferenceAttachmentTypeRegistry; constructor(private readonly initializerContext: PluginInitializerContext) { this.kibanaVersion = initializerContext.env.packageInfo.version; this.logger = this.initializerContext.logger.get(); this.clientFactory = new CasesClientFactory(this.logger); this.persistableStateAttachmentTypeRegistry = new PersistableStateAttachmentTypeRegistry(); + this.externalReferenceAttachmentTypeRegistry = new ExternalReferenceAttachmentTypeRegistry(); } public setup(core: CoreSetup, plugins: PluginsSetup): PluginSetupContract { @@ -143,6 +146,9 @@ export class CasePlugin { return { attachmentFramework: { + registerExternalReference: (externalReferenceAttachmentType) => { + this.externalReferenceAttachmentTypeRegistry.register(externalReferenceAttachmentType); + }, registerPersistableState: (persistableStateAttachmentType) => { this.persistableStateAttachmentTypeRegistry.register(persistableStateAttachmentType); }, @@ -172,6 +178,7 @@ export class CasePlugin { // eslint-disable-next-line @typescript-eslint/no-non-null-assertion lensEmbeddableFactory: this.lensEmbeddableFactory!, persistableStateAttachmentTypeRegistry: this.persistableStateAttachmentTypeRegistry, + externalReferenceAttachmentTypeRegistry: this.externalReferenceAttachmentTypeRegistry, }); const client = core.elasticsearch.client; diff --git a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/kibana.json b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/kibana.json similarity index 88% rename from x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/kibana.json rename to x-pack/test/cases_api_integration/common/fixtures/plugins/cases/kibana.json index 950e3b23f6a34..70b86286bb6b9 100644 --- a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/kibana.json +++ b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/kibana.json @@ -1,5 +1,5 @@ { - "id": "casesClientUserFixture", + "id": "casesFixture", "owner": { "githubTeam": "response-ops", "name": "ResponseOps" diff --git a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/package.json b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/package.json similarity index 70% rename from x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/package.json rename to x-pack/test/cases_api_integration/common/fixtures/plugins/cases/package.json index d396141fb0059..a9e25c9dc2cbe 100644 --- a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/package.json +++ b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/package.json @@ -1,11 +1,11 @@ { - "name": "cases-client-user-fixture", + "name": "cases-fixture", "version": "1.0.0", "kibana": { "version": "kibana", "templateVersion": "1.0.0" }, - "main": "target/test/plugin_api_integration/plugins/cases_client_user_fixture", + "main": "target/test/plugin_api_integration/plugins/cases_fixture", "scripts": { "kbn": "node ../../../../../../../scripts/kbn.js", "build": "rm -rf './target' && ../../../../../../../node_modules/.bin/tsc" diff --git a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/attachments/external_reference.ts b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/attachments/external_reference.ts new file mode 100644 index 0000000000000..a54f586b4c3e3 --- /dev/null +++ b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/attachments/external_reference.ts @@ -0,0 +1,12 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { ExternalReferenceAttachmentType } from '@kbn/cases-plugin/server/attachment_framework/types'; + +export const getExternalReferenceAttachment = (): ExternalReferenceAttachmentType => ({ + id: '.test', +}); diff --git a/x-pack/test/cases_api_integration/common/fixtures/plugins/security_solution/attachments/persistable_state.ts b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/attachments/persistable_state.ts similarity index 92% rename from x-pack/test/cases_api_integration/common/fixtures/plugins/security_solution/attachments/persistable_state.ts rename to x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/attachments/persistable_state.ts index 065137302acb7..4bb043c41ddb5 100644 --- a/x-pack/test/cases_api_integration/common/fixtures/plugins/security_solution/attachments/persistable_state.ts +++ b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/attachments/persistable_state.ts @@ -10,7 +10,7 @@ import { PersistableStateAttachmentTypeSetup, } from '@kbn/cases-plugin/server/attachment_framework/types'; -export const getPersistableAttachment = (): PersistableStateAttachmentTypeSetup => ({ +export const getPersistableStateAttachment = (): PersistableStateAttachmentTypeSetup => ({ id: '.test', inject: (state, references) => ({ ...state, diff --git a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/server/index.ts b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/index.ts similarity index 100% rename from x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/server/index.ts rename to x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/index.ts diff --git a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/server/plugin.ts b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/plugin.ts similarity index 83% rename from x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/server/plugin.ts rename to x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/plugin.ts index ea42b988d2f26..8fc826581dda6 100644 --- a/x-pack/test/cases_api_integration/common/fixtures/plugins/cases_client_user/server/plugin.ts +++ b/x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/plugin.ts @@ -13,9 +13,13 @@ import { SpacesPluginStart } from '@kbn/spaces-plugin/server'; import { SecurityPluginStart } from '@kbn/security-plugin/server'; import { PluginStartContract as CasesPluginStart } from '@kbn/cases-plugin/server'; import { CasesPatchRequest } from '@kbn/cases-plugin/common/api'; +import { PluginSetupContract as CasesSetup } from '@kbn/cases-plugin/server/types'; +import { getPersistableStateAttachment } from './attachments/persistable_state'; +import { getExternalReferenceAttachment } from './attachments/external_reference'; export interface FixtureSetupDeps { features: FeaturesPluginSetup; + cases: CasesSetup; } export interface FixtureStartDeps { @@ -32,6 +36,9 @@ export class FixturePlugin implements Plugin, deps: FixtureSetupDeps) { + deps.cases.attachmentFramework.registerExternalReference(getExternalReferenceAttachment()); + deps.cases.attachmentFramework.registerPersistableState(getPersistableStateAttachment()); + const router = core.http.createRouter(); /** * This simply wraps the cases patch case api so that we can test updating the status of an alert using diff --git a/x-pack/test/cases_api_integration/common/fixtures/plugins/security_solution/server/plugin.ts b/x-pack/test/cases_api_integration/common/fixtures/plugins/security_solution/server/plugin.ts index 347c69982e423..7fd45bb883f2f 100644 --- a/x-pack/test/cases_api_integration/common/fixtures/plugins/security_solution/server/plugin.ts +++ b/x-pack/test/cases_api_integration/common/fixtures/plugins/security_solution/server/plugin.ts @@ -10,12 +10,9 @@ import { Plugin, CoreSetup } from '@kbn/core/server'; import { PluginSetupContract as FeaturesPluginSetup } from '@kbn/features-plugin/server'; import { SpacesPluginStart } from '@kbn/spaces-plugin/server'; import { SecurityPluginStart } from '@kbn/security-plugin/server'; -import { PluginSetupContract as CasesPluginSetup } from '@kbn/cases-plugin/server'; -import { getPersistableAttachment } from '../attachments/persistable_state'; export interface FixtureSetupDeps { features: FeaturesPluginSetup; - cases: CasesPluginSetup; } export interface FixtureStartDeps { @@ -25,9 +22,7 @@ export interface FixtureStartDeps { export class FixturePlugin implements Plugin { public setup(core: CoreSetup, deps: FixtureSetupDeps) { - const { features, cases } = deps; - - cases.attachmentFramework.registerPersistableState(getPersistableAttachment()); + const { features } = deps; features.registerKibanaFeature({ id: 'securitySolutionFixture', diff --git a/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/external_references.ts b/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/external_references.ts index e831cd3c8f496..9490504e09d00 100644 --- a/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/external_references.ts +++ b/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/external_references.ts @@ -38,6 +38,10 @@ export default ({ getService }: FtrProviderContext): void => { const supertest = getService('supertest'); const es = getService('es'); + /** + * Attachment types are being registered in + * x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/plugin.ts + */ describe('External references', () => { afterEach(async () => { await deleteAllCaseItems(es); @@ -455,5 +459,15 @@ export default ({ getService }: FtrProviderContext): void => { expectedHttpCode: 400, }); }); + + it('400s when creating a non registered external reference attachment type', async () => { + const postedCase = await createCase(supertest, postCaseReq); + await createComment({ + supertest, + caseId: postedCase.id, + params: { ...postExternalReferenceSOReq, externalReferenceAttachmentTypeId: 'not-exists' }, + expectedHttpCode: 400, + }); + }); }); }; diff --git a/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/persistable_state.ts b/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/persistable_state.ts index c91aaa6953c7f..ce2cffac13cb3 100644 --- a/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/persistable_state.ts +++ b/x-pack/test/cases_api_integration/security_and_spaces/tests/common/attachments_framework/persistable_state.ts @@ -39,6 +39,10 @@ export default ({ getService }: FtrProviderContext): void => { const es = getService('es'); const kibanaServer = getService('kibanaServer'); + /** + * Attachment types are being registered in + * x-pack/test/cases_api_integration/common/fixtures/plugins/cases/server/plugin.ts + */ describe('Persistable state attachments', () => { describe('references', () => { afterEach(async () => { @@ -247,6 +251,16 @@ export default ({ getService }: FtrProviderContext): void => { expectedHttpCode: 400, }); }); + + it('400s when creating a non registered persistable state attachment type', async () => { + const postedCase = await createCase(supertest, postCaseReq); + await createComment({ + supertest, + caseId: postedCase.id, + params: { ...persistableStateAttachment, persistableStateAttachmentTypeId: 'not-exists' }, + expectedHttpCode: 400, + }); + }); }); describe('Migrations', () => { diff --git a/x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/attachments/external_reference.ts b/x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/attachments/external_reference.ts new file mode 100644 index 0000000000000..a54f586b4c3e3 --- /dev/null +++ b/x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/attachments/external_reference.ts @@ -0,0 +1,12 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { ExternalReferenceAttachmentType } from '@kbn/cases-plugin/server/attachment_framework/types'; + +export const getExternalReferenceAttachment = (): ExternalReferenceAttachmentType => ({ + id: '.test', +}); diff --git a/x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/plugin.ts b/x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/plugin.ts index fd86aa7300eb1..df760a036b01e 100644 --- a/x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/plugin.ts +++ b/x-pack/test/functional_with_es_ssl/fixtures/plugins/cases/server/plugin.ts @@ -7,6 +7,7 @@ import { PluginSetupContract as CasesSetup } from '@kbn/cases-plugin/server/types'; import { Plugin, CoreSetup } from '@kbn/core/server'; +import { getExternalReferenceAttachment } from './attachments/external_reference'; import { getPersistableStateAttachmentServer } from './attachments/persistable_state'; export interface CasesExamplePublicSetupDeps { @@ -15,6 +16,7 @@ export interface CasesExamplePublicSetupDeps { export class CasesFixturePlugin implements Plugin { public setup(core: CoreSetup, { cases }: CasesExamplePublicSetupDeps) { + cases.attachmentFramework.registerExternalReference(getExternalReferenceAttachment()); cases.attachmentFramework.registerPersistableState(getPersistableStateAttachmentServer()); } From 42d8e65ceeb71c1d08f998eb64a15c1e82b21fbc Mon Sep 17 00:00:00 2001 From: Nicolas Chaulet Date: Mon, 18 Jul 2022 09:28:55 -0400 Subject: [PATCH 088/111] [Fleet] integration tests docker registry more robust (#136438) --- .../helpers/docker_registry_helper.ts | 92 ++++++++++++++----- 1 file changed, 67 insertions(+), 25 deletions(-) diff --git a/x-pack/plugins/fleet/server/integration_tests/helpers/docker_registry_helper.ts b/x-pack/plugins/fleet/server/integration_tests/helpers/docker_registry_helper.ts index f400becfa0085..77bf8e0fbf3e4 100644 --- a/x-pack/plugins/fleet/server/integration_tests/helpers/docker_registry_helper.ts +++ b/x-pack/plugins/fleet/server/integration_tests/helpers/docker_registry_helper.ts @@ -5,17 +5,52 @@ * 2.0. */ -import { spawn } from 'child_process'; import type { ChildProcess } from 'child_process'; +import * as Rx from 'rxjs'; +import { filter, take, map, tap } from 'rxjs/operators'; +import execa from 'execa'; + +import { observeLines } from '@kbn/stdio-dev-helpers'; +import { ToolingLog } from '@kbn/tooling-log'; import pRetry from 'p-retry'; -import fetch from 'node-fetch'; -const delay = (ms: number) => new Promise((resolve) => setTimeout(resolve, ms)); +const BEFORE_SETUP_TIMEOUT = 30 * 60 * 1000; // 30 minutes; const DOCKER_START_TIMEOUT = 5 * 60 * 1000; // 5 minutes +const DOCKER_IMAGE = `docker.elastic.co/package-registry/distribution:93ffe45d8c4ae11365bc70b1038643121049b9fe`; + +function firstWithTimeout(source$: Rx.Observable, errorMsg: string, ms = 30 * 1000) { + return Rx.race( + source$.pipe(take(1)), + Rx.timer(ms).pipe( + map(() => { + throw new Error(`[docker:${DOCKER_IMAGE}] ${errorMsg} within ${ms / 1000} seconds`); + }) + ) + ); +} + +function childProcessToLogLine(childProcess: ChildProcess, log: ToolingLog) { + const logLine$ = new Rx.Subject(); + + Rx.merge( + observeLines(childProcess.stdout!).pipe( + tap((line) => log.info(`[docker:${DOCKER_IMAGE}] ${line}`)) + ), // TypeScript note: As long as the proc stdio[1] is 'pipe', then stdout will not be null + observeLines(childProcess.stderr!).pipe( + tap((line) => log.error(`[docker:${DOCKER_IMAGE}] ${line}`)) + ) // TypeScript note: As long as the proc stdio[2] is 'pipe', then stderr will not be null + ).subscribe(logLine$); + + return logLine$.asObservable(); +} export function useDockerRegistry() { + const logger = new ToolingLog({ + level: 'info', + writeTo: process.stdout, + }); const packageRegistryPort = process.env.FLEET_PACKAGE_REGISTRY_PORT || '8081'; if (!packageRegistryPort.match(/^[0-9]{4}/)) { @@ -24,38 +59,42 @@ export function useDockerRegistry() { let dockerProcess: ChildProcess | undefined; async function startDockerRegistryServer() { - const dockerImage = `docker.elastic.co/package-registry/distribution:93ffe45d8c4ae11365bc70b1038643121049b9fe`; + const args = ['run', '--rm', '-p', `${packageRegistryPort}:8080`, DOCKER_IMAGE]; - const args = ['run', '--rm', '-p', `${packageRegistryPort}:8080`, dockerImage]; - - dockerProcess = spawn('docker', args, { stdio: 'inherit' }); + dockerProcess = execa('docker', args, { + stdio: ['ignore', 'pipe', 'pipe'], + }); let isExited = dockerProcess.exitCode !== null; dockerProcess.once('exit', () => { isExited = true; }); - - const startedAt = Date.now(); - - while (!isExited && Date.now() - startedAt <= DOCKER_START_TIMEOUT) { - try { - const res = await fetch(`http://localhost:${packageRegistryPort}/`); - if (res.status === 200) { - return; - } - } catch (err) { - // swallow errors - } - - await delay(3000); + const waitForLogLine = /package manifests loaded/; + + try { + await firstWithTimeout( + childProcessToLogLine(dockerProcess, logger).pipe( + filter((line) => { + process.stdout.write(line); + return waitForLogLine.test(line); + }) + ), + 'no package manifests loaded', + DOCKER_START_TIMEOUT + ).toPromise(); + } catch (err) { + dockerProcess.kill(); + throw err; } if (isExited && dockerProcess.exitCode !== 0) { throw new Error(`Unable to setup docker registry exit code ${dockerProcess.exitCode}`); } + } - dockerProcess.kill(); - throw new pRetry.AbortError('Unable to setup docker registry after timeout'); + async function pullDockerImage() { + logger.info(`[docker:${DOCKER_IMAGE}] pulling docker image "${DOCKER_IMAGE}"`); + await execa('docker', ['pull', DOCKER_IMAGE]); } async function cleanupDockerRegistryServer() { @@ -65,8 +104,11 @@ export function useDockerRegistry() { } beforeAll(async () => { - const testTimeout = 5 * 60 * 1000; // 5 minutes timeout - jest.setTimeout(testTimeout); + jest.setTimeout(BEFORE_SETUP_TIMEOUT); + await pRetry(() => pullDockerImage(), { + retries: 3, + }); + await pRetry(() => startDockerRegistryServer(), { retries: 3, }); From 26d6b8208837a072f313e83a6e254fa35a4d8b29 Mon Sep 17 00:00:00 2001 From: Miriam <31922082+MiriamAparicio@users.noreply.github.com> Date: Mon, 18 Jul 2022 14:29:47 +0100 Subject: [PATCH 089/111] Increase name width on some tables (#136513) --- .../service_overview_instances_table/get_columns.tsx | 1 + .../apm/public/components/shared/dependencies_table/index.tsx | 1 + .../public/components/shared/transactions_table/get_columns.tsx | 1 + 3 files changed, 3 insertions(+) diff --git a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_instances_table/get_columns.tsx b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_instances_table/get_columns.tsx index 1180cf7586db0..21261f5d32e64 100644 --- a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_instances_table/get_columns.tsx +++ b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_instances_table/get_columns.tsx @@ -80,6 +80,7 @@ export function getColumns({ 'xpack.apm.serviceOverview.instancesTableColumnNodeName', { defaultMessage: 'Node name' } ), + width: '30%', render: (_, item) => { const { serviceNodeName } = item; const isMissingServiceNodeName = diff --git a/x-pack/plugins/apm/public/components/shared/dependencies_table/index.tsx b/x-pack/plugins/apm/public/components/shared/dependencies_table/index.tsx index 99f50def4d417..718a978f1599e 100644 --- a/x-pack/plugins/apm/public/components/shared/dependencies_table/index.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependencies_table/index.tsx @@ -90,6 +90,7 @@ export function DependenciesTable(props: Props) { return ; }, sortable: true, + width: '30%', }, ...getSpanMetricColumns({ breakpoints, diff --git a/x-pack/plugins/apm/public/components/shared/transactions_table/get_columns.tsx b/x-pack/plugins/apm/public/components/shared/transactions_table/get_columns.tsx index 84670b8448f17..dd68dc94a2c1a 100644 --- a/x-pack/plugins/apm/public/components/shared/transactions_table/get_columns.tsx +++ b/x-pack/plugins/apm/public/components/shared/transactions_table/get_columns.tsx @@ -68,6 +68,7 @@ export function getColumns({ 'xpack.apm.serviceOverview.transactionsTableColumnName', { defaultMessage: 'Name' } ), + width: '30%', render: (_, { name, transactionType: type }) => { return ( Date: Mon, 18 Jul 2022 23:09:56 +0930 Subject: [PATCH 090/111] Update dependency @elastic/charts to v46.13.0 (#136250) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Marta Bondyra <4283304+mbondyra@users.noreply.github.com> --- package.json | 2 +- yarn.lock | 10 +++++----- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/package.json b/package.json index 4f98a16e13959..5d9e8f86bacfd 100644 --- a/package.json +++ b/package.json @@ -104,7 +104,7 @@ "@elastic/apm-rum": "^5.12.0", "@elastic/apm-rum-react": "^1.4.2", "@elastic/apm-synthtrace": "link:bazel-bin/packages/elastic-apm-synthtrace", - "@elastic/charts": "46.12.0", + "@elastic/charts": "46.13.0", "@elastic/datemath": "5.0.3", "@elastic/elasticsearch": "npm:@elastic/elasticsearch-canary@8.3.0-canary.1", "@elastic/ems-client": "8.3.3", diff --git a/yarn.lock b/yarn.lock index 83f4084c5dbc6..65ac755b1eed0 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1429,10 +1429,10 @@ dependencies: object-hash "^1.3.0" -"@elastic/charts@46.12.0": - version "46.12.0" - resolved "https://registry.yarnpkg.com/@elastic/charts/-/charts-46.12.0.tgz#95c5ba2d4eff75b52fb294b867fb7b147da3383a" - integrity sha512-YIILkL3CXSoBMBiwj1N6FJTWMB9PpKi1bfMZVJCGHb23+J3LiiAqsQYsZbm7L28ziH3s0RveRomRcfVo38NvMg== +"@elastic/charts@46.13.0": + version "46.13.0" + resolved "https://registry.yarnpkg.com/@elastic/charts/-/charts-46.13.0.tgz#6000de23944f264c8ac2bb0a8728fac1eb8c3b2f" + integrity sha512-v3qGpARn8stI5v6aSUaQE3tEYdZLmGgA//oU4BSLemmKUaBpaK5ZOYwjoBGdqzo52F7gqM7/O1QepdfxS/CBRw== dependencies: "@popperjs/core" "^2.4.0" bezier-easing "^2.1.0" @@ -13640,7 +13640,7 @@ domhandler@^3.0.0: dependencies: domelementtype "^2.0.1" -domhandler@^4.0.0, domhandler@^4.0, domhandler@^4.2.0, domhandler@^4.2.2: +domhandler@^4.0, domhandler@^4.0.0, domhandler@^4.2.0, domhandler@^4.2.2: version "4.3.0" resolved "https://registry.yarnpkg.com/domhandler/-/domhandler-4.3.0.tgz#16c658c626cf966967e306f966b431f77d4a5626" integrity sha512-fC0aXNQXqKSFTr2wDNZDhsEYjCiYsDWl3D01kwt25hm1YIPyDGHvvi3rw+PLqHAl/m71MaiF7d5zvBr0p5UB2g== From b403ec137dd3d6dd2c70546a7690cd83c37f4768 Mon Sep 17 00:00:00 2001 From: Julia Bardi <90178898+juliaElastic@users.noreply.github.com> Date: Mon, 18 Jul 2022 16:13:29 +0200 Subject: [PATCH 091/111] [Fleet] prevent adding tags to hosted agents (#136516) * prevent adding tags to hosted agents * fixed tests * added unit test * functional test for hosted check --- .../fleet/server/routes/agent/handlers.ts | 2 + .../agents/filter_hosted_agents.test.ts | 45 +++++++++++++++++++ .../services/agents/filter_hosted_agents.ts | 32 +++++++++++++ .../services/agents/update_agent_tags.test.ts | 34 +++++++++----- .../services/agents/update_agent_tags.ts | 18 ++++++-- .../apis/agents/update_agent_tags.ts | 39 ++++++++++++++++ 6 files changed, 157 insertions(+), 13 deletions(-) create mode 100644 x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.test.ts create mode 100644 x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.ts diff --git a/x-pack/plugins/fleet/server/routes/agent/handlers.ts b/x-pack/plugins/fleet/server/routes/agent/handlers.ts index 7a10a50e2fb7b..42c1ec24f4ee2 100644 --- a/x-pack/plugins/fleet/server/routes/agent/handlers.ts +++ b/x-pack/plugins/fleet/server/routes/agent/handlers.ts @@ -122,12 +122,14 @@ export const bulkUpdateAgentTagsHandler: RequestHandler< > = async (context, request, response) => { const coreContext = await context.core; const esClient = coreContext.elasticsearch.client.asInternalUser; + const soClient = coreContext.savedObjects.client; const agentOptions = Array.isArray(request.body.agents) ? { agentIds: request.body.agents } : { kuery: request.body.agents }; try { const results = await AgentService.updateAgentTags( + soClient, esClient, { ...agentOptions, batchSize: request.body.batchSize }, request.body.tagsToAdd ?? [], diff --git a/x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.test.ts b/x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.test.ts new file mode 100644 index 0000000000000..a6ae638c08c70 --- /dev/null +++ b/x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.test.ts @@ -0,0 +1,45 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { SavedObjectsClientContract } from '@kbn/core/server'; +import { savedObjectsClientMock } from '@kbn/core/server/mocks'; + +import { HostedAgentPolicyRestrictionRelatedError } from '../../errors'; +import type { Agent } from '../../types'; + +import { filterHostedPolicies } from './filter_hosted_agents'; + +jest.mock('./hosted_agent', () => ({ + ...jest.requireActual('./hosted_agent'), + getHostedPolicies: jest.fn().mockResolvedValue({ hosted: true }), +})); + +describe('filterHostedPolicies', () => { + let soClient: jest.Mocked; + + beforeEach(() => { + soClient = savedObjectsClientMock.create(); + }); + + it('should filter out agents with hosted policies', async () => { + const outgoingErrors = {}; + const agents = await filterHostedPolicies( + soClient, + [ + { id: 'agent1', policy_id: 'hosted' }, + { id: 'agent2', policy_id: 'other' }, + ] as Agent[], + outgoingErrors, + 'error' + ); + + expect(agents).toEqual([{ id: 'agent2', policy_id: 'other' }]); + expect(outgoingErrors).toEqual({ + agent1: new HostedAgentPolicyRestrictionRelatedError('error'), + }); + }); +}); diff --git a/x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.ts b/x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.ts new file mode 100644 index 0000000000000..4f1f37feffb92 --- /dev/null +++ b/x-pack/plugins/fleet/server/services/agents/filter_hosted_agents.ts @@ -0,0 +1,32 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { SavedObjectsClientContract } from '@kbn/core/server'; + +import type { Agent } from '../../types'; +import { HostedAgentPolicyRestrictionRelatedError } from '../../errors'; + +import { getHostedPolicies, isHostedAgent } from './hosted_agent'; + +export async function filterHostedPolicies( + soClient: SavedObjectsClientContract, + givenAgents: Agent[], + outgoingErrors: Record, + errorMessage: string +): Promise { + const hostedPolicies = await getHostedPolicies(soClient, givenAgents); + + return givenAgents.reduce((agents, agent, index) => { + if (isHostedAgent(hostedPolicies, agent)) { + const id = givenAgents[index].id; + outgoingErrors[id] = new HostedAgentPolicyRestrictionRelatedError(errorMessage); + } else { + agents.push(agent); + } + return agents; + }, []); +} diff --git a/x-pack/plugins/fleet/server/services/agents/update_agent_tags.test.ts b/x-pack/plugins/fleet/server/services/agents/update_agent_tags.test.ts index 53bf035903c36..748f85db2843b 100644 --- a/x-pack/plugins/fleet/server/services/agents/update_agent_tags.test.ts +++ b/x-pack/plugins/fleet/server/services/agents/update_agent_tags.test.ts @@ -4,17 +4,25 @@ * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ - +import type { SavedObjectsClientContract } from '@kbn/core/server'; import type { ElasticsearchClientMock } from '@kbn/core/server/mocks'; -import { elasticsearchServiceMock } from '@kbn/core/server/mocks'; +import { elasticsearchServiceMock, savedObjectsClientMock } from '@kbn/core/server/mocks'; import { updateAgentTags } from './update_agent_tags'; +jest.mock('./filter_hosted_agents', () => ({ + filterHostedPolicies: jest + .fn() + .mockImplementation((soClient, givenAgents) => Promise.resolve(givenAgents)), +})); + describe('update_agent_tags', () => { let esClient: ElasticsearchClientMock; + let soClient: jest.Mocked; beforeEach(() => { esClient = elasticsearchServiceMock.createInternalClient(); + soClient = savedObjectsClientMock.create(); esClient.mget.mockResolvedValue({ docs: [ { @@ -46,19 +54,19 @@ describe('update_agent_tags', () => { } it('should replace tag in middle place when one add and one remove tag', async () => { - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['newName'], ['two']); + await updateAgentTags(soClient, esClient, { agentIds: ['agent1'] }, ['newName'], ['two']); expectTagsInEsBulk(['one', 'newName', 'three']); }); it('should replace tag in first place when one add and one remove tag', async () => { - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['newName'], ['one']); + await updateAgentTags(soClient, esClient, { agentIds: ['agent1'] }, ['newName'], ['one']); expectTagsInEsBulk(['newName', 'two', 'three']); }); it('should replace tag in last place when one add and one remove tag', async () => { - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['newName'], ['three']); + await updateAgentTags(soClient, esClient, { agentIds: ['agent1'] }, ['newName'], ['three']); expectTagsInEsBulk(['one', 'two', 'newName']); }); @@ -72,31 +80,37 @@ describe('update_agent_tags', () => { } as any, ], }); - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['newName'], ['three']); + await updateAgentTags(soClient, esClient, { agentIds: ['agent1'] }, ['newName'], ['three']); expectTagsInEsBulk(['newName']); }); it('should remove duplicate tags', async () => { - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['one'], ['two']); + await updateAgentTags(soClient, esClient, { agentIds: ['agent1'] }, ['one'], ['two']); expectTagsInEsBulk(['one', 'three']); }); it('should add tag at the end when no tagsToRemove', async () => { - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['newName'], []); + await updateAgentTags(soClient, esClient, { agentIds: ['agent1'] }, ['newName'], []); expectTagsInEsBulk(['one', 'two', 'three', 'newName']); }); it('should add tag at the end when tagsToRemove not in existing tags', async () => { - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['newName'], ['dummy']); + await updateAgentTags(soClient, esClient, { agentIds: ['agent1'] }, ['newName'], ['dummy']); expectTagsInEsBulk(['one', 'two', 'three', 'newName']); }); it('should add tag at the end when multiple tagsToRemove', async () => { - await updateAgentTags(esClient, { agentIds: ['agent1'] }, ['newName'], ['one', 'two']); + await updateAgentTags( + soClient, + esClient, + { agentIds: ['agent1'] }, + ['newName'], + ['one', 'two'] + ); expectTagsInEsBulk(['three', 'newName']); }); diff --git a/x-pack/plugins/fleet/server/services/agents/update_agent_tags.ts b/x-pack/plugins/fleet/server/services/agents/update_agent_tags.ts index fed7e5c4e0152..c4893c7769651 100644 --- a/x-pack/plugins/fleet/server/services/agents/update_agent_tags.ts +++ b/x-pack/plugins/fleet/server/services/agents/update_agent_tags.ts @@ -7,7 +7,7 @@ import { difference, uniq } from 'lodash'; import type * as estypes from '@elastic/elasticsearch/lib/api/typesWithBodyKey'; -import type { ElasticsearchClient } from '@kbn/core/server'; +import type { ElasticsearchClient, SavedObjectsClientContract } from '@kbn/core/server'; import type { Agent, BulkActionResult } from '../../types'; import { AgentReassignmentError } from '../../errors'; @@ -20,12 +20,14 @@ import { } from './crud'; import type { GetAgentsOptions } from '.'; import { searchHitToAgent } from './helpers'; +import { filterHostedPolicies } from './filter_hosted_agents'; function isMgetDoc(doc?: estypes.MgetResponseItem): doc is estypes.GetGetResult { return Boolean(doc && 'found' in doc); } export async function updateAgentTags( + soClient: SavedObjectsClientContract, esClient: ElasticsearchClient, options: ({ agents: Agent[] } | GetAgentsOptions) & { batchSize?: number }, tagsToAdd: string[], @@ -55,6 +57,7 @@ export async function updateAgentTags( }, async (agents: Agent[], skipSuccess: boolean) => await updateTagsBatch( + soClient, esClient, agents, outgoingErrors, @@ -67,6 +70,7 @@ export async function updateAgentTags( } return await updateTagsBatch( + soClient, esClient, givenAgents, outgoingErrors, @@ -77,6 +81,7 @@ export async function updateAgentTags( } async function updateTagsBatch( + soClient: SavedObjectsClientContract, esClient: ElasticsearchClient, givenAgents: Agent[], outgoingErrors: Record, @@ -87,6 +92,13 @@ async function updateTagsBatch( ): Promise<{ items: BulkActionResult[] }> { const errors: Record = { ...outgoingErrors }; + const filteredAgents = await filterHostedPolicies( + soClient, + givenAgents, + errors, + `Cannot modify tags on a hosted agent` + ); + const getNewTags = (agent: Agent): string[] => { const existingTags = agent.tags ?? []; @@ -106,7 +118,7 @@ async function updateTagsBatch( await bulkUpdateAgents( esClient, - givenAgents.map((agent) => ({ + filteredAgents.map((agent) => ({ agentId: agent.id, data: { tags: getNewTags(agent), @@ -114,5 +126,5 @@ async function updateTagsBatch( })) ); - return { items: errorsToResults(givenAgents, errors, agentIds, skipSuccess) }; + return { items: errorsToResults(filteredAgents, errors, agentIds, skipSuccess) }; } diff --git a/x-pack/test/fleet_api_integration/apis/agents/update_agent_tags.ts b/x-pack/test/fleet_api_integration/apis/agents/update_agent_tags.ts index 16ea3eb2b0b62..2de75be2e50b0 100644 --- a/x-pack/test/fleet_api_integration/apis/agents/update_agent_tags.ts +++ b/x-pack/test/fleet_api_integration/apis/agents/update_agent_tags.ts @@ -126,6 +126,45 @@ export default function (providerContext: FtrProviderContext) { }) .expect(403); }); + + it('should not update tags of hosted agent', async () => { + // move agent2 to policy2 to keep it regular + await supertest.put(`/api/fleet/agents/agent2/reassign`).set('kbn-xsrf', 'xxx').send({ + policy_id: 'policy2', + }); + // update enrolled policy to hosted + await supertest.put(`/api/fleet/agent_policies/policy1`).set('kbn-xsrf', 'xxxx').send({ + name: 'Test policy', + namespace: 'default', + is_managed: true, + }); + + // attempt to update tags of agent in hosted agent policy + const { body } = await supertest + .post(`/api/fleet/agents/bulk_update_agent_tags`) + .set('kbn-xsrf', 'xxx') + .send({ + tagsToAdd: ['newTag'], + agents: ['agent1', 'agent2'], + }) + .expect(200); + + expect(body).to.eql({ + agent1: { + success: false, + error: `Cannot modify tags on a hosted agent in Fleet because the agent policy is managed by an external orchestration solution, such as Elastic Cloud, Kubernetes, etc. Please make changes using your orchestration solution.`, + }, + agent2: { success: true }, + }); + + const [agent1data, agent2data] = await Promise.all([ + supertest.get(`/api/fleet/agents/agent1`), + supertest.get(`/api/fleet/agents/agent2`), + ]); + + expect(agent1data.body.item.tags.includes('newTag')).to.be(false); + expect(agent2data.body.item.tags.includes('newTag')).to.be(true); + }); }); }); } From 1aa3a12e7f82fba982c96106677080f87ad61785 Mon Sep 17 00:00:00 2001 From: Bhavya RM Date: Mon, 18 Jul 2022 10:24:51 -0400 Subject: [PATCH 092/111] Migrating test/api_integration/fixtures/es_archiver/management/saved_objects/search to kbnArchiver (#135996) --- .../apis/saved_objects_management/find.ts | 21 +- .../management/saved_objects/search/data.json | 198 -------- .../saved_objects/search/mappings.json | 476 ------------------ .../kbn_archiver/saved_objects/search.json | 143 ++++++ 4 files changed, 155 insertions(+), 683 deletions(-) delete mode 100644 test/api_integration/fixtures/es_archiver/management/saved_objects/search/data.json delete mode 100644 test/api_integration/fixtures/es_archiver/management/saved_objects/search/mappings.json create mode 100644 test/api_integration/fixtures/kbn_archiver/saved_objects/search.json diff --git a/test/api_integration/apis/saved_objects_management/find.ts b/test/api_integration/apis/saved_objects_management/find.ts index e945d0f1f001a..ca891986f609a 100644 --- a/test/api_integration/apis/saved_objects_management/find.ts +++ b/test/api_integration/apis/saved_objects_management/find.ts @@ -12,7 +12,6 @@ import { FtrProviderContext } from '../../ftr_provider_context'; export default function ({ getService }: FtrProviderContext) { const supertest = getService('supertest'); - const esArchiver = getService('esArchiver'); const kibanaServer = getService('kibanaServer'); describe('find', () => { @@ -194,14 +193,18 @@ export default function ({ getService }: FtrProviderContext) { }); describe('meta attributes injected properly', () => { - before(() => - esArchiver.load('test/api_integration/fixtures/es_archiver/management/saved_objects/search') - ); - after(() => - esArchiver.unload( - 'test/api_integration/fixtures/es_archiver/management/saved_objects/search' - ) - ); + before(async () => { + await kibanaServer.savedObjects.cleanStandardList(); + await kibanaServer.importExport.load( + 'test/api_integration/fixtures/kbn_archiver/saved_objects/search.json' + ); + }); + after(async () => { + await kibanaServer.importExport.unload( + 'test/api_integration/fixtures/kbn_archiver/saved_objects/search.json' + ); + await kibanaServer.savedObjects.cleanStandardList(); + }); it('should inject meta attributes for searches', async () => await supertest diff --git a/test/api_integration/fixtures/es_archiver/management/saved_objects/search/data.json b/test/api_integration/fixtures/es_archiver/management/saved_objects/search/data.json deleted file mode 100644 index 05116741dbe5c..0000000000000 --- a/test/api_integration/fixtures/es_archiver/management/saved_objects/search/data.json +++ /dev/null @@ -1,198 +0,0 @@ -{ - "type": "doc", - "value": { - "id": "index-pattern:8963ca30-3224-11e8-a572-ffca06da1357", - "index": ".kibana", - "source": { - "coreMigrationVersion": "7.14.0", - "index-pattern": { - "fields": "[{\"name\":\"_id\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_index\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_score\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_source\",\"type\":\"_source\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_type\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"id\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true}]", - "title": "saved_objects*" - }, - "migrationVersion": { - "index-pattern": "7.11.0" - }, - "references": [ - ], - "type": "index-pattern", - "updated_at": "2018-03-28T01:08:34.290Z" - }, - "type": "_doc" - } -} - -{ - "type": "doc", - "value": { - "id": "config:7.0.0-alpha1", - "index": ".kibana", - "source": { - "config": { - "buildNum": 8467, - "defaultIndex": "8963ca30-3224-11e8-a572-ffca06da1357", - "telemetry:optIn": false - }, - "coreMigrationVersion": "7.14.0", - "migrationVersion": { - "config": "7.13.0" - }, - "references": [ - ], - "type": "config", - "updated_at": "2018-03-28T01:08:39.248Z" - }, - "type": "_doc" - } -} - -{ - "type": "doc", - "value": { - "id": "search:960372e0-3224-11e8-a572-ffca06da1357", - "index": ".kibana", - "source": { - "coreMigrationVersion": "7.14.0", - "migrationVersion": { - "search": "7.9.3" - }, - "references": [ - { - "id": "8963ca30-3224-11e8-a572-ffca06da1357", - "name": "kibanaSavedObjectMeta.searchSourceJSON.index", - "type": "index-pattern" - } - ], - "search": { - "columns": [ - "_source" - ], - "description": "", - "hits": 0, - "kibanaSavedObjectMeta": { - "searchSourceJSON": "{\"highlightAll\":true,\"version\":true,\"query\":{\"query\":\"id:3\",\"language\":\"lucene\"},\"filter\":[],\"indexRefName\":\"kibanaSavedObjectMeta.searchSourceJSON.index\"}" - }, - "sort": [ - [ - "_score", - "desc" - ] - ], - "title": "OneRecord", - "version": 1 - }, - "type": "search", - "updated_at": "2018-03-28T01:08:55.182Z" - }, - "type": "_doc" - } -} - -{ - "type": "doc", - "value": { - "id": "visualization:a42c0580-3224-11e8-a572-ffca06da1357", - "index": ".kibana", - "source": { - "coreMigrationVersion": "7.14.0", - "migrationVersion": { - "visualization": "7.14.0" - }, - "references": [ - { - "id": "960372e0-3224-11e8-a572-ffca06da1357", - "name": "search_0", - "type": "search" - } - ], - "type": "visualization", - "updated_at": "2018-03-28T01:09:18.936Z", - "visualization": { - "description": "", - "kibanaSavedObjectMeta": { - "searchSourceJSON": "{\"filter\":[],\"query\":{\"query\":\"\",\"language\":\"lucene\"}}" - }, - "savedSearchRefName": "search_0", - "title": "VisualizationFromSavedSearch", - "uiStateJSON": "{\"vis\":{\"params\":{\"sort\":{\"columnIndex\":null,\"direction\":null}}}}", - "version": 1, - "visState": "{\"title\":\"VisualizationFromSavedSearch\",\"type\":\"table\",\"params\":{\"perPage\":10,\"showPartialRows\":false,\"showMeticsAtAllLevels\":false,\"sort\":{\"columnIndex\":null,\"direction\":null},\"showTotal\":false,\"totalFunc\":\"sum\",\"showToolbar\":true},\"aggs\":[{\"id\":\"1\",\"enabled\":true,\"type\":\"count\",\"schema\":\"metric\",\"params\":{}}]}" - } - }, - "type": "_doc" - } -} - -{ - "type": "doc", - "value": { - "id": "visualization:add810b0-3224-11e8-a572-ffca06da1357", - "index": ".kibana", - "source": { - "coreMigrationVersion": "7.14.0", - "migrationVersion": { - "visualization": "7.14.0" - }, - "references": [ - { - "id": "8963ca30-3224-11e8-a572-ffca06da1357", - "name": "kibanaSavedObjectMeta.searchSourceJSON.index", - "type": "index-pattern" - } - ], - "type": "visualization", - "updated_at": "2018-03-28T01:09:35.163Z", - "visualization": { - "description": "", - "kibanaSavedObjectMeta": { - "searchSourceJSON": "{\"filter\":[],\"query\":{\"query\":\"\",\"language\":\"lucene\"},\"indexRefName\":\"kibanaSavedObjectMeta.searchSourceJSON.index\"}" - }, - "title": "Visualization", - "uiStateJSON": "{}", - "version": 1, - "visState": "{\"title\":\"Visualization\",\"type\":\"metric\",\"params\":{\"addTooltip\":true,\"addLegend\":false,\"type\":\"metric\",\"metric\":{\"percentageMode\":false,\"useRanges\":false,\"colorSchema\":\"Green to Red\",\"metricColorMode\":\"None\",\"colorsRange\":[{\"from\":0,\"to\":10000}],\"labels\":{\"show\":true},\"invertColors\":false,\"style\":{\"bgFill\":\"#000\",\"bgColor\":false,\"labelColor\":false,\"subText\":\"\",\"fontSize\":60}}},\"aggs\":[{\"id\":\"1\",\"enabled\":true,\"type\":\"count\",\"schema\":\"metric\",\"params\":{}}]}" - } - }, - "type": "_doc" - } -} - -{ - "type": "doc", - "value": { - "id": "dashboard:b70c7ae0-3224-11e8-a572-ffca06da1357", - "index": ".kibana", - "source": { - "coreMigrationVersion": "7.14.0", - "dashboard": { - "description": "", - "hits": 0, - "kibanaSavedObjectMeta": { - "searchSourceJSON": "{\"query\":{\"query\":\"\",\"language\":\"lucene\"},\"filter\":[],\"highlightAll\":true,\"version\":true}" - }, - "optionsJSON": "{\"darkTheme\":false,\"useMargins\":true,\"hidePanelTitles\":false}", - "panelsJSON": "[{\"version\":\"7.0.0-alpha1\",\"gridData\":{\"w\":24,\"h\":15,\"x\":0,\"y\":0,\"i\":\"1\"},\"panelIndex\":\"1\",\"embeddableConfig\":{\"enhancements\":{}},\"panelRefName\":\"panel_0\"},{\"version\":\"7.0.0-alpha1\",\"gridData\":{\"w\":24,\"h\":15,\"x\":24,\"y\":0,\"i\":\"2\"},\"panelIndex\":\"2\",\"embeddableConfig\":{\"enhancements\":{}},\"panelRefName\":\"panel_1\"}]", - "timeRestore": false, - "title": "Dashboard", - "version": 1 - }, - "migrationVersion": { - "dashboard": "7.14.0" - }, - "references": [ - { - "id": "add810b0-3224-11e8-a572-ffca06da1357", - "name": "panel_0", - "type": "visualization" - }, - { - "id": "a42c0580-3224-11e8-a572-ffca06da1357", - "name": "panel_1", - "type": "visualization" - } - ], - "type": "dashboard", - "updated_at": "2018-03-28T01:09:50.606Z" - }, - "type": "_doc" - } -} \ No newline at end of file diff --git a/test/api_integration/fixtures/es_archiver/management/saved_objects/search/mappings.json b/test/api_integration/fixtures/es_archiver/management/saved_objects/search/mappings.json deleted file mode 100644 index e9ec4e680d74e..0000000000000 --- a/test/api_integration/fixtures/es_archiver/management/saved_objects/search/mappings.json +++ /dev/null @@ -1,476 +0,0 @@ -{ - "type": "index", - "value": { - "aliases": { - ".kibana_$KIBANA_PACKAGE_VERSION": {}, - ".kibana": {} - }, - "index": ".kibana_$KIBANA_PACKAGE_VERSION_001", - "mappings": { - "_meta": { - "migrationMappingPropertyHashes": { - "application_usage_daily": "43b8830d5d0df85a6823d290885fc9fd", - "application_usage_totals": "3d1b76c39bfb2cc8296b024d73854724", - "application_usage_transactional": "3d1b76c39bfb2cc8296b024d73854724", - "config": "c63748b75f39d0c54de12d12c1ccbc20", - "core-usage-stats": "3d1b76c39bfb2cc8296b024d73854724", - "coreMigrationVersion": "2f4316de49999235636386fe51dc06c1", - "dashboard": "40554caf09725935e2c02e02563a2d07", - "index-pattern": "45915a1ad866812242df474eb0479052", - "kql-telemetry": "d12a98a6f19a2d273696597547e064ee", - "legacy-url-alias": "6155300fd11a00e23d5cbaa39f0fce0a", - "migrationVersion": "4a1746014a75ade3a714e1db5763276f", - "namespace": "2f4316de49999235636386fe51dc06c1", - "namespaces": "2f4316de49999235636386fe51dc06c1", - "originId": "2f4316de49999235636386fe51dc06c1", - "query": "11aaeb7f5f7fa5bb43f25e18ce26e7d9", - "references": "7997cf5a56cc02bdc9c93361bde732b0", - "sample-data-telemetry": "7d3cfeb915303c9641c59681967ffeb4", - "search": "db2c00e39b36f40930a3b9fc71c823e1", - "search-telemetry": "3d1b76c39bfb2cc8296b024d73854724", - "telemetry": "36a616f7026dfa617d6655df850fe16d", - "type": "2f4316de49999235636386fe51dc06c1", - "ui-counter": "0d409297dc5ebe1e3a1da691c6ee32e3", - "ui-metric": "0d409297dc5ebe1e3a1da691c6ee32e3", - "updated_at": "00da57df13e94e9d98437d13ace4bfe0", - "url": "c7f66a0df8b1b52f17c28c4adb111105", - "usage-counters": "8cc260bdceffec4ffc3ad165c97dc1b4", - "visualization": "f819cf6636b75c9e76ba733a0c6ef355" - } - }, - "dynamic": "strict", - "properties": { - "application_usage_daily": { - "dynamic": "false", - "properties": { - "timestamp": { - "type": "date" - } - } - }, - "application_usage_totals": { - "dynamic": "false", - "type": "object" - }, - "application_usage_transactional": { - "dynamic": "false", - "type": "object" - }, - "config": { - "dynamic": "false", - "properties": { - "buildNum": { - "type": "keyword" - } - } - }, - "core-usage-stats": { - "dynamic": "false", - "type": "object" - }, - "coreMigrationVersion": { - "type": "keyword" - }, - "dashboard": { - "properties": { - "description": { - "type": "text" - }, - "hits": { - "doc_values": false, - "index": false, - "type": "integer" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "index": false, - "type": "text" - } - } - }, - "optionsJSON": { - "index": false, - "type": "text" - }, - "panelsJSON": { - "index": false, - "type": "text" - }, - "refreshInterval": { - "properties": { - "display": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "pause": { - "doc_values": false, - "index": false, - "type": "boolean" - }, - "section": { - "doc_values": false, - "index": false, - "type": "integer" - }, - "value": { - "doc_values": false, - "index": false, - "type": "integer" - } - } - }, - "timeFrom": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "timeRestore": { - "doc_values": false, - "index": false, - "type": "boolean" - }, - "timeTo": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "title": { - "type": "text" - }, - "version": { - "type": "integer" - } - } - }, - "graph-workspace": { - "dynamic": "false", - "type": "object" - }, - "index-pattern": { - "dynamic": "false", - "properties": { - "title": { - "type": "text" - }, - "type": { - "type": "keyword" - } - } - }, - "kql-telemetry": { - "properties": { - "optInCount": { - "type": "long" - }, - "optOutCount": { - "type": "long" - } - } - }, - "legacy-url-alias": { - "dynamic": "false", - "properties": { - "disabled": { - "type": "boolean" - }, - "sourceId": { - "type": "keyword" - }, - "targetType": { - "type": "keyword" - } - } - }, - "migrationVersion": { - "dynamic": "true", - "properties": { - "config": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "dashboard": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "index-pattern": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "search": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - }, - "visualization": { - "fields": { - "keyword": { - "ignore_above": 256, - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "namespace": { - "type": "keyword" - }, - "namespaces": { - "type": "keyword" - }, - "originId": { - "type": "keyword" - }, - "query": { - "properties": { - "description": { - "type": "text" - }, - "filters": { - "enabled": false, - "type": "object" - }, - "query": { - "properties": { - "language": { - "type": "keyword" - }, - "query": { - "index": false, - "type": "keyword" - } - } - }, - "timefilter": { - "enabled": false, - "type": "object" - }, - "title": { - "type": "text" - } - } - }, - "references": { - "properties": { - "id": { - "type": "keyword" - }, - "name": { - "type": "keyword" - }, - "type": { - "type": "keyword" - } - }, - "type": "nested" - }, - "sample-data-telemetry": { - "properties": { - "installCount": { - "type": "long" - }, - "unInstallCount": { - "type": "long" - } - } - }, - "search": { - "properties": { - "columns": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "description": { - "type": "text" - }, - "grid": { - "enabled": false, - "type": "object" - }, - "hideChart": { - "doc_values": false, - "index": false, - "type": "boolean" - }, - "hits": { - "doc_values": false, - "index": false, - "type": "integer" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "index": false, - "type": "text" - } - } - }, - "sort": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "title": { - "type": "text" - }, - "version": { - "type": "integer" - } - } - }, - "search-telemetry": { - "dynamic": "false", - "type": "object" - }, - "server": { - "dynamic": "false", - "type": "object" - }, - "telemetry": { - "properties": { - "allowChangingOptInStatus": { - "type": "boolean" - }, - "enabled": { - "type": "boolean" - }, - "lastReported": { - "type": "date" - }, - "lastVersionChecked": { - "type": "keyword" - }, - "reportFailureCount": { - "type": "integer" - }, - "reportFailureVersion": { - "type": "keyword" - }, - "sendUsageFrom": { - "type": "keyword" - }, - "userHasSeenNotice": { - "type": "boolean" - } - } - }, - "type": { - "type": "keyword" - }, - "ui-counter": { - "properties": { - "count": { - "type": "integer" - } - } - }, - "ui-metric": { - "properties": { - "count": { - "type": "integer" - } - } - }, - "updated_at": { - "type": "date" - }, - "url": { - "properties": { - "accessCount": { - "type": "long" - }, - "accessDate": { - "type": "date" - }, - "createDate": { - "type": "date" - }, - "url": { - "fields": { - "keyword": { - "ignore_above": 2048, - "type": "keyword" - } - }, - "type": "text" - } - } - }, - "usage-counters": { - "dynamic": "false", - "properties": { - "domainId": { - "type": "keyword" - } - } - }, - "visualization": { - "properties": { - "description": { - "type": "text" - }, - "kibanaSavedObjectMeta": { - "properties": { - "searchSourceJSON": { - "index": false, - "type": "text" - } - } - }, - "savedSearchRefName": { - "doc_values": false, - "index": false, - "type": "keyword" - }, - "title": { - "type": "text" - }, - "uiStateJSON": { - "index": false, - "type": "text" - }, - "version": { - "type": "integer" - }, - "visState": { - "index": false, - "type": "text" - } - } - } - } - }, - "settings": { - "index": { - "auto_expand_replicas": "0-1", - "number_of_replicas": "0", - "number_of_shards": "1", - "priority": "10", - "refresh_interval": "1s", - "routing_partition_size": "1" - } - } - } -} \ No newline at end of file diff --git a/test/api_integration/fixtures/kbn_archiver/saved_objects/search.json b/test/api_integration/fixtures/kbn_archiver/saved_objects/search.json new file mode 100644 index 0000000000000..7bd1b73a9ba19 --- /dev/null +++ b/test/api_integration/fixtures/kbn_archiver/saved_objects/search.json @@ -0,0 +1,143 @@ +{ + "attributes": { + "fields": "[{\"name\":\"_id\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_index\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"_score\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_source\",\"type\":\"_source\",\"count\":0,\"scripted\":false,\"searchable\":false,\"aggregatable\":false,\"readFromDocValues\":false},{\"name\":\"_type\",\"type\":\"string\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":false},{\"name\":\"id\",\"type\":\"number\",\"count\":0,\"scripted\":false,\"searchable\":true,\"aggregatable\":true,\"readFromDocValues\":true}]", + "title": "saved_objects*" + }, + "coreMigrationVersion": "8.4.0", + "id": "8963ca30-3224-11e8-a572-ffca06da1357", + "migrationVersion": { + "index-pattern": "8.0.0" + }, + "references": [], + "type": "index-pattern", + "updated_at": "2018-03-28T01:08:34.290Z", + "version": "WzEyLDFd" +} + +{ + "attributes": { + "columns": [ + "_source" + ], + "description": "", + "hits": 0, + "kibanaSavedObjectMeta": { + "searchSourceJSON": "{\"highlightAll\":true,\"version\":true,\"query\":{\"query\":\"id:3\",\"language\":\"lucene\"},\"filter\":[],\"indexRefName\":\"kibanaSavedObjectMeta.searchSourceJSON.index\"}" + }, + "sort": [ + [ + "_score", + "desc" + ] + ], + "title": "OneRecord", + "version": 1 + }, + "coreMigrationVersion": "8.4.0", + "id": "960372e0-3224-11e8-a572-ffca06da1357", + "migrationVersion": { + "search": "8.0.0" + }, + "references": [ + { + "id": "8963ca30-3224-11e8-a572-ffca06da1357", + "name": "kibanaSavedObjectMeta.searchSourceJSON.index", + "type": "index-pattern" + } + ], + "type": "search", + "updated_at": "2018-03-28T01:08:55.182Z", + "version": "WzE0LDFd" +} + +{ + "attributes": { + "description": "", + "kibanaSavedObjectMeta": { + "searchSourceJSON": "{\"filter\":[],\"query\":{\"query\":\"\",\"language\":\"lucene\"}}" + }, + "savedSearchRefName": "search_0", + "title": "VisualizationFromSavedSearch", + "uiStateJSON": "{\"vis\":{\"params\":{\"sort\":{\"columnIndex\":null,\"direction\":null}}}}", + "version": 1, + "visState": "{\"title\":\"VisualizationFromSavedSearch\",\"type\":\"table\",\"params\":{\"perPage\":10,\"showPartialRows\":false,\"showMeticsAtAllLevels\":false,\"sort\":{\"columnIndex\":null,\"direction\":null},\"showTotal\":false,\"totalFunc\":\"sum\",\"showToolbar\":true},\"aggs\":[{\"id\":\"1\",\"enabled\":true,\"type\":\"count\",\"schema\":\"metric\",\"params\":{}}]}" + }, + "coreMigrationVersion": "8.4.0", + "id": "a42c0580-3224-11e8-a572-ffca06da1357", + "migrationVersion": { + "visualization": "8.3.0" + }, + "references": [ + { + "id": "960372e0-3224-11e8-a572-ffca06da1357", + "name": "search_0", + "type": "search" + } + ], + "type": "visualization", + "updated_at": "2018-03-28T01:09:18.936Z", + "version": "WzE1LDFd" +} + +{ + "attributes": { + "description": "", + "kibanaSavedObjectMeta": { + "searchSourceJSON": "{\"filter\":[],\"query\":{\"query\":\"\",\"language\":\"lucene\"},\"indexRefName\":\"kibanaSavedObjectMeta.searchSourceJSON.index\"}" + }, + "title": "Visualization", + "uiStateJSON": "{}", + "version": 1, + "visState": "{\"title\":\"Visualization\",\"type\":\"metric\",\"params\":{\"addTooltip\":true,\"addLegend\":false,\"type\":\"metric\",\"metric\":{\"percentageMode\":false,\"useRanges\":false,\"colorSchema\":\"Green to Red\",\"metricColorMode\":\"None\",\"colorsRange\":[{\"from\":0,\"to\":10000}],\"labels\":{\"show\":true},\"invertColors\":false,\"style\":{\"bgFill\":\"#000\",\"bgColor\":false,\"labelColor\":false,\"subText\":\"\",\"fontSize\":60}}},\"aggs\":[{\"id\":\"1\",\"enabled\":true,\"type\":\"count\",\"schema\":\"metric\",\"params\":{}}]}" + }, + "coreMigrationVersion": "8.4.0", + "id": "add810b0-3224-11e8-a572-ffca06da1357", + "migrationVersion": { + "visualization": "8.3.0" + }, + "references": [ + { + "id": "8963ca30-3224-11e8-a572-ffca06da1357", + "name": "kibanaSavedObjectMeta.searchSourceJSON.index", + "type": "index-pattern" + } + ], + "type": "visualization", + "updated_at": "2018-03-28T01:09:35.163Z", + "version": "WzE2LDFd" +} + +{ + "attributes": { + "description": "", + "hits": 0, + "kibanaSavedObjectMeta": { + "searchSourceJSON": "{\"query\":{\"query\":\"\",\"language\":\"lucene\"},\"filter\":[],\"highlightAll\":true,\"version\":true}" + }, + "optionsJSON": "{\"darkTheme\":false,\"useMargins\":true,\"hidePanelTitles\":false}", + "panelsJSON": "[{\"version\":\"7.0.0-alpha1\",\"gridData\":{\"w\":24,\"h\":15,\"x\":0,\"y\":0,\"i\":\"1\"},\"panelIndex\":\"1\",\"embeddableConfig\":{\"enhancements\":{}},\"panelRefName\":\"panel_0\"},{\"version\":\"7.0.0-alpha1\",\"gridData\":{\"w\":24,\"h\":15,\"x\":24,\"y\":0,\"i\":\"2\"},\"panelIndex\":\"2\",\"embeddableConfig\":{\"enhancements\":{}},\"panelRefName\":\"panel_1\"}]", + "timeRestore": false, + "title": "Dashboard", + "version": 1 + }, + "coreMigrationVersion": "8.4.0", + "id": "b70c7ae0-3224-11e8-a572-ffca06da1357", + "migrationVersion": { + "dashboard": "8.3.0" + }, + "references": [ + { + "id": "add810b0-3224-11e8-a572-ffca06da1357", + "name": "panel_0", + "type": "visualization" + }, + { + "id": "a42c0580-3224-11e8-a572-ffca06da1357", + "name": "panel_1", + "type": "visualization" + } + ], + "type": "dashboard", + "updated_at": "2018-03-28T01:09:50.606Z", + "version": "WzE3LDFd" +} \ No newline at end of file From 68edf8255216400b627ab42f135654f1edb959e3 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 18 Jul 2022 08:01:25 -0700 Subject: [PATCH 093/111] Update ftr (main) (#136434) * Update ftr * dedupe Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Jonathan Budzenski --- package.json | 4 ++-- yarn.lock | 43 ++++++++++++++++++++++++------------------- 2 files changed, 26 insertions(+), 21 deletions(-) diff --git a/package.json b/package.json index 5d9e8f86bacfd..93912b9cf2cf7 100644 --- a/package.json +++ b/package.json @@ -1062,7 +1062,7 @@ "fetch-mock": "^7.3.9", "file-loader": "^4.2.0", "form-data": "^4.0.0", - "geckodriver": "^3.0.1", + "geckodriver": "^3.0.2", "gulp": "4.0.2", "gulp-babel": "^8.0.0", "gulp-brotli": "^3.0.0", @@ -1138,7 +1138,7 @@ "resolve": "^1.22.0", "rxjs-marbles": "^5.0.6", "sass-loader": "^10.3.1", - "selenium-webdriver": "^4.3.0", + "selenium-webdriver": "^4.3.1", "simple-git": "1.116.0", "sinon": "^7.4.2", "sort-package-json": "^1.53.1", diff --git a/yarn.lock b/yarn.lock index 65ac755b1eed0..8f1b5730031dd 100644 --- a/yarn.lock +++ b/yarn.lock @@ -10735,17 +10735,17 @@ cacheable-request@^6.0.0: normalize-url "^4.1.0" responselike "^1.0.2" -cacheable-request@^7.0.1: - version "7.0.1" - resolved "https://registry.yarnpkg.com/cacheable-request/-/cacheable-request-7.0.1.tgz#062031c2856232782ed694a257fa35da93942a58" - integrity sha512-lt0mJ6YAnsrBErpTMWeu5kl/tg9xMAWjavYTN6VQXM1A/teBITuNcccXsCxF0tDQQJf9DfAaX5O4e0zp0KlfZw== +cacheable-request@^7.0.2: + version "7.0.2" + resolved "https://registry.yarnpkg.com/cacheable-request/-/cacheable-request-7.0.2.tgz#ea0d0b889364a25854757301ca12b2da77f91d27" + integrity sha512-pouW8/FmiPQbuGpkXQ9BAPv/Mo5xDGANgSNXzTzJ8DrKGuXOssM4wIQRjfanNRh3Yu5cfYPvcorqbhg2KIJtew== dependencies: clone-response "^1.0.2" get-stream "^5.1.0" http-cache-semantics "^4.0.0" keyv "^4.0.0" lowercase-keys "^2.0.0" - normalize-url "^4.1.0" + normalize-url "^6.0.1" responselike "^2.0.0" cached-path-relative@^1.0.0, cached-path-relative@^1.0.2: @@ -15906,14 +15906,14 @@ gaze@^1.0.0: dependencies: globule "^1.0.0" -geckodriver@^3.0.1: - version "3.0.1" - resolved "https://registry.yarnpkg.com/geckodriver/-/geckodriver-3.0.1.tgz#ded3512f3c6ddc490139b9d5e8fd6925d41c5631" - integrity sha512-cHmbNFqt4eelymsuVt7B5nh+qYGpPCltM7rd+k+CBaTvxGGr4j6STeOYahXMNdSeUbCVhqP345OuqWnvHYAz4Q== +geckodriver@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/geckodriver/-/geckodriver-3.0.2.tgz#6bd69166a24859c5edbc6ece9868339378b6c97b" + integrity sha512-GHOQzQnTeZOJdcdEXLuzmcRwkbHuei1VivXkn2BLyleKiT6lTvl0T7vm+d0wvr/EZC7jr0m1u1pBHSfqtuFuNQ== dependencies: adm-zip "0.5.9" bluebird "3.7.2" - got "11.8.2" + got "11.8.5" https-proxy-agent "5.0.0" tar "6.1.11" @@ -16388,17 +16388,17 @@ google-protobuf@^3.6.1: resolved "https://registry.yarnpkg.com/google-protobuf/-/google-protobuf-3.19.4.tgz#8d32c3e34be9250956f28c0fb90955d13f311888" integrity sha512-OIPNCxsG2lkIvf+P5FNfJ/Km95CsXOBecS9ZcAU6m2Rq3svc0Apl9nB3GMDNKfQ9asNv4KjyAqGwPQFrVle3Yg== -got@11.8.2, got@^11.8.2: - version "11.8.2" - resolved "https://registry.yarnpkg.com/got/-/got-11.8.2.tgz#7abb3959ea28c31f3576f1576c1effce23f33599" - integrity sha512-D0QywKgIe30ODs+fm8wMZiAcZjypcCodPNuMz5H9Mny7RJ+IjJ10BdmGW7OM7fHXP+O7r6ZwapQ/YQmMSvB0UQ== +got@11.8.5, got@^11.8.2: + version "11.8.5" + resolved "https://registry.yarnpkg.com/got/-/got-11.8.5.tgz#ce77d045136de56e8f024bebb82ea349bc730046" + integrity sha512-o0Je4NvQObAuZPHLFoRSkdG2lTgtcynqymzg2Vupdx6PorhaT5MCbIyXG6d4D94kk8ZG57QeosgdiqfJWhEhlQ== dependencies: "@sindresorhus/is" "^4.0.0" "@szmarczak/http-timer" "^4.0.5" "@types/cacheable-request" "^6.0.1" "@types/responselike" "^1.0.0" cacheable-lookup "^5.0.3" - cacheable-request "^7.0.1" + cacheable-request "^7.0.2" decompress-response "^6.0.0" http2-wrapper "^1.0.0-beta.5.2" lowercase-keys "^2.0.0" @@ -21826,6 +21826,11 @@ normalize-url@^4.1.0: resolved "https://registry.yarnpkg.com/normalize-url/-/normalize-url-4.5.1.tgz#0dd90cf1288ee1d1313b87081c9a5932ee48518a" integrity sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA== +normalize-url@^6.0.1: + version "6.1.0" + resolved "https://registry.yarnpkg.com/normalize-url/-/normalize-url-6.1.0.tgz#40d0885b535deffe3f3147bec877d05fe4c5668a" + integrity sha512-DlL+XwOy3NxAQ8xuC0okPgK46iuVNAK01YN7RueYBqqFeGsBjV9XmCAzAdgt+667bCl5kPh9EqKKDwnaPG1I7A== + now-and-later@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/now-and-later/-/now-and-later-2.0.0.tgz#bc61cbb456d79cb32207ce47ca05136ff2e7d6ee" @@ -26301,10 +26306,10 @@ select-hose@^2.0.0: resolved "https://registry.yarnpkg.com/select-hose/-/select-hose-2.0.0.tgz#625d8658f865af43ec962bfc376a37359a4994ca" integrity sha1-Yl2GWPhlr0Psliv8N2o3NZpJlMo= -selenium-webdriver@^4.3.0: - version "4.3.0" - resolved "https://registry.yarnpkg.com/selenium-webdriver/-/selenium-webdriver-4.3.0.tgz#00526ddeca3c187c8d889cd3f790926b95d5f044" - integrity sha512-9XFr8w95BO7jageR61AtiB83fJNem3fdtOQcUpqIIDHWSxihomyG/yBlL1H4y/shi/dO/Ai3PJMAOG+OW3+JHw== +selenium-webdriver@^4.3.1: + version "4.3.1" + resolved "https://registry.yarnpkg.com/selenium-webdriver/-/selenium-webdriver-4.3.1.tgz#5e9c6c4adee65e57776b5bd4c07c59b65b8f056d" + integrity sha512-TjH/ls1WKRQoFEHcqtn6UtwcLnA3yvx08v9cSSFYvyhp8hJWRtbe9ae2I8uXPisEZ2EaGKKoxBZ4EHv0BJM15g== dependencies: jszip "^3.10.0" tmp "^0.2.1" From d392a61cdca497e037cbd0c42f24b3f24bac58be Mon Sep 17 00:00:00 2001 From: Nicolas Chaulet Date: Mon, 18 Jul 2022 11:05:41 -0400 Subject: [PATCH 094/111] [Fleet] Show mappings rollover modal when editing fleet @custom component template (#135845) --- .../common/types/component_templates.ts | 4 + .../component_template_edit.test.tsx | 107 +++++- .../component_template_edit.helpers.ts | 9 +- .../helpers/http_requests.ts | 26 ++ .../helpers/setup_environment.tsx | 34 +- .../component_template_edit.tsx | 41 ++- .../mappings_datastreams_rollover_modal.tsx | 125 +++++++ .../component_template_form.tsx | 3 + .../steps/step_review.tsx | 316 ++++++++++-------- .../steps/step_review_container.tsx | 17 +- .../component_templates_context.tsx | 4 + .../component_templates/constants.ts | 2 + .../components/component_templates/lib/api.ts | 34 ++ .../component_templates/lib/request.ts | 4 +- .../component_templates/shared_imports.ts | 1 + .../public/application/index.tsx | 3 +- .../routes/api/component_templates/index.ts | 2 + .../register_datastream_route.ts | 78 +++++ .../server/routes/api/data_streams/index.ts | 3 + .../api/data_streams/register_post_route.ts | 104 ++++++ .../index_management/component_templates.ts | 82 ++++- .../index_management/data_streams.ts | 84 +++++ .../index_management/lib/elasticsearch.js | 49 +++ 23 files changed, 966 insertions(+), 166 deletions(-) create mode 100644 x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_edit/mappings_datastreams_rollover_modal.tsx create mode 100644 x-pack/plugins/index_management/server/routes/api/component_templates/register_datastream_route.ts create mode 100644 x-pack/plugins/index_management/server/routes/api/data_streams/register_post_route.ts diff --git a/x-pack/plugins/index_management/common/types/component_templates.ts b/x-pack/plugins/index_management/common/types/component_templates.ts index 50d4b37298b4b..d2842b0486303 100644 --- a/x-pack/plugins/index_management/common/types/component_templates.ts +++ b/x-pack/plugins/index_management/common/types/component_templates.ts @@ -40,3 +40,7 @@ export interface ComponentTemplateListItem { hasSettings: boolean; isManaged: boolean; } + +export interface ComponentTemplateDatastreams { + data_streams: string[]; +} diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/component_template_edit.test.tsx b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/component_template_edit.test.tsx index e2ccb0ca70808..94beecf441b07 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/component_template_edit.test.tsx +++ b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/component_template_edit.test.tsx @@ -50,6 +50,9 @@ describe('', () => { COMPONENT_TEMPLATE_TO_EDIT.name, COMPONENT_TEMPLATE_TO_EDIT ); + httpRequestsMockHelpers.setGetComponentTemplateDatastream(COMPONENT_TEMPLATE_TO_EDIT.name, { + data_streams: [], + }); await act(async () => { testBed = await setup(httpSetup); @@ -86,7 +89,7 @@ describe('', () => { describe('form payload', () => { it('should send the correct payload with changed values', async () => { - const { actions, component, form } = testBed; + const { actions, component, form, coreStart } = testBed; await act(async () => { form.setInputValue('versionField.input', '1'); @@ -120,6 +123,108 @@ describe('', () => { }), }) ); + // Mapping rollout modal should not be opened if the component template is not managed by Fleet + expect(coreStart.overlays.openModal).not.toBeCalled(); + }); + }); + + describe('managed by fleet', () => { + const DATASTREAM_NAME = 'logs-test-default'; + beforeEach(async () => { + httpRequestsMockHelpers.setLoadComponentTemplateResponse( + COMPONENT_TEMPLATE_TO_EDIT.name, + Object.assign({}, COMPONENT_TEMPLATE_TO_EDIT, { + _meta: { managed_by: 'fleet' }, + }) + ); + + httpRequestsMockHelpers.setGetComponentTemplateDatastream(COMPONENT_TEMPLATE_TO_EDIT.name, { + data_streams: [DATASTREAM_NAME], + }); + + await act(async () => { + testBed = await setup(httpSetup); + }); + + testBed.component.update(); + }); + + it('should show mappings rollover modal on save if apply mappings call failed', async () => { + httpRequestsMockHelpers.setPostDatastreamMappingsFromTemplate( + DATASTREAM_NAME, + {}, + { message: 'Bad request', statusCode: 400 } + ); + const { actions, component, form, coreStart } = testBed; + + await act(async () => { + form.setInputValue('versionField.input', '1'); + }); + + await act(async () => { + actions.clickNextButton(); + }); + + component.update(); + + await actions.completeStepSettings(); + await actions.completeStepMappings(); + await actions.completeStepAliases(); + + await act(async () => { + actions.clickNextButton(); + }); + + component.update(); + + expect(httpSetup.put).toHaveBeenLastCalledWith( + `${API_BASE_PATH}/component_templates/${COMPONENT_TEMPLATE_TO_EDIT.name}`, + expect.anything() + ); + expect(httpSetup.post).toHaveBeenLastCalledWith( + `${API_BASE_PATH}/data_streams/${DATASTREAM_NAME}/mappings_from_template`, + expect.anything() + ); + + expect(coreStart.overlays.openModal).toBeCalled(); + }); + + it('should not show mappings rollover modal on save if apply mappings call succeed', async () => { + httpRequestsMockHelpers.setPostDatastreamMappingsFromTemplate(DATASTREAM_NAME, { + success: true, + }); + const { actions, component, form, coreStart } = testBed; + + await act(async () => { + form.setInputValue('versionField.input', '1'); + }); + + await act(async () => { + actions.clickNextButton(); + }); + + component.update(); + + await actions.completeStepSettings(); + await actions.completeStepMappings(); + await actions.completeStepAliases(); + + await act(async () => { + actions.clickNextButton(); + }); + + component.update(); + + expect(httpSetup.put).toHaveBeenLastCalledWith( + `${API_BASE_PATH}/component_templates/${COMPONENT_TEMPLATE_TO_EDIT.name}`, + expect.anything() + ); + expect(httpSetup.post).toHaveBeenLastCalledWith( + `${API_BASE_PATH}/data_streams/${DATASTREAM_NAME}/mappings_from_template`, + expect.anything() + ); + + expect(coreStart.overlays.openModal).not.toBeCalled(); }); }); }); diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/component_template_edit.helpers.ts b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/component_template_edit.helpers.ts index f1ec4abaf90a3..6b49171ea5620 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/component_template_edit.helpers.ts +++ b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/component_template_edit.helpers.ts @@ -6,7 +6,8 @@ */ import { registerTestBed, TestBed, AsyncTestBedConfig } from '@kbn/test-jest-helpers'; -import { HttpSetup } from '@kbn/core/public'; +import { coreMock } from '@kbn/core/public/mocks'; +import type { HttpSetup } from '@kbn/core/public'; import { BASE_PATH } from '../../../../../../../common'; import { ComponentTemplateEdit } from '../../../component_template_wizard'; @@ -18,6 +19,7 @@ import { export type ComponentTemplateEditTestBed = TestBed & { actions: ReturnType; + coreStart: ReturnType; }; export const setup = async ( @@ -32,8 +34,10 @@ export const setup = async ( doMountAsync: true, }; + const coreStart = coreMock.createStart(); + const initTestBed = registerTestBed( - WithAppDependencies(ComponentTemplateEdit, httpSetup), + WithAppDependencies(ComponentTemplateEdit, httpSetup, coreStart), testBedConfig ); const testBed = await initTestBed(); @@ -41,5 +45,6 @@ export const setup = async ( return { ...testBed, actions: getFormActions(testBed), + coreStart, }; }; diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/http_requests.ts b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/http_requests.ts index f3019e12eea9c..8ce2a34db397b 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/http_requests.ts +++ b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/http_requests.ts @@ -55,6 +55,18 @@ const registerHttpRequestMockHelpers = ( .set(path, error ? defuse(Promise.reject({ body: error })) : Promise.resolve(response)); }; + const setGetComponentTemplateDatastream = ( + templateId: string, + response?: HttpResponse, + error?: ResponseError + ) => + mockResponse( + 'GET', + `${API_BASE_PATH}/component_templates/${templateId}/datastreams`, + response, + error + ); + const setLoadComponentTemplatesResponse = (response?: HttpResponse, error?: ResponseError) => mockResponse('GET', `${API_BASE_PATH}/component_templates`, response, error); @@ -74,11 +86,25 @@ const registerHttpRequestMockHelpers = ( const setCreateComponentTemplateResponse = (response?: HttpResponse, error?: ResponseError) => mockResponse('POST', `${API_BASE_PATH}/component_templates`, response, error); + const setPostDatastreamMappingsFromTemplate = ( + name: string, + response?: HttpResponse, + error?: ResponseError + ) => + mockResponse( + 'POST', + `${API_BASE_PATH}/data_streams/${name}/mappings_from_template`, + response, + error + ); + return { setLoadComponentTemplatesResponse, setDeleteComponentTemplateResponse, setLoadComponentTemplateResponse, setCreateComponentTemplateResponse, + setGetComponentTemplateDatastream, + setPostDatastreamMappingsFromTemplate, }; }; diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/setup_environment.tsx b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/setup_environment.tsx index 0987fc18e657e..25165fe782c99 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/setup_environment.tsx +++ b/x-pack/plugins/index_management/public/application/components/component_templates/__jest__/client_integration/helpers/setup_environment.tsx @@ -7,10 +7,10 @@ import React from 'react'; -import { HttpSetup } from '@kbn/core/public'; +import type { CoreStart, HttpSetup } from '@kbn/core/public'; import { docLinksServiceMock } from '@kbn/core-doc-links-browser-mocks'; import { executionContextServiceMock } from '@kbn/core-execution-context-browser-mocks'; -import { notificationServiceMock, applicationServiceMock } from '@kbn/core/public/mocks'; +import { notificationServiceMock, applicationServiceMock, coreMock } from '@kbn/core/public/mocks'; import { GlobalFlyout } from '@kbn/es-ui-shared-plugin/public'; import { AppContextProvider } from '../../../../../app_context'; @@ -27,7 +27,8 @@ const appDependencies = { docLinks: {} as any, } as any; -export const componentTemplatesDependencies = (httpSetup: HttpSetup) => ({ +export const componentTemplatesDependencies = (httpSetup: HttpSetup, coreStart?: CoreStart) => ({ + overlays: coreStart?.overlays ?? coreMock.createStart().overlays, httpClient: httpSetup, apiBasePath: API_BASE_PATH, trackMetric: () => {}, @@ -40,16 +41,17 @@ export const componentTemplatesDependencies = (httpSetup: HttpSetup) => ({ export const setupEnvironment = initHttpRequests; -export const WithAppDependencies = (Comp: any, httpSetup: HttpSetup) => (props: any) => - ( - - - - - - - - - / - - ); +export const WithAppDependencies = + (Comp: any, httpSetup: HttpSetup, coreStart?: CoreStart) => (props: any) => + ( + + + + + + + + + / + + ); diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_edit/component_template_edit.tsx b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_edit/component_template_edit.tsx index a3b9f0a38354b..99c8464e4a468 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_edit/component_template_edit.tsx +++ b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_edit/component_template_edit.tsx @@ -8,6 +8,7 @@ import React, { useState, useEffect, useMemo, useCallback } from 'react'; import { RouteComponentProps } from 'react-router-dom'; import { FormattedMessage } from '@kbn/i18n-react'; +import { toMountPoint } from '@kbn/kibana-react-plugin/public'; import { EuiPageContentBody, EuiPageHeader, EuiSpacer } from '@elastic/eui'; import { History } from 'history'; @@ -22,6 +23,9 @@ import { import { ComponentTemplateForm } from '../component_template_form'; import type { WizardSection } from '../component_template_form'; import { useRedirectPath } from '../../../../hooks/redirect_path'; +import { MANAGED_BY_FLEET } from '../../constants'; + +import { MappingsDatastreamRolloverModal } from './mappings_datastreams_rollover_modal'; interface MatchParams { name: string; @@ -57,7 +61,7 @@ export const ComponentTemplateEdit: React.FunctionComponent { - const { api, breadcrumbs } = useComponentTemplatesContext(); + const { api, breadcrumbs, overlays } = useComponentTemplatesContext(); const { activeStep: defaultActiveStep, updateStep } = useStepFromQueryString(history); const redirectTo = useRedirectPath(history); @@ -67,6 +71,8 @@ export const ComponentTemplateEdit: React.FunctionComponent dataStreamResponse?.data_streams ?? [], [dataStreamResponse]); useEffect(() => { breadcrumbs.setEditBreadcrumbs(); @@ -85,6 +91,38 @@ export const ComponentTemplateEdit: React.FunctionComponent { + ref.close(); + }} + /> + ) + ); + + await ref.onClose; + } + } redirectTo({ pathname: encodeURI( `/component_templates/${encodeURIComponent(updatedComponentTemplate.name)}` @@ -141,6 +179,7 @@ export const ComponentTemplateEdit: React.FunctionComponent void; + api: ReturnType['api']; +} + +export const MappingsDatastreamRolloverModal: React.FunctionComponent = ({ + componentTemplatename, + dataStreams, + onClose, + api, +}) => { + const [error, setError] = useState(); + const [isLoading, setIsLoading] = useState(false); + + const onConfirm = useCallback(() => { + async function confirm() { + try { + setIsLoading(true); + for (const dataStream of dataStreams) { + await api.postDataStreamRollover(dataStream); + } + await onClose(); + } catch (err) { + setError(err); + } finally { + setIsLoading(false); + } + } + + confirm(); + }, [api, onClose, dataStreams]); + + return ( + + } + onCancel={onClose} + onConfirm={onConfirm} + cancelButtonText={ + + } + confirmButtonText={ + + } + > + {error && ( + <> + + } + color="danger" + iconType="alert" + data-test-subj="applyMappingsRolloverError" + > +
    {error.message}
    +
    + + + )} + + {componentTemplatename}, + moreInfoLink: ( + + + + ), + datastreams: ( + <> + +
      + {dataStreams.map((dataStream) => ( +
    • + {dataStream} +
    • + ))} +
    + + + ), + }} + /> +
    +
    + ); +}; diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/component_template_form.tsx b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/component_template_form.tsx index 0d846d4b41740..ae12800719f96 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/component_template_form.tsx +++ b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/component_template_form.tsx @@ -40,6 +40,7 @@ interface Props { isEditing?: boolean; defaultActiveWizardSection?: WizardSection; onStepChange?: (stepId: string) => void; + dataStreams?: string[]; } const wizardSections: { [id: string]: { id: WizardSection; label: string } } = { @@ -85,6 +86,7 @@ export const ComponentTemplateForm = ({ isManaged: false, }, }, + dataStreams, isEditing, isSaving, saveError, @@ -243,6 +245,7 @@ export const ComponentTemplateForm = ({ diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review.tsx b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review.tsx index 3243ef5d865b8..da25af901020a 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review.tsx +++ b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review.tsx @@ -18,6 +18,7 @@ import { EuiDescriptionListDescription, EuiText, EuiCodeBlock, + EuiCode, } from '@elastic/eui'; import { FormattedMessage } from '@kbn/i18n-react'; @@ -26,6 +27,7 @@ import { serializers, serializeComponentTemplate, } from '../../../shared_imports'; +import { MANAGED_BY_FLEET } from '../../../constants'; const { stripEmptyFields } = serializers; @@ -47,164 +49,208 @@ const getDescriptionText = (data: any) => { interface Props { componentTemplate: ComponentTemplateDeserialized; + dataStreams?: string[]; } -export const StepReview: React.FunctionComponent = React.memo(({ componentTemplate }) => { - const { name } = componentTemplate; +export const StepReview: React.FunctionComponent = React.memo( + ({ dataStreams, componentTemplate }) => { + const { name } = componentTemplate; - const serializedComponentTemplate = serializeComponentTemplate( - stripEmptyFields(componentTemplate, { - types: ['string'], - }) as ComponentTemplateDeserialized - ); + const serializedComponentTemplate = serializeComponentTemplate( + stripEmptyFields(componentTemplate, { + types: ['string'], + }) as ComponentTemplateDeserialized + ); - const { - template: serializedTemplate, - _meta: serializedMeta, - version: serializedVersion, - } = serializedComponentTemplate; - - const SummaryTab = () => ( -
    - - - - - - {/* Version */} - {typeof serializedVersion !== 'undefined' && ( - <> - - - - {serializedVersion} - - )} + const { + template: serializedTemplate, + _meta: serializedMeta, + version: serializedVersion, + } = serializedComponentTemplate; - {/* Index settings */} - - - - - {getDescriptionText(serializedTemplate?.settings)} - + const isFleetDatastreamsVisible = + dataStreams?.length && componentTemplate._meta?.managed_by === MANAGED_BY_FLEET; - {/* Mappings */} - - - - - {getDescriptionText(serializedTemplate?.mappings)} - + const SummaryTab = () => ( +
    + - {/* Aliases */} - - - - - {getDescriptionText(serializedTemplate?.aliases)} - - - - - - {/* Metadata */} - {serializedMeta && ( + + + {/* Version */} + {typeof serializedVersion !== 'undefined' && ( + <> + + + + {serializedVersion} + + )} + + {/* Index settings */} - - {JSON.stringify(serializedMeta, null, 2)} - + {getDescriptionText(serializedTemplate?.settings)} + + + {/* Mappings */} + + + + + {getDescriptionText(serializedTemplate?.mappings)} + + + {/* Aliases */} + + + + + {getDescriptionText(serializedTemplate?.aliases)} + + {isFleetDatastreamsVisible && ( + + {/* Datastream mappings */} + + + +
      + {dataStreams.map((dataStream) => ( +
    • + {dataStream} +
    • + ))} +
    +
    +
    )} -
    - -
    - ); + + {/* Metadata */} + {serializedMeta && ( + + + + + + + {JSON.stringify(serializedMeta, null, 2)} + + + + )} + +
    +
    + ); - const RequestTab = () => { - const endpoint = `PUT _component_template/${name || ''}`; - const templateString = JSON.stringify(serializedComponentTemplate, null, 2); - const request = `${endpoint}\n${templateString}`; + const RequestTab = () => { + const endpoint = `PUT _component_template/${name || ''}`; + const templateString = JSON.stringify(serializedComponentTemplate, null, 2); + const request = `${endpoint}\n${templateString}`; - // Beyond a certain point, highlighting the syntax will bog down performance to unacceptable - // levels. This way we prevent that happening for very large requests. - const language = request.length < 60000 ? 'json' : undefined; + // Beyond a certain point, highlighting the syntax will bog down performance to unacceptable + // levels. This way we prevent that happening for very large requests. + const language = request.length < 60000 ? 'json' : undefined; - return ( -
    - + return ( +
    + + + +

    + +

    +
    - -

    + + + + {request} + + + {isFleetDatastreamsVisible && ( + <> + + +

    + +

    +
    + + )} +
    + ); + }; + + return ( +
    + +

    -

    - +

    +
    - + - - {request} - + , + }, + { + id: 'request', + name: i18n.translate( + 'xpack.idxMgmt.componentTemplateForm.stepReview.requestTabTitle', + { + defaultMessage: 'Request', + } + ), + content: , + }, + ]} + />
    ); - }; - - return ( -
    - -

    - -

    -
    - - - - , - }, - { - id: 'request', - name: i18n.translate('xpack.idxMgmt.componentTemplateForm.stepReview.requestTabTitle', { - defaultMessage: 'Request', - }), - content: , - }, - ]} - /> -
    - ); -}); + } +); diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review_container.tsx b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review_container.tsx index aee8b25d64ed1..b2f2fbd0d57fd 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review_container.tsx +++ b/x-pack/plugins/index_management/public/application/components/component_templates/component_template_wizard/component_template_form/steps/step_review_container.tsx @@ -13,14 +13,17 @@ import { StepReview } from './step_review'; interface Props { getComponentTemplateData: (wizardContent: WizardContent) => ComponentTemplateDeserialized; + dataStreams?: string[]; } -export const StepReviewContainer = React.memo(({ getComponentTemplateData }: Props) => { - const { getData } = Forms.useMultiContentContext(); +export const StepReviewContainer = React.memo( + ({ getComponentTemplateData, dataStreams }: Props) => { + const { getData } = Forms.useMultiContentContext(); - const wizardContent = getData(); - // Build the final template object, providing the wizard content data - const componentTemplate = getComponentTemplateData(wizardContent); + const wizardContent = getData(); + // Build the final template object, providing the wizard content data + const componentTemplate = getComponentTemplateData(wizardContent); - return ; -}); + return ; + } +); diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/component_templates_context.tsx b/x-pack/plugins/index_management/public/application/components/component_templates/component_templates_context.tsx index e67d5fe122a34..3f9380bf8e72d 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/component_templates_context.tsx +++ b/x-pack/plugins/index_management/public/application/components/component_templates/component_templates_context.tsx @@ -29,6 +29,7 @@ interface Props { setBreadcrumbs: ManagementAppMountParams['setBreadcrumbs']; getUrlForApp: CoreStart['application']['getUrlForApp']; executionContext: ExecutionContextStart; + overlays: CoreStart['overlays']; } interface Context { @@ -39,6 +40,7 @@ interface Context { breadcrumbs: ReturnType; trackMetric: (type: UiCounterMetricType, eventName: string) => void; toasts: NotificationsSetup['toasts']; + overlays: CoreStart['overlays']; getUrlForApp: CoreStart['application']['getUrlForApp']; executionContext: ExecutionContextStart; } @@ -51,6 +53,7 @@ export const ComponentTemplatesProvider = ({ children: React.ReactNode; }) => { const { + overlays, httpClient, apiBasePath, trackMetric, @@ -71,6 +74,7 @@ export const ComponentTemplatesProvider = ({ return ( ({ + path: `${apiBasePath}/component_templates/${encodeURIComponent(name)}/datastreams`, + method: 'get', + }); + } + function deleteComponentTemplates(names: string[]) { const result = sendRequest({ path: `${apiBasePath}/component_templates/${names @@ -79,11 +88,36 @@ export const getApi = ( return result; } + async function getComponentTemplateDatastreams(name: string) { + return sendRequest({ + path: `${apiBasePath}/component_templates/${encodeURIComponent(name)}/datastreams`, + method: 'get', + }); + } + + async function postDataStreamRollover(name: string) { + return sendRequest({ + path: `${apiBasePath}/data_streams/${encodeURIComponent(name)}/rollover`, + method: 'post', + }); + } + + async function postDataStreamMappingsFromTemplate(name: string) { + return sendRequest({ + path: `${apiBasePath}/data_streams/${encodeURIComponent(name)}/mappings_from_template`, + method: 'post', + }); + } + return { useLoadComponentTemplates, deleteComponentTemplates, useLoadComponentTemplate, createComponentTemplate, updateComponentTemplate, + useLoadComponentTemplatesDatastream, + getComponentTemplateDatastreams, + postDataStreamRollover, + postDataStreamMappingsFromTemplate, }; }; diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/lib/request.ts b/x-pack/plugins/index_management/public/application/components/component_templates/lib/request.ts index 7bb4b90da2fed..62809d61e9a24 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/lib/request.ts +++ b/x-pack/plugins/index_management/public/application/components/component_templates/lib/request.ts @@ -20,7 +20,9 @@ import { export type UseRequestHook = ( config: UseRequestConfig ) => UseRequestResponse; -export type SendRequestHook = (config: SendRequestConfig) => Promise; +export type SendRequestHook = ( + config: SendRequestConfig +) => Promise>; export const getUseRequest = (httpClient: HttpSetup): UseRequestHook => diff --git a/x-pack/plugins/index_management/public/application/components/component_templates/shared_imports.ts b/x-pack/plugins/index_management/public/application/components/component_templates/shared_imports.ts index 64ee7a16ef2fb..78dd0395b6e34 100644 --- a/x-pack/plugins/index_management/public/application/components/component_templates/shared_imports.ts +++ b/x-pack/plugins/index_management/public/application/components/component_templates/shared_imports.ts @@ -65,6 +65,7 @@ export type { ComponentTemplateSerialized, ComponentTemplateDeserialized, ComponentTemplateListItem, + ComponentTemplateDatastreams, } from '../../../../common'; export { serializeComponentTemplate } from '../../../../common/lib'; diff --git a/x-pack/plugins/index_management/public/application/index.tsx b/x-pack/plugins/index_management/public/application/index.tsx index ad0779e88c392..d3c97c3fe3d3f 100644 --- a/x-pack/plugins/index_management/public/application/index.tsx +++ b/x-pack/plugins/index_management/public/application/index.tsx @@ -35,7 +35,7 @@ export const renderApp = ( return () => undefined; } - const { i18n, docLinks, notifications, application, executionContext } = core; + const { i18n, docLinks, notifications, application, executionContext, overlays } = core; const { Context: I18nContext } = i18n; const { services, history, setBreadcrumbs, uiSettings, kibanaVersion, theme$ } = dependencies; @@ -51,6 +51,7 @@ export const renderApp = ( const componentTemplateProviderValues = { httpClient: services.httpService.httpClient, + overlays, apiBasePath: API_BASE_PATH, trackMetric: services.uiMetricService.trackMetric.bind(services.uiMetricService), docLinks, diff --git a/x-pack/plugins/index_management/server/routes/api/component_templates/index.ts b/x-pack/plugins/index_management/server/routes/api/component_templates/index.ts index fdc72893c7b7f..9a3e22068a7f3 100644 --- a/x-pack/plugins/index_management/server/routes/api/component_templates/index.ts +++ b/x-pack/plugins/index_management/server/routes/api/component_templates/index.ts @@ -12,11 +12,13 @@ import { registerCreateRoute } from './register_create_route'; import { registerUpdateRoute } from './register_update_route'; import { registerDeleteRoute } from './register_delete_route'; import { registerPrivilegesRoute } from './register_privileges_route'; +import { registerGetDatastreams } from './register_datastream_route'; export function registerComponentTemplateRoutes(dependencies: RouteDependencies) { registerGetAllRoute(dependencies); registerCreateRoute(dependencies); registerUpdateRoute(dependencies); + registerGetDatastreams(dependencies); registerDeleteRoute(dependencies); registerPrivilegesRoute(dependencies); } diff --git a/x-pack/plugins/index_management/server/routes/api/component_templates/register_datastream_route.ts b/x-pack/plugins/index_management/server/routes/api/component_templates/register_datastream_route.ts new file mode 100644 index 0000000000000..b117f7b8f9ba4 --- /dev/null +++ b/x-pack/plugins/index_management/server/routes/api/component_templates/register_datastream_route.ts @@ -0,0 +1,78 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { ElasticsearchClient } from '@kbn/core/server'; +import { schema } from '@kbn/config-schema'; +import type { IndicesDataStream } from '@elastic/elasticsearch/lib/api/types'; + +import { RouteDependencies } from '../../../types'; +import { addBasePath } from '..'; + +const paramsSchema = schema.object({ + name: schema.string(), +}); + +async function getDatastreamsForComponentTemplate( + esClient: ElasticsearchClient, + name: string +): Promise { + const { component_templates: componentTemplates } = await esClient.cluster.getComponentTemplate({ + name, + }); + + if (!componentTemplates.find((componentTemplate) => componentTemplate.name === name)) { + return []; + } + + const { index_templates: indexTemplates } = await esClient.indices.getIndexTemplate(); + + const datastreamNames = indexTemplates + .filter((indexTemplate) => indexTemplate.index_template.composed_of.includes(name)) + .map((indexTemplate) => indexTemplate.index_template.index_patterns) + .flat() + .join(','); + + if (datastreamNames.length < 0) { + return []; + } + const { data_streams: dataStreams } = await esClient.indices.getDataStream({ + name: datastreamNames, + }); + + return dataStreams; +} + +export const registerGetDatastreams = ({ + router, + lib: { handleEsError }, +}: RouteDependencies): void => { + router.get( + { + path: addBasePath('/component_templates/{name}/datastreams'), + validate: { + params: paramsSchema, + }, + }, + async (context, request, response) => { + const { client } = (await context.core).elasticsearch; + + const { name } = request.params; + + try { + const dataStreams = await getDatastreamsForComponentTemplate(client.asCurrentUser, name); + + return response.ok({ + body: { + data_streams: dataStreams.map((ds) => ds.name), + }, + }); + } catch (error) { + return handleEsError({ error, response }); + } + } + ); +}; diff --git a/x-pack/plugins/index_management/server/routes/api/data_streams/index.ts b/x-pack/plugins/index_management/server/routes/api/data_streams/index.ts index 8c241cdf4885d..39238c410489d 100644 --- a/x-pack/plugins/index_management/server/routes/api/data_streams/index.ts +++ b/x-pack/plugins/index_management/server/routes/api/data_streams/index.ts @@ -9,9 +9,12 @@ import { RouteDependencies } from '../../../types'; import { registerGetOneRoute, registerGetAllRoute } from './register_get_route'; import { registerDeleteRoute } from './register_delete_route'; +import { registerPostOneApplyLatestMappings, registerPostOneRollover } from './register_post_route'; export function registerDataStreamRoutes(dependencies: RouteDependencies) { registerGetOneRoute(dependencies); + registerPostOneApplyLatestMappings(dependencies); + registerPostOneRollover(dependencies); registerGetAllRoute(dependencies); registerDeleteRoute(dependencies); } diff --git a/x-pack/plugins/index_management/server/routes/api/data_streams/register_post_route.ts b/x-pack/plugins/index_management/server/routes/api/data_streams/register_post_route.ts new file mode 100644 index 0000000000000..8e2a5a3790986 --- /dev/null +++ b/x-pack/plugins/index_management/server/routes/api/data_streams/register_post_route.ts @@ -0,0 +1,104 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { schema, TypeOf } from '@kbn/config-schema'; + +import { IScopedClusterClient } from '@kbn/core/server'; +import { RouteDependencies } from '../../../types'; +import { addBasePath } from '..'; + +const getDataStreams = (client: IScopedClusterClient, name = '*') => { + return client.asCurrentUser.indices.getDataStream({ + name, + expand_wildcards: 'all', + }); +}; + +export function registerPostOneApplyLatestMappings({ + router, + lib: { handleEsError }, + config, +}: RouteDependencies) { + const paramsSchema = schema.object({ + name: schema.string(), + }); + router.post( + { + path: addBasePath('/data_streams/{name}/mappings_from_template'), + validate: { params: paramsSchema }, + }, + async (context, request, response) => { + const { name } = request.params as TypeOf; + const { client } = (await context.core).elasticsearch; + try { + const { data_streams: dataStreams } = await getDataStreams(client, name); + // The API is meant to be used only for applying the mapping to one specific datastream + if (dataStreams[0]) { + const { template } = dataStreams[0]; + const simulateResult = await client.asCurrentUser.indices.simulateTemplate({ + name: template, + }); + + const mappings = simulateResult.template.mappings; + // for now, remove from object so as not to update stream or data stream properties of the index until type and name + // are added in https://github.com/elastic/kibana/issues/66551. namespace value we will continue + // to skip updating and assume the value in the index mapping is correct + if (mappings && mappings.properties) { + delete mappings.properties.stream; + delete mappings.properties.data_stream; + } + await client.asCurrentUser.indices.putMapping({ + index: name, + body: mappings || {}, + write_index_only: true, + }); + + return response.ok({ body: { success: true } }); + } + + return response.notFound(); + } catch (error) { + return handleEsError({ error, response }); + } + } + ); +} + +export function registerPostOneRollover({ + router, + lib: { handleEsError }, + config, +}: RouteDependencies) { + const paramsSchema = schema.object({ + name: schema.string(), + }); + router.post( + { + path: addBasePath('/data_streams/{name}/rollover'), + validate: { params: paramsSchema }, + }, + async (context, request, response) => { + const { name } = request.params as TypeOf; + const { client } = (await context.core).elasticsearch; + try { + const { data_streams: dataStreams } = await getDataStreams(client, name); + // That API is mean to be used to rollover one specific datastream + if (dataStreams[0]) { + await client.asCurrentUser.indices.rollover({ + alias: name, + }); + + return response.ok({ body: { success: true } }); + } + + return response.notFound(); + } catch (error) { + return handleEsError({ error, response }); + } + } + ); +} diff --git a/x-pack/test/api_integration/apis/management/index_management/component_templates.ts b/x-pack/test/api_integration/apis/management/index_management/component_templates.ts index d9e7b0383144e..0065057d762f4 100644 --- a/x-pack/test/api_integration/apis/management/index_management/component_templates.ts +++ b/x-pack/test/api_integration/apis/management/index_management/component_templates.ts @@ -16,12 +16,21 @@ import { API_BASE_PATH } from './constants'; export default function ({ getService }: FtrProviderContext) { const supertest = getService('supertest'); - const { createComponentTemplate, cleanUpComponentTemplates, deleteComponentTemplate } = - initElasticsearchHelpers(getService); + const { + createComponentTemplate, + createIndexTemplate, + cleanUpIndexTemplates, + cleanUpComponentTemplates, + deleteComponentTemplate, + cleanupDatastreams, + createDatastream, + } = initElasticsearchHelpers(getService); describe('Component templates', function () { after(async () => { + await cleanUpIndexTemplates(); await cleanUpComponentTemplates(); + await cleanupDatastreams(); }); describe('Get', () => { @@ -391,5 +400,74 @@ export default function ({ getService }: FtrProviderContext) { }); }); }); + + describe('Get datastreams', () => { + const COMPONENT_NAME = 'test_get_component_template_datastreams'; + const COMPONENT = { + template: { + settings: { + index: { + number_of_shards: 1, + }, + }, + mappings: { + _source: { + enabled: false, + }, + properties: { + host_name: { + type: 'keyword', + }, + created_at: { + type: 'date', + format: 'EEE MMM dd HH:mm:ss Z yyyy', + }, + }, + }, + }, + }; + const DATASTREAM_NAME = 'logs-test-component-template-default'; + const INDEX_PATTERN = 'logs-test-component-template-*'; + const TEMPLATE_NAME = 'test_get_component_template_datastreams'; + const TEMPLATE = { + index_patterns: INDEX_PATTERN, + composed_of: [COMPONENT_NAME], + }; + + // Create component template to verify GET requests + before(async () => { + try { + await createComponentTemplate({ body: COMPONENT, name: COMPONENT_NAME }, true); + await createIndexTemplate({ body: TEMPLATE, name: TEMPLATE_NAME }, true); + } catch (err) { + // eslint-disable-next-line no-console + console.log('[Setup error] Error creating component template'); + throw err; + } + }); + + describe('without datastreams', () => { + it('should return no datastreams', async () => { + const uri = `${API_BASE_PATH}/component_templates/${COMPONENT_NAME}/datastreams`; + + const { body } = await supertest.get(uri).set('kbn-xsrf', 'xxx').expect(200); + + expect(body).to.eql({ data_streams: [] }); + }); + }); + + describe('with datastreams', () => { + before(async () => { + await createDatastream(DATASTREAM_NAME); + }); + it('should return datastreams', async () => { + const uri = `${API_BASE_PATH}/component_templates/${COMPONENT_NAME}/datastreams`; + + const { body } = await supertest.get(uri).set('kbn-xsrf', 'xxx').expect(200); + + expect(body).to.eql({ data_streams: ['logs-test-component-template-default'] }); + }); + }); + }); }); } diff --git a/x-pack/test/api_integration/apis/management/index_management/data_streams.ts b/x-pack/test/api_integration/apis/management/index_management/data_streams.ts index cd3c63ab96f4a..0117204343285 100644 --- a/x-pack/test/api_integration/apis/management/index_management/data_streams.ts +++ b/x-pack/test/api_integration/apis/management/index_management/data_streams.ts @@ -39,6 +39,33 @@ export default function ({ getService }: FtrProviderContext) { await es.indices.createDataStream({ name }); }; + const updateIndexTemplateMappings = async (name: string, mappings: any) => { + await es.indices.putIndexTemplate({ + name, + body: { + // We need to match the names of backing indices with this template. + index_patterns: [name + '*'], + template: { + mappings, + }, + data_stream: {}, + }, + }); + }; + + const getDatastream = async (name: string) => { + const { + data_streams: [datastream], + } = await es.indices.getDataStream({ name }); + return datastream; + }; + + const getMapping = async (name: string) => { + const res = await es.indices.getMapping({ index: name }); + + return Object.values(res)[0]!.mappings; + }; + const deleteComposableIndexTemplate = async (name: string) => { await es.indices.deleteIndexTemplate({ name }); }; @@ -214,5 +241,62 @@ export default function ({ getService }: FtrProviderContext) { .expect(404); }); }); + + describe('Mappings from template', () => { + const testDataStreamName1 = 'test-data-stream-mappings-1'; + + before(async () => { + await createDataStream(testDataStreamName1); + }); + + after(async () => { + await deleteDataStream(testDataStreamName1); + }); + + it('Apply mapping from index template', async () => { + const beforeMapping = await getMapping(testDataStreamName1); + expect(beforeMapping.properties).eql({ + '@timestamp': { type: 'date' }, + }); + await updateIndexTemplateMappings(testDataStreamName1, { + properties: { + test: { type: 'integer' }, + }, + }); + await supertest + .post(`${API_BASE_PATH}/data_streams/${testDataStreamName1}/mappings_from_template`) + .set('kbn-xsrf', 'xxx') + .expect(200); + + const afterMapping = await getMapping(testDataStreamName1); + expect(afterMapping.properties).eql({ + '@timestamp': { type: 'date' }, + test: { type: 'integer' }, + }); + }); + }); + + describe('Rollover', () => { + const testDataStreamName1 = 'test-data-stream-rollover-1'; + + before(async () => { + await createDataStream(testDataStreamName1); + }); + + after(async () => { + await deleteDataStream(testDataStreamName1); + }); + + it('Rollover datastreams', async () => { + await supertest + .post(`${API_BASE_PATH}/data_streams/${testDataStreamName1}/rollover`) + .set('kbn-xsrf', 'xxx') + .expect(200); + + const datastream = await getDatastream(testDataStreamName1); + + expect(datastream.generation).equal(2); + }); + }); }); } diff --git a/x-pack/test/api_integration/apis/management/index_management/lib/elasticsearch.js b/x-pack/test/api_integration/apis/management/index_management/lib/elasticsearch.js index 9c67f493a7ca3..d71085439e868 100644 --- a/x-pack/test/api_integration/apis/management/index_management/lib/elasticsearch.js +++ b/x-pack/test/api_integration/apis/management/index_management/lib/elasticsearch.js @@ -17,8 +17,29 @@ export const initElasticsearchHelpers = (getService) => { const esDeleteAllIndices = getService('esDeleteAllIndices'); let indicesCreated = []; + let datastreamCreated = []; + let indexTemplatesCreated = []; let componentTemplatesCreated = []; + const createDatastream = (datastream) => { + datastreamCreated.push(datastream); + return es.indices.createDataStream({ name: datastream }); + }; + + const deleteDatastream = (datastream) => { + return es.indices.deleteDataStream({ name: datastream }); + }; + + const cleanupDatastreams = () => + Promise.all(datastreamCreated.map(deleteDatastream)) + .then(() => { + datastreamCreated = []; + }) + .catch((err) => { + // eslint-disable-next-line no-console + console.log(`[Cleanup error] Error deleting ES resources: ${err.message}`); + }); + const createIndex = (index = getRandomString(), body) => { indicesCreated.push(index); return es.indices.create({ index, body }).then(() => index); @@ -37,6 +58,18 @@ export const initElasticsearchHelpers = (getService) => { const catTemplate = (name) => es.cat.templates({ name, format: 'json' }, { meta: true }); + const createIndexTemplate = (indexTemplate, shouldCacheTemplate) => { + if (shouldCacheTemplate) { + indexTemplatesCreated.push(indexTemplate.name); + } + + return es.indices.putIndexTemplate(indexTemplate, { meta: true }); + }; + + const deleteIndexTemplate = (indexTemplateName) => { + return es.indices.deleteIndexTemplate({ name: indexTemplateName }, { meta: true }); + }; + const createComponentTemplate = (componentTemplate, shouldCacheTemplate) => { if (shouldCacheTemplate) { componentTemplatesCreated.push(componentTemplate.name); @@ -59,13 +92,29 @@ export const initElasticsearchHelpers = (getService) => { console.log(`[Cleanup error] Error deleting ES resources: ${err.message}`); }); + const cleanUpIndexTemplates = () => + Promise.all(indexTemplatesCreated.map(deleteIndexTemplate)) + .then(() => { + indexTemplatesCreated = []; + }) + .catch((err) => { + // eslint-disable-next-line no-console + console.log(`[Cleanup error] Error deleting ES resources: ${err.message}`); + }); + return { createIndex, deleteAllIndices, catIndex, indexStats, + createDatastream, + deleteDatastream, + cleanupDatastreams, cleanUp, catTemplate, + createIndexTemplate, + deleteIndexTemplate, + cleanUpIndexTemplates, createComponentTemplate, deleteComponentTemplate, cleanUpComponentTemplates, From fd6224df54144f1abec2e1bd6f066177d522bf0b Mon Sep 17 00:00:00 2001 From: Maryam Saeidi Date: Mon, 18 Jul 2022 17:08:04 +0200 Subject: [PATCH 095/111] [Actionable Observability] Add actionable-observability as owner of rule_details page (#136522) --- .github/CODEOWNERS | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 3fb8a5f2d1b8e..ba24eeb249155 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -106,6 +106,7 @@ /x-pack/plugins/observability/public/pages/alerts @elastic/actionable-observability /x-pack/plugins/observability/public/pages/cases @elastic/actionable-observability /x-pack/plugins/observability/public/pages/rules @elastic/actionable-observability +/x-pack/plugins/observability/public/pages/rule_details @elastic/actionable-observability # Infra Monitoring /x-pack/plugins/infra/ @elastic/infra-monitoring-ui From da4c898b673da0036b584b64290b80fcff60e8db Mon Sep 17 00:00:00 2001 From: Abdon Pijpelink Date: Mon, 18 Jul 2022 17:08:21 +0200 Subject: [PATCH 096/111] Removed anchor from link to common cluster issues page (#136378) Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- docs/setup/upgrade/resolving-migration-failures.asciidoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/setup/upgrade/resolving-migration-failures.asciidoc b/docs/setup/upgrade/resolving-migration-failures.asciidoc index 85847b15cb084..0af9fafa36d77 100644 --- a/docs/setup/upgrade/resolving-migration-failures.asciidoc +++ b/docs/setup/upgrade/resolving-migration-failures.asciidoc @@ -177,7 +177,7 @@ If the cluster exceeded the low watermark for disk usage, the output should cont -------------------------------------------- "The node is above the low watermark cluster setting [cluster.routing.allocation.disk.watermark.low=85%], using more disk space than the maximum allowed [85.0%], actual free: [11.692661332965082%]" -------------------------------------------- -Refer to the {es} guide for how to {ref}/fix-common-cluster-issues.html#_error_disk_usage_exceeded_flood_stage_watermark_index_has_read_only_allow_delete_block[fix common cluster issues]. +Refer to the {es} guide for how to {ref}/fix-common-cluster-issues.html[fix common cluster issues]. If routing allocation is the issue, the `_cluster/allocation/explain` API will return an entry similar to this: From b49eda607e74879e2fc5d61f01419d5807fc2fa3 Mon Sep 17 00:00:00 2001 From: Jonathan Buttner <56361221+jonathan-buttner@users.noreply.github.com> Date: Mon, 18 Jul 2022 11:11:16 -0400 Subject: [PATCH 097/111] [ResponseOps][Cases] Reduce index refreshes (#136452) * Adding refresh options * Fixing test --- .../cases/server/client/attachments/delete.ts | 2 + .../cases/server/client/cases/create.ts | 1 + .../cases/server/client/cases/delete.ts | 2 + .../plugins/cases/server/client/cases/push.ts | 3 + .../cases/server/client/cases/update.ts | 1 + .../cases/server/client/configure/client.ts | 9 +- .../client/configure/create_mappings.ts | 3 +- .../cases/server/client/configure/types.ts | 5 +- .../client/configure/update_mappings.ts | 3 +- .../common/models/case_with_comments.ts | 20 +- .../server/services/attachments/index.ts | 29 +- .../cases/server/services/cases/index.test.ts | 1 + .../cases/server/services/cases/index.ts | 29 +- .../server/services/configure/index.test.ts | 2 + .../cases/server/services/configure/index.ts | 25 +- .../services/connector_mappings/index.ts | 9 +- x-pack/plugins/cases/server/services/types.ts | 14 + .../services/user_actions/index.test.ts | 445 +++++++++--------- .../server/services/user_actions/index.ts | 48 +- 19 files changed, 390 insertions(+), 261 deletions(-) create mode 100644 x-pack/plugins/cases/server/services/types.ts diff --git a/x-pack/plugins/cases/server/client/attachments/delete.ts b/x-pack/plugins/cases/server/client/attachments/delete.ts index 68852dd1edea8..f22a7d5ce3c79 100644 --- a/x-pack/plugins/cases/server/client/attachments/delete.ts +++ b/x-pack/plugins/cases/server/client/attachments/delete.ts @@ -79,6 +79,7 @@ export async function deleteAll( attachmentService.delete({ unsecuredSavedObjectsClient, attachmentId: comment.id, + refresh: false, }); // Ensuring we don't too many concurrent deletions running. @@ -149,6 +150,7 @@ export async function deleteComment( await attachmentService.delete({ unsecuredSavedObjectsClient, attachmentId: attachmentID, + refresh: false, }); await userActionService.createUserAction({ diff --git a/x-pack/plugins/cases/server/client/cases/create.ts b/x-pack/plugins/cases/server/client/cases/create.ts index 714c8199d11a5..1997977e98a32 100644 --- a/x-pack/plugins/cases/server/client/cases/create.ts +++ b/x-pack/plugins/cases/server/client/cases/create.ts @@ -79,6 +79,7 @@ export const create = async ( newCase: query, }), id: savedObjectID, + refresh: false, }); await userActionService.createUserAction({ diff --git a/x-pack/plugins/cases/server/client/cases/delete.ts b/x-pack/plugins/cases/server/client/cases/delete.ts index 3e3f70433a624..64fc7ef50078d 100644 --- a/x-pack/plugins/cases/server/client/cases/delete.ts +++ b/x-pack/plugins/cases/server/client/cases/delete.ts @@ -53,6 +53,7 @@ export async function deleteCases(ids: string[], clientArgs: CasesClientArgs): P const deleteCasesMapper = async (id: string) => caseService.deleteCase({ id, + refresh: false, }); // Ensuring we don't too many concurrent deletions running. @@ -81,6 +82,7 @@ export async function deleteCases(ids: string[], clientArgs: CasesClientArgs): P attachmentService.delete({ unsecuredSavedObjectsClient, attachmentId: comment.id, + refresh: false, }) ); diff --git a/x-pack/plugins/cases/server/client/cases/push.ts b/x-pack/plugins/cases/server/client/cases/push.ts index cfdec1da5e775..46e570db2dbe8 100644 --- a/x-pack/plugins/cases/server/client/cases/push.ts +++ b/x-pack/plugins/cases/server/client/cases/push.ts @@ -237,6 +237,7 @@ export const push = async ( updated_by: { username, full_name, email }, }, version: myCase.version, + refresh: false, }), attachmentService.bulkUpdate({ @@ -251,6 +252,7 @@ export const push = async ( }, version: comment.version, })), + refresh: false, }), ]); @@ -262,6 +264,7 @@ export const push = async ( user, caseId, owner: myCase.attributes.owner, + refresh: false, }); if (myCase.attributes.settings.syncAlerts) { diff --git a/x-pack/plugins/cases/server/client/cases/update.ts b/x-pack/plugins/cases/server/client/cases/update.ts index 6569dcd3f52b2..8678846db8bee 100644 --- a/x-pack/plugins/cases/server/client/cases/update.ts +++ b/x-pack/plugins/cases/server/client/cases/update.ts @@ -339,6 +339,7 @@ export const update = async ( version, }; }), + refresh: false, }); // If a status update occurred and the case is synced then we need to update all alerts' status diff --git a/x-pack/plugins/cases/server/client/configure/client.ts b/x-pack/plugins/cases/server/client/configure/client.ts index 9bb6b83316264..735317f312a39 100644 --- a/x-pack/plugins/cases/server/client/configure/client.ts +++ b/x-pack/plugins/cases/server/client/configure/client.ts @@ -289,11 +289,13 @@ async function update( mappings = await casesClientInternal.configuration.updateMappings({ connector, mappingId: resMappings[0].id, + refresh: false, }); } else { mappings = await casesClientInternal.configuration.createMappings({ connector, owner: configuration.attributes.owner, + refresh: false, }); } } @@ -375,7 +377,11 @@ async function create( if (myCaseConfigure.saved_objects.length > 0) { const deleteConfigurationMapper = async (c: SavedObject) => - caseConfigureService.delete({ unsecuredSavedObjectsClient, configurationId: c.id }); + caseConfigureService.delete({ + unsecuredSavedObjectsClient, + configurationId: c.id, + refresh: false, + }); // Ensuring we don't too many concurrent deletions running. await pMap(myCaseConfigure.saved_objects, deleteConfigurationMapper, { @@ -397,6 +403,7 @@ async function create( mappings = await casesClientInternal.configuration.createMappings({ connector: configuration.connector, owner: configuration.owner, + refresh: false, }); } catch (e) { error = e.isBoom diff --git a/x-pack/plugins/cases/server/client/configure/create_mappings.ts b/x-pack/plugins/cases/server/client/configure/create_mappings.ts index 52f00453ef0ec..6067daaee5526 100644 --- a/x-pack/plugins/cases/server/client/configure/create_mappings.ts +++ b/x-pack/plugins/cases/server/client/configure/create_mappings.ts @@ -13,7 +13,7 @@ import { CreateMappingsArgs } from './types'; import { casesConnectors } from '../../connectors'; export const createMappings = async ( - { connector, owner }: CreateMappingsArgs, + { connector, owner, refresh }: CreateMappingsArgs, clientArgs: CasesClientArgs ): Promise => { const { unsecuredSavedObjectsClient, connectorMappingsService, logger } = clientArgs; @@ -34,6 +34,7 @@ export const createMappings = async ( id: connector.id, }, ], + refresh, }); return theMapping.attributes.mappings; diff --git a/x-pack/plugins/cases/server/client/configure/types.ts b/x-pack/plugins/cases/server/client/configure/types.ts index c7ac49c9e94aa..d425b7f67d908 100644 --- a/x-pack/plugins/cases/server/client/configure/types.ts +++ b/x-pack/plugins/cases/server/client/configure/types.ts @@ -6,15 +6,16 @@ */ import { CaseConnector } from '../../../common/api'; +import { IndexRefresh } from '../../services/types'; export interface MappingsArgs { connector: CaseConnector; } -export interface CreateMappingsArgs extends MappingsArgs { +export interface CreateMappingsArgs extends MappingsArgs, IndexRefresh { owner: string; } -export interface UpdateMappingsArgs extends MappingsArgs { +export interface UpdateMappingsArgs extends MappingsArgs, IndexRefresh { mappingId: string; } diff --git a/x-pack/plugins/cases/server/client/configure/update_mappings.ts b/x-pack/plugins/cases/server/client/configure/update_mappings.ts index 490ec69cc5a26..4068827d8eb00 100644 --- a/x-pack/plugins/cases/server/client/configure/update_mappings.ts +++ b/x-pack/plugins/cases/server/client/configure/update_mappings.ts @@ -13,7 +13,7 @@ import { UpdateMappingsArgs } from './types'; import { casesConnectors } from '../../connectors'; export const updateMappings = async ( - { connector, mappingId }: UpdateMappingsArgs, + { connector, mappingId, refresh }: UpdateMappingsArgs, clientArgs: CasesClientArgs ): Promise => { const { unsecuredSavedObjectsClient, connectorMappingsService, logger } = clientArgs; @@ -34,6 +34,7 @@ export const updateMappings = async ( id: connector.id, }, ], + refresh, }); return theMapping.attributes.mappings ?? []; diff --git a/x-pack/plugins/cases/server/common/models/case_with_comments.ts b/x-pack/plugins/cases/server/common/models/case_with_comments.ts index 2c6c600820429..3574ca707f729 100644 --- a/x-pack/plugins/cases/server/common/models/case_with_comments.ts +++ b/x-pack/plugins/cases/server/common/models/case_with_comments.ts @@ -32,6 +32,7 @@ import { MAX_DOCS_PER_PAGE, } from '../../../common/constants'; import { CasesClientArgs } from '../../client'; +import { RefreshSetting } from '../../services/types'; import { createCaseError } from '../error'; import { countAlertsForID, @@ -88,6 +89,7 @@ export class CaseCommentModel { const { id, version, ...queryRestAttributes } = updateRequest; const options: SavedObjectsUpdateOptions = { version, + refresh: false, }; if (queryRestAttributes.type === CommentType.user && queryRestAttributes?.comment) { @@ -115,7 +117,7 @@ export class CaseCommentModel { }, options, }), - this.updateCaseUserAndDate(updatedAt), + this.updateCaseUserAndDateSkipRefresh(updatedAt), ]); await commentableCase.createUpdateCommentUserAction(comment, updateRequest, owner); @@ -130,7 +132,14 @@ export class CaseCommentModel { } } - private async updateCaseUserAndDate(date: string): Promise { + private async updateCaseUserAndDateSkipRefresh(date: string) { + return this.updateCaseUserAndDate(date, false); + } + + private async updateCaseUserAndDate( + date: string, + refresh: RefreshSetting + ): Promise { try { const updatedCase = await this.params.caseService.patchCase({ originalCase: this.caseInfo, @@ -140,6 +149,7 @@ export class CaseCommentModel { updated_by: { ...this.params.user }, }, version: this.caseInfo.version, + refresh, }); return this.newObjectWithInfo({ @@ -209,8 +219,9 @@ export class CaseCommentModel { }), references, id, + refresh: false, }), - this.updateCaseUserAndDate(createdDate), + this.updateCaseUserAndDateSkipRefresh(createdDate), ]); await Promise.all([ @@ -411,8 +422,9 @@ export class CaseCommentModel { id, }; }), + refresh: false, }), - this.updateCaseUserAndDate(new Date().toISOString()), + this.updateCaseUserAndDateSkipRefresh(new Date().toISOString()), ]); const savedObjectsWithoutErrors = newlyCreatedAttachments.saved_objects.filter( diff --git a/x-pack/plugins/cases/server/services/attachments/index.ts b/x-pack/plugins/cases/server/services/attachments/index.ts index 1975f0c653011..aa055663d6e03 100644 --- a/x-pack/plugins/cases/server/services/attachments/index.ts +++ b/x-pack/plugins/cases/server/services/attachments/index.ts @@ -42,6 +42,7 @@ import { } from '../so_references'; import { SavedObjectFindOptionsKueryNode } from '../../common/types'; import { PersistableStateAttachmentTypeRegistry } from '../../attachment_framework/persistable_state_registry'; +import { IndexRefresh } from '../types'; interface AttachedToCaseArgs extends ClientArgs { caseId: string; @@ -64,13 +65,15 @@ interface GetAttachmentArgs extends ClientArgs { attachmentId: string; } -interface CreateAttachmentArgs extends ClientArgs { +interface DeleteAttachmentArgs extends GetAttachmentArgs, IndexRefresh {} + +interface CreateAttachmentArgs extends ClientArgs, IndexRefresh { attributes: AttachmentAttributes; references: SavedObjectReference[]; id: string; } -interface BulkCreateAttachments extends ClientArgs { +interface BulkCreateAttachments extends ClientArgs, IndexRefresh { attachments: Array<{ attributes: AttachmentAttributes; references: SavedObjectReference[]; @@ -86,7 +89,7 @@ interface UpdateArgs { export type UpdateAttachmentArgs = UpdateArgs & ClientArgs; -interface BulkUpdateAttachmentArgs extends ClientArgs { +interface BulkUpdateAttachmentArgs extends ClientArgs, IndexRefresh { comments: UpdateArgs[]; } @@ -256,10 +259,16 @@ export class AttachmentService { } } - public async delete({ unsecuredSavedObjectsClient, attachmentId }: GetAttachmentArgs) { + public async delete({ + unsecuredSavedObjectsClient, + attachmentId, + refresh, + }: DeleteAttachmentArgs) { try { this.log.debug(`Attempting to DELETE attachment ${attachmentId}`); - return await unsecuredSavedObjectsClient.delete(CASE_COMMENT_SAVED_OBJECT, attachmentId); + return await unsecuredSavedObjectsClient.delete(CASE_COMMENT_SAVED_OBJECT, attachmentId, { + refresh, + }); } catch (error) { this.log.error(`Error on DELETE attachment ${attachmentId}: ${error}`); throw error; @@ -271,6 +280,7 @@ export class AttachmentService { attributes, references, id, + refresh, }: CreateAttachmentArgs): Promise> { try { this.log.debug(`Attempting to POST a new comment`); @@ -288,6 +298,7 @@ export class AttachmentService { { references: extractedReferences, id, + refresh, } ); @@ -304,6 +315,7 @@ export class AttachmentService { public async bulkCreate({ unsecuredSavedObjectsClient, attachments, + refresh, }: BulkCreateAttachments): Promise> { try { this.log.debug(`Attempting to bulk create attachments`); @@ -322,7 +334,8 @@ export class AttachmentService { attributes: extractedAttributes, references: extractedReferences, }; - }) + }), + { refresh } ); return { @@ -390,6 +403,7 @@ export class AttachmentService { public async bulkUpdate({ unsecuredSavedObjectsClient, comments, + refresh, }: BulkUpdateAttachmentArgs): Promise> { try { this.log.debug( @@ -422,7 +436,8 @@ export class AttachmentService { */ references: shouldUpdateRefs ? extractedReferences : undefined, }; - }) + }), + { refresh } ); return { diff --git a/x-pack/plugins/cases/server/services/cases/index.test.ts b/x-pack/plugins/cases/server/services/cases/index.test.ts index 69b3773ef0fed..1088187c7b46b 100644 --- a/x-pack/plugins/cases/server/services/cases/index.test.ts +++ b/x-pack/plugins/cases/server/services/cases/index.test.ts @@ -554,6 +554,7 @@ describe('CasesService', () => { "type": "action", }, ], + "refresh": undefined, } `); }); diff --git a/x-pack/plugins/cases/server/services/cases/index.ts b/x-pack/plugins/cases/server/services/cases/index.ts index 6656ff3b14a50..5790f57e37b6b 100644 --- a/x-pack/plugins/cases/server/services/cases/index.ts +++ b/x-pack/plugins/cases/server/services/cases/index.ts @@ -55,6 +55,7 @@ import { ESCaseAttributes } from './types'; import { AttachmentService } from '../attachments'; import { AggregationBuilder, AggregationResponse } from '../../client/metrics/types'; import { createCaseError } from '../../common/error'; +import { IndexRefresh } from '../types'; interface GetCaseIdsByAlertIdArgs { alertId: string; @@ -70,6 +71,8 @@ interface GetCaseArgs { id: string; } +interface DeleteCaseArgs extends GetCaseArgs, IndexRefresh {} + interface GetCasesArgs { caseIds: string[]; } @@ -84,12 +87,12 @@ interface FindCaseCommentsArgs { options?: SavedObjectFindOptionsKueryNode; } -interface PostCaseArgs { +interface PostCaseArgs extends IndexRefresh { attributes: CaseAttributes; id: string; } -interface PatchCase { +interface PatchCase extends IndexRefresh { caseId: string; updatedAttributes: Partial; originalCase: SavedObject; @@ -97,8 +100,8 @@ interface PatchCase { } type PatchCaseArgs = PatchCase; -interface PatchCasesArgs { - cases: PatchCase[]; +interface PatchCasesArgs extends IndexRefresh { + cases: Array>; } interface GetUserArgs { @@ -297,10 +300,10 @@ export class CasesService { }, new Map()); } - public async deleteCase({ id: caseId }: GetCaseArgs) { + public async deleteCase({ id: caseId, refresh }: DeleteCaseArgs) { try { this.log.debug(`Attempting to DELETE case ${caseId}`); - return await this.unsecuredSavedObjectsClient.delete(CASE_SAVED_OBJECT, caseId); + return await this.unsecuredSavedObjectsClient.delete(CASE_SAVED_OBJECT, caseId, { refresh }); } catch (error) { this.log.error(`Error on DELETE case ${caseId}: ${error}`); throw error; @@ -564,14 +567,18 @@ export class CasesService { } } - public async postNewCase({ attributes, id }: PostCaseArgs): Promise> { + public async postNewCase({ + attributes, + id, + refresh, + }: PostCaseArgs): Promise> { try { this.log.debug(`Attempting to POST a new case`); const transformedAttributes = transformAttributesToESModel(attributes); const createdCase = await this.unsecuredSavedObjectsClient.create( CASE_SAVED_OBJECT, transformedAttributes.attributes, - { id, references: transformedAttributes.referenceHandler.build() } + { id, references: transformedAttributes.referenceHandler.build(), refresh } ); return transformSavedObjectToExternalModel(createdCase); } catch (error) { @@ -585,6 +592,7 @@ export class CasesService { updatedAttributes, originalCase, version, + refresh, }: PatchCaseArgs): Promise> { try { this.log.debug(`Attempting to UPDATE case ${caseId}`); @@ -597,6 +605,7 @@ export class CasesService { { version, references: transformedAttributes.referenceHandler.build(originalCase.references), + refresh, } ); @@ -609,6 +618,7 @@ export class CasesService { public async patchCases({ cases, + refresh, }: PatchCasesArgs): Promise> { try { this.log.debug(`Attempting to UPDATE case ${cases.map((c) => c.caseId).join(', ')}`); @@ -625,7 +635,8 @@ export class CasesService { }); const updatedCases = await this.unsecuredSavedObjectsClient.bulkUpdate( - bulkUpdate + bulkUpdate, + { refresh } ); return transformUpdateResponsesToExternalModels(updatedCases); } catch (error) { diff --git a/x-pack/plugins/cases/server/services/configure/index.test.ts b/x-pack/plugins/cases/server/services/configure/index.test.ts index dbe5a157994da..b967886b13be9 100644 --- a/x-pack/plugins/cases/server/services/configure/index.test.ts +++ b/x-pack/plugins/cases/server/services/configure/index.test.ts @@ -364,6 +364,7 @@ describe('CaseConfigureService', () => { expect(unsecuredSavedObjectsClient.update.mock.calls[0][3]).toMatchInlineSnapshot(` Object { "references": undefined, + "refresh": undefined, } `); }); @@ -469,6 +470,7 @@ describe('CaseConfigureService', () => { "type": "action", }, ], + "refresh": undefined, } `); }); diff --git a/x-pack/plugins/cases/server/services/configure/index.ts b/x-pack/plugins/cases/server/services/configure/index.ts index 2b8bc3c6b7cc8..4cd7f5ad7283f 100644 --- a/x-pack/plugins/cases/server/services/configure/index.ts +++ b/x-pack/plugins/cases/server/services/configure/index.ts @@ -25,6 +25,7 @@ import { } from '../transform'; import { ConnectorReferenceHandler } from '../connector_reference_handler'; import { ESCasesConfigureAttributes } from './types'; +import { IndexRefresh } from '../types'; interface ClientArgs { unsecuredSavedObjectsClient: SavedObjectsClientContract; @@ -33,16 +34,19 @@ interface ClientArgs { interface GetCaseConfigureArgs extends ClientArgs { configurationId: string; } + +interface DeleteCaseConfigureArgs extends GetCaseConfigureArgs, IndexRefresh {} + interface FindCaseConfigureArgs extends ClientArgs { options?: SavedObjectFindOptionsKueryNode; } -interface PostCaseConfigureArgs extends ClientArgs { +interface PostCaseConfigureArgs extends ClientArgs, IndexRefresh { attributes: CasesConfigureAttributes; id: string; } -interface PatchCaseConfigureArgs extends ClientArgs { +interface PatchCaseConfigureArgs extends ClientArgs, IndexRefresh { configurationId: string; updatedAttributes: Partial; originalConfiguration: SavedObject; @@ -51,10 +55,18 @@ interface PatchCaseConfigureArgs extends ClientArgs { export class CaseConfigureService { constructor(private readonly log: Logger) {} - public async delete({ unsecuredSavedObjectsClient, configurationId }: GetCaseConfigureArgs) { + public async delete({ + unsecuredSavedObjectsClient, + configurationId, + refresh, + }: DeleteCaseConfigureArgs) { try { this.log.debug(`Attempting to DELETE case configure ${configurationId}`); - return await unsecuredSavedObjectsClient.delete(CASE_CONFIGURE_SAVED_OBJECT, configurationId); + return await unsecuredSavedObjectsClient.delete( + CASE_CONFIGURE_SAVED_OBJECT, + configurationId, + { refresh } + ); } catch (error) { this.log.debug(`Error on DELETE case configure ${configurationId}: ${error}`); throw error; @@ -105,6 +117,7 @@ export class CaseConfigureService { unsecuredSavedObjectsClient, attributes, id, + refresh, }: PostCaseConfigureArgs): Promise> { try { this.log.debug(`Attempting to POST a new case configuration`); @@ -112,7 +125,7 @@ export class CaseConfigureService { const createdConfig = await unsecuredSavedObjectsClient.create( CASE_CONFIGURE_SAVED_OBJECT, esConfigInfo.attributes, - { id, references: esConfigInfo.referenceHandler.build() } + { id, references: esConfigInfo.referenceHandler.build(), refresh } ); return transformToExternalModel(createdConfig); @@ -127,6 +140,7 @@ export class CaseConfigureService { configurationId, updatedAttributes, originalConfiguration, + refresh, }: PatchCaseConfigureArgs): Promise> { try { this.log.debug(`Attempting to UPDATE case configuration ${configurationId}`); @@ -141,6 +155,7 @@ export class CaseConfigureService { }, { references: esUpdateInfo.referenceHandler.build(originalConfiguration.references), + refresh, } ); diff --git a/x-pack/plugins/cases/server/services/connector_mappings/index.ts b/x-pack/plugins/cases/server/services/connector_mappings/index.ts index 302a546ca69ea..2163775bf50ef 100644 --- a/x-pack/plugins/cases/server/services/connector_mappings/index.ts +++ b/x-pack/plugins/cases/server/services/connector_mappings/index.ts @@ -10,6 +10,7 @@ import { Logger, SavedObjectReference, SavedObjectsClientContract } from '@kbn/c import { CASE_CONNECTOR_MAPPINGS_SAVED_OBJECT } from '../../../common/constants'; import { ConnectorMappings } from '../../../common/api'; import { SavedObjectFindOptionsKueryNode } from '../../common/types'; +import { IndexRefresh } from '../types'; interface ClientArgs { unsecuredSavedObjectsClient: SavedObjectsClientContract; @@ -18,12 +19,12 @@ interface FindConnectorMappingsArgs extends ClientArgs { options?: SavedObjectFindOptionsKueryNode; } -interface PostConnectorMappingsArgs extends ClientArgs { +interface PostConnectorMappingsArgs extends ClientArgs, IndexRefresh { attributes: ConnectorMappings; references: SavedObjectReference[]; } -interface UpdateConnectorMappingsArgs extends ClientArgs { +interface UpdateConnectorMappingsArgs extends ClientArgs, IndexRefresh { mappingId: string; attributes: Partial; references: SavedObjectReference[]; @@ -49,6 +50,7 @@ export class ConnectorMappingsService { unsecuredSavedObjectsClient, attributes, references, + refresh, }: PostConnectorMappingsArgs) { try { this.log.debug(`Attempting to POST a new connector mappings`); @@ -57,6 +59,7 @@ export class ConnectorMappingsService { attributes, { references, + refresh, } ); } catch (error) { @@ -70,6 +73,7 @@ export class ConnectorMappingsService { mappingId, attributes, references, + refresh, }: UpdateConnectorMappingsArgs) { try { this.log.debug(`Attempting to UPDATE connector mappings ${mappingId}`); @@ -79,6 +83,7 @@ export class ConnectorMappingsService { attributes, { references, + refresh, } ); } catch (error) { diff --git a/x-pack/plugins/cases/server/services/types.ts b/x-pack/plugins/cases/server/services/types.ts new file mode 100644 index 0000000000000..1df1158583fa4 --- /dev/null +++ b/x-pack/plugins/cases/server/services/types.ts @@ -0,0 +1,14 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { SavedObjectsCreateOptions } from '@kbn/core/server'; + +export type RefreshSetting = NonNullable; + +export interface IndexRefresh { + refresh?: SavedObjectsCreateOptions['refresh']; +} diff --git a/x-pack/plugins/cases/server/services/user_actions/index.test.ts b/x-pack/plugins/cases/server/services/user_actions/index.test.ts index 450b5f423c426..14931763a4cc4 100644 --- a/x-pack/plugins/cases/server/services/user_actions/index.test.ts +++ b/x-pack/plugins/cases/server/services/user_actions/index.test.ts @@ -854,46 +854,49 @@ describe('CaseUserActionService', () => { user: commonArgs.user, }); - expect(unsecuredSavedObjectsClient.bulkCreate).toHaveBeenCalledWith([ - { - attributes: { - action: 'delete', - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + expect(unsecuredSavedObjectsClient.bulkCreate).toHaveBeenCalledWith( + [ + { + attributes: { + action: 'delete', + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'delete_case', + owner: 'securitySolution', + payload: {}, }, - type: 'delete_case', - owner: 'securitySolution', - payload: {}, + references: [ + { id: '1', name: 'associated-cases', type: 'cases' }, + { id: '3', name: 'connectorId', type: 'action' }, + ], + type: 'cases-user-actions', }, - references: [ - { id: '1', name: 'associated-cases', type: 'cases' }, - { id: '3', name: 'connectorId', type: 'action' }, - ], - type: 'cases-user-actions', - }, - { - attributes: { - action: 'delete', - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + { + attributes: { + action: 'delete', + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'delete_case', + owner: 'securitySolution', + payload: {}, }, - type: 'delete_case', - owner: 'securitySolution', - payload: {}, + references: [ + { id: '2', name: 'associated-cases', type: 'cases' }, + { id: '4', name: 'connectorId', type: 'action' }, + ], + type: 'cases-user-actions', }, - references: [ - { id: '2', name: 'associated-cases', type: 'cases' }, - { id: '4', name: 'connectorId', type: 'action' }, - ], - type: 'cases-user-actions', - }, - ]); + ], + { refresh: undefined } + ); }); }); @@ -906,161 +909,164 @@ describe('CaseUserActionService', () => { user: commonArgs.user, }); - expect(unsecuredSavedObjectsClient.bulkCreate).toHaveBeenCalledWith([ - { - attributes: { - action: Actions.update, - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + expect(unsecuredSavedObjectsClient.bulkCreate).toHaveBeenCalledWith( + [ + { + attributes: { + action: Actions.update, + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'title', + owner: 'securitySolution', + payload: { title: 'updated title' }, }, - type: 'title', - owner: 'securitySolution', - payload: { title: 'updated title' }, + references: [{ id: '1', name: 'associated-cases', type: 'cases' }], + type: 'cases-user-actions', }, - references: [{ id: '1', name: 'associated-cases', type: 'cases' }], - type: 'cases-user-actions', - }, - { - attributes: { - action: Actions.update, - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + { + attributes: { + action: Actions.update, + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'status', + owner: 'securitySolution', + payload: { status: 'closed' }, }, - type: 'status', - owner: 'securitySolution', - payload: { status: 'closed' }, + references: [{ id: '1', name: 'associated-cases', type: 'cases' }], + type: 'cases-user-actions', }, - references: [{ id: '1', name: 'associated-cases', type: 'cases' }], - type: 'cases-user-actions', - }, - { - attributes: { - action: Actions.update, - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', - }, - type: 'connector', - owner: 'securitySolution', - payload: { - connector: { - fields: { - category: 'Denial of Service', - destIp: true, - malwareHash: true, - malwareUrl: true, - priority: '2', - sourceIp: true, - subcategory: '45', + { + attributes: { + action: Actions.update, + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'connector', + owner: 'securitySolution', + payload: { + connector: { + fields: { + category: 'Denial of Service', + destIp: true, + malwareHash: true, + malwareUrl: true, + priority: '2', + sourceIp: true, + subcategory: '45', + }, + name: 'ServiceNow SN', + type: '.servicenow-sir', }, - name: 'ServiceNow SN', - type: '.servicenow-sir', }, }, + references: [ + { id: '1', name: 'associated-cases', type: 'cases' }, + { id: '456', name: 'connectorId', type: 'action' }, + ], + type: 'cases-user-actions', }, - references: [ - { id: '1', name: 'associated-cases', type: 'cases' }, - { id: '456', name: 'connectorId', type: 'action' }, - ], - type: 'cases-user-actions', - }, - { - attributes: { - action: Actions.update, - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + { + attributes: { + action: Actions.update, + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'description', + owner: 'securitySolution', + payload: { description: 'updated desc' }, }, - type: 'description', - owner: 'securitySolution', - payload: { description: 'updated desc' }, + references: [{ id: '2', name: 'associated-cases', type: 'cases' }], + type: 'cases-user-actions', }, - references: [{ id: '2', name: 'associated-cases', type: 'cases' }], - type: 'cases-user-actions', - }, - { - attributes: { - action: 'add', - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + { + attributes: { + action: 'add', + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'tags', + owner: 'securitySolution', + payload: { tags: ['one', 'two'] }, }, - type: 'tags', - owner: 'securitySolution', - payload: { tags: ['one', 'two'] }, + references: [{ id: '2', name: 'associated-cases', type: 'cases' }], + type: 'cases-user-actions', }, - references: [{ id: '2', name: 'associated-cases', type: 'cases' }], - type: 'cases-user-actions', - }, - { - attributes: { - action: 'delete', - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + { + attributes: { + action: 'delete', + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'tags', + owner: 'securitySolution', + payload: { tags: ['defacement'] }, }, - type: 'tags', - owner: 'securitySolution', - payload: { tags: ['defacement'] }, + references: [{ id: '2', name: 'associated-cases', type: 'cases' }], + type: 'cases-user-actions', }, - references: [{ id: '2', name: 'associated-cases', type: 'cases' }], - type: 'cases-user-actions', - }, - { - attributes: { - action: Actions.update, - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', + { + attributes: { + action: Actions.update, + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'settings', + owner: 'securitySolution', + payload: { settings: { syncAlerts: false } }, }, - type: 'settings', - owner: 'securitySolution', - payload: { settings: { syncAlerts: false } }, + references: [{ id: '2', name: 'associated-cases', type: 'cases' }], + type: 'cases-user-actions', }, - references: [{ id: '2', name: 'associated-cases', type: 'cases' }], - type: 'cases-user-actions', - }, - { - attributes: { - action: 'update', - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', - }, - owner: 'securitySolution', - payload: { - severity: 'critical', + { + attributes: { + action: 'update', + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + owner: 'securitySolution', + payload: { + severity: 'critical', + }, + type: 'severity', }, - type: 'severity', + references: [ + { + id: '2', + name: 'associated-cases', + type: 'cases', + }, + ], + type: 'cases-user-actions', }, - references: [ - { - id: '2', - name: 'associated-cases', - type: 'cases', - }, - ], - type: 'cases-user-actions', - }, - ]); + ], + { refresh: undefined } + ); }); }); @@ -1070,56 +1076,59 @@ describe('CaseUserActionService', () => { ...commonArgs, attachments, }); - expect(unsecuredSavedObjectsClient.bulkCreate).toHaveBeenCalledWith([ - { - attributes: { - action: 'delete', - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', - }, - type: 'comment', - owner: 'securitySolution', - payload: { - comment: { comment: 'a comment', owner: 'securitySolution', type: 'user' }, + expect(unsecuredSavedObjectsClient.bulkCreate).toHaveBeenCalledWith( + [ + { + attributes: { + action: 'delete', + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'comment', + owner: 'securitySolution', + payload: { + comment: { comment: 'a comment', owner: 'securitySolution', type: 'user' }, + }, }, + references: [ + { id: '123', name: 'associated-cases', type: 'cases' }, + { id: '1', name: 'associated-cases-comments', type: 'cases-comments' }, + ], + type: 'cases-user-actions', }, - references: [ - { id: '123', name: 'associated-cases', type: 'cases' }, - { id: '1', name: 'associated-cases-comments', type: 'cases-comments' }, - ], - type: 'cases-user-actions', - }, - { - attributes: { - action: 'delete', - created_at: '2022-01-09T22:00:00.000Z', - created_by: { - email: 'elastic@elastic.co', - full_name: 'Elastic User', - username: 'elastic', - }, - type: 'comment', - owner: 'securitySolution', - payload: { - comment: { - alertId: 'alert-id-1', - index: 'alert-index-1', - owner: 'securitySolution', - rule: { id: 'rule-id-1', name: 'rule-name-1' }, - type: 'alert', + { + attributes: { + action: 'delete', + created_at: '2022-01-09T22:00:00.000Z', + created_by: { + email: 'elastic@elastic.co', + full_name: 'Elastic User', + username: 'elastic', + }, + type: 'comment', + owner: 'securitySolution', + payload: { + comment: { + alertId: 'alert-id-1', + index: 'alert-index-1', + owner: 'securitySolution', + rule: { id: 'rule-id-1', name: 'rule-name-1' }, + type: 'alert', + }, }, }, + references: [ + { id: '123', name: 'associated-cases', type: 'cases' }, + { id: '2', name: 'associated-cases-comments', type: 'cases-comments' }, + ], + type: 'cases-user-actions', }, - references: [ - { id: '123', name: 'associated-cases', type: 'cases' }, - { id: '2', name: 'associated-cases-comments', type: 'cases-comments' }, - ], - type: 'cases-user-actions', - }, - ]); + ], + { refresh: undefined } + ); }); }); diff --git a/x-pack/plugins/cases/server/services/user_actions/index.ts b/x-pack/plugins/cases/server/services/user_actions/index.ts index 3adde90f369d1..f0bdc0f44ddea 100644 --- a/x-pack/plugins/cases/server/services/user_actions/index.ts +++ b/x-pack/plugins/cases/server/services/user_actions/index.ts @@ -58,6 +58,7 @@ import { BuilderFactory } from './builder_factory'; import { defaultSortField, isCommentRequestTypeExternalReferenceSO } from '../../common/utils'; import { PersistableStateAttachmentTypeRegistry } from '../../attachment_framework/persistable_state_registry'; import { injectPersistableReferencesToSO } from '../../attachment_framework/so_references'; +import { IndexRefresh } from '../types'; interface GetCaseUserActionArgs extends ClientArgs { caseId: string; @@ -68,18 +69,18 @@ export interface UserActionItem { references: SavedObjectReference[]; } -interface PostCaseUserActionArgs extends ClientArgs { +interface PostCaseUserActionArgs extends ClientArgs, IndexRefresh { actions: BuilderReturnValue[]; } -interface CreateUserActionES extends ClientArgs { +interface CreateUserActionES extends ClientArgs, IndexRefresh { attributes: T; references: SavedObjectReference[]; } type CommonUserActionArgs = ClientArgs & CommonArguments; -interface BulkCreateCaseDeletionUserAction extends ClientArgs { +interface BulkCreateCaseDeletionUserAction extends ClientArgs, IndexRefresh { cases: Array<{ id: string; owner: string; connectorId: string }>; user: User; } @@ -90,18 +91,19 @@ interface GetUserActionItemByDifference extends CommonUserActionArgs { newValue: unknown; } -interface BulkCreateBulkUpdateCaseUserActions extends ClientArgs { +interface BulkCreateBulkUpdateCaseUserActions extends ClientArgs, IndexRefresh { originalCases: Array>; updatedCases: Array>; user: User; } -interface BulkCreateAttachmentUserAction extends Omit { +interface BulkCreateAttachmentUserAction extends Omit, IndexRefresh { attachments: Array<{ id: string; owner: string; attachment: CommentRequest }>; } type CreateUserActionClient = CreateUserAction & - CommonUserActionArgs; + CommonUserActionArgs & + IndexRefresh; export class CaseUserActionService { private static readonly userActionFieldsAllowed: Set = new Set(Object.keys(ActionTypes)); @@ -184,6 +186,7 @@ export class CaseUserActionService { unsecuredSavedObjectsClient, cases, user, + refresh, }: BulkCreateCaseDeletionUserAction): Promise { this.log.debug(`Attempting to create a create case user action`); const userActionsWithReferences = cases.reduce((acc, caseInfo) => { @@ -204,7 +207,11 @@ export class CaseUserActionService { return [...acc, deleteCaseUserAction]; }, []); - await this.bulkCreate({ unsecuredSavedObjectsClient, actions: userActionsWithReferences }); + await this.bulkCreate({ + unsecuredSavedObjectsClient, + actions: userActionsWithReferences, + refresh, + }); } public async bulkCreateUpdateCase({ @@ -212,6 +219,7 @@ export class CaseUserActionService { originalCases, updatedCases, user, + refresh, }: BulkCreateBulkUpdateCaseUserActions): Promise { const userActionsWithReferences = updatedCases.reduce( (acc, updatedCase) => { @@ -250,7 +258,11 @@ export class CaseUserActionService { [] ); - await this.bulkCreate({ unsecuredSavedObjectsClient, actions: userActionsWithReferences }); + await this.bulkCreate({ + unsecuredSavedObjectsClient, + actions: userActionsWithReferences, + refresh, + }); } private async bulkCreateAttachment({ @@ -259,6 +271,7 @@ export class CaseUserActionService { attachments, user, action = Actions.create, + refresh, }: BulkCreateAttachmentUserAction): Promise { this.log.debug(`Attempting to create a bulk create case user action`); const userActionsWithReferences = attachments.reduce( @@ -282,7 +295,11 @@ export class CaseUserActionService { [] ); - await this.bulkCreate({ unsecuredSavedObjectsClient, actions: userActionsWithReferences }); + await this.bulkCreate({ + unsecuredSavedObjectsClient, + actions: userActionsWithReferences, + refresh, + }); } public async bulkCreateAttachmentDeletion({ @@ -290,6 +307,7 @@ export class CaseUserActionService { caseId, attachments, user, + refresh, }: BulkCreateAttachmentUserAction): Promise { await this.bulkCreateAttachment({ unsecuredSavedObjectsClient, @@ -297,6 +315,7 @@ export class CaseUserActionService { attachments, user, action: Actions.delete, + refresh, }); } @@ -305,6 +324,7 @@ export class CaseUserActionService { caseId, attachments, user, + refresh, }: BulkCreateAttachmentUserAction): Promise { await this.bulkCreateAttachment({ unsecuredSavedObjectsClient, @@ -312,6 +332,7 @@ export class CaseUserActionService { attachments, user, action: Actions.create, + refresh, }); } @@ -325,6 +346,7 @@ export class CaseUserActionService { payload, connectorId, attachmentId, + refresh, }: CreateUserActionClient) { try { this.log.debug(`Attempting to create a user action of type: ${type}`); @@ -342,7 +364,7 @@ export class CaseUserActionService { if (userAction) { const { attributes, references } = userAction; - await this.create({ unsecuredSavedObjectsClient, attributes, references }); + await this.create({ unsecuredSavedObjectsClient, attributes, references, refresh }); } } catch (error) { this.log.error(`Error on creating user action of type: ${type}. Error: ${error}`); @@ -382,12 +404,14 @@ export class CaseUserActionService { unsecuredSavedObjectsClient, attributes, references, + refresh, }: CreateUserActionES): Promise { try { this.log.debug(`Attempting to POST a new case user action`); await unsecuredSavedObjectsClient.create(CASE_USER_ACTION_SAVED_OBJECT, attributes, { references: references ?? [], + refresh, }); } catch (error) { this.log.error(`Error on POST a new case user action: ${error}`); @@ -398,6 +422,7 @@ export class CaseUserActionService { public async bulkCreate({ unsecuredSavedObjectsClient, actions, + refresh, }: PostCaseUserActionArgs): Promise { if (isEmpty(actions)) { return; @@ -407,7 +432,8 @@ export class CaseUserActionService { this.log.debug(`Attempting to POST a new case user action`); await unsecuredSavedObjectsClient.bulkCreate( - actions.map((action) => ({ type: CASE_USER_ACTION_SAVED_OBJECT, ...action })) + actions.map((action) => ({ type: CASE_USER_ACTION_SAVED_OBJECT, ...action })), + { refresh } ); } catch (error) { this.log.error(`Error on POST a new case user action: ${error}`); From 40165b7c2020ac2c95bdfc8f7db3933475e1c5ef Mon Sep 17 00:00:00 2001 From: Nick Peihl Date: Mon, 18 Jul 2022 11:20:34 -0400 Subject: [PATCH 098/111] [Maps] Add ML Anomalies layer to telemetry (#136345) * Add ML Anomalies layer to telemetry * Fix telemetry --- x-pack/plugins/maps/common/constants.ts | 1 + .../common/telemetry/layer_stats_collector.ts | 4 +++ x-pack/plugins/maps/common/telemetry/types.ts | 1 + .../maps_telemetry/collectors/register.ts | 18 ++++++++++++ .../plugins/ml/public/maps/anomaly_source.tsx | 4 +-- .../ml/public/maps/anomaly_source_factory.ts | 5 ++-- .../schema/xpack_plugins.json | 28 +++++++++++++++++++ 7 files changed, 56 insertions(+), 5 deletions(-) diff --git a/x-pack/plugins/maps/common/constants.ts b/x-pack/plugins/maps/common/constants.ts index d2c69e89078af..387d91d75b7eb 100644 --- a/x-pack/plugins/maps/common/constants.ts +++ b/x-pack/plugins/maps/common/constants.ts @@ -63,6 +63,7 @@ export enum SOURCE_TYPES { ES_SEARCH = 'ES_SEARCH', ES_PEW_PEW = 'ES_PEW_PEW', ES_TERM_SOURCE = 'ES_TERM_SOURCE', + ES_ML_ANOMALIES = 'ML_ANOMALIES', EMS_XYZ = 'EMS_XYZ', // identifies a custom TMS source. EMS-prefix in the name is a little unfortunate :( WMS = 'WMS', KIBANA_TILEMAP = 'KIBANA_TILEMAP', diff --git a/x-pack/plugins/maps/common/telemetry/layer_stats_collector.ts b/x-pack/plugins/maps/common/telemetry/layer_stats_collector.ts index 634d11ca350a6..0978b3ace87ec 100644 --- a/x-pack/plugins/maps/common/telemetry/layer_stats_collector.ts +++ b/x-pack/plugins/maps/common/telemetry/layer_stats_collector.ts @@ -195,6 +195,10 @@ function getLayerKey(layerDescriptor: LayerDescriptor): LAYER_KEYS | null { return LAYER_KEYS.ES_POINT_TO_POINT; } + if (layerDescriptor.sourceDescriptor.type === SOURCE_TYPES.ES_ML_ANOMALIES) { + return LAYER_KEYS.ES_ML_ANOMALIES; + } + if (layerDescriptor.sourceDescriptor.type === SOURCE_TYPES.ES_SEARCH) { const sourceDescriptor = layerDescriptor.sourceDescriptor as ESSearchSourceDescriptor; diff --git a/x-pack/plugins/maps/common/telemetry/types.ts b/x-pack/plugins/maps/common/telemetry/types.ts index c48be2de13c49..7b0dfc4eae3bb 100644 --- a/x-pack/plugins/maps/common/telemetry/types.ts +++ b/x-pack/plugins/maps/common/telemetry/types.ts @@ -25,6 +25,7 @@ export enum LAYER_KEYS { ES_AGG_GRIDS = 'es_agg_grids', ES_AGG_HEXAGONS = 'es_agg_hexagons', ES_AGG_HEATMAP = 'es_agg_heatmap', + ES_ML_ANOMALIES = 'es_ml_anomalies', EMS_REGION = 'ems_region', EMS_BASEMAP = 'ems_basemap', KBN_TMS_RASTER = 'kbn_tms_raster', diff --git a/x-pack/plugins/maps/server/maps_telemetry/collectors/register.ts b/x-pack/plugins/maps/server/maps_telemetry/collectors/register.ts index d044264237b5b..2a8a07578109f 100644 --- a/x-pack/plugins/maps/server/maps_telemetry/collectors/register.ts +++ b/x-pack/plugins/maps/server/maps_telemetry/collectors/register.ts @@ -106,6 +106,24 @@ export function registerMapsUsageCollector(usageCollection?: UsageCollectionSetu _meta: { description: 'total number of es document layers in cluster' }, }, }, + es_ml_anomalies: { + min: { + type: 'long', + _meta: { description: 'min number of es machine learning anomaly layers per map' }, + }, + max: { + type: 'long', + _meta: { description: 'max number of es machine learning anomaly layers per map' }, + }, + avg: { + type: 'float', + _meta: { description: 'avg number of es machine learning anomaly layers per map' }, + }, + total: { + type: 'long', + _meta: { description: 'total number of es machine learning anomaly layers in cluster' }, + }, + }, es_point_to_point: { min: { type: 'long', diff --git a/x-pack/plugins/ml/public/maps/anomaly_source.tsx b/x-pack/plugins/ml/public/maps/anomaly_source.tsx index 46b6a033c6390..41bf7fedfabad 100644 --- a/x-pack/plugins/ml/public/maps/anomaly_source.tsx +++ b/x-pack/plugins/ml/public/maps/anomaly_source.tsx @@ -11,6 +11,7 @@ import { FieldFormatter, MAX_ZOOM, MIN_ZOOM, + SOURCE_TYPES, TooltipFeatureAction, VECTOR_SHAPE_TYPE, VectorSourceRequestMeta, @@ -29,7 +30,6 @@ import { AnomalySourceTooltipProperty, ANOMALY_SOURCE_FIELDS, } from './anomaly_source_field'; -import { ML_ANOMALY } from './anomaly_source_factory'; import { getResultsForJobId, ML_ANOMALY_LAYERS, MlAnomalyLayersType } from './util'; import { UpdateAnomalySourceEditor } from './update_anomaly_source_editor'; import type { MlApiServices } from '../application/services/ml_api_service'; @@ -51,7 +51,7 @@ export class AnomalySource implements IVectorSource { } return { - type: ML_ANOMALY, + type: SOURCE_TYPES.ES_ML_ANOMALIES, jobId: descriptor.jobId, typicalActual: descriptor.typicalActual || ML_ANOMALY_LAYERS.ACTUAL, }; diff --git a/x-pack/plugins/ml/public/maps/anomaly_source_factory.ts b/x-pack/plugins/ml/public/maps/anomaly_source_factory.ts index 81646d98d0c13..0556d703cdd96 100644 --- a/x-pack/plugins/ml/public/maps/anomaly_source_factory.ts +++ b/x-pack/plugins/ml/public/maps/anomaly_source_factory.ts @@ -6,14 +6,13 @@ */ import type { StartServicesAccessor } from '@kbn/core/public'; +import { SOURCE_TYPES } from '@kbn/maps-plugin/common'; import { HttpService } from '../application/services/http_service'; import type { MlPluginStart, MlStartDependencies } from '../plugin'; import type { MlApiServices } from '../application/services/ml_api_service'; -export const ML_ANOMALY = 'ML_ANOMALIES'; - export class AnomalySourceFactory { - public readonly type = ML_ANOMALY; + public readonly type = SOURCE_TYPES.ES_ML_ANOMALIES; constructor( private getStartServices: StartServicesAccessor, diff --git a/x-pack/plugins/telemetry_collection_xpack/schema/xpack_plugins.json b/x-pack/plugins/telemetry_collection_xpack/schema/xpack_plugins.json index 7c30e55ab151a..ed0da3e34b22b 100644 --- a/x-pack/plugins/telemetry_collection_xpack/schema/xpack_plugins.json +++ b/x-pack/plugins/telemetry_collection_xpack/schema/xpack_plugins.json @@ -5832,6 +5832,34 @@ } } }, + "es_ml_anomalies": { + "properties": { + "min": { + "type": "long", + "_meta": { + "description": "min number of es machine learning anomaly layers per map" + } + }, + "max": { + "type": "long", + "_meta": { + "description": "max number of es machine learning anomaly layers per map" + } + }, + "avg": { + "type": "float", + "_meta": { + "description": "avg number of es machine learning anomaly layers per map" + } + }, + "total": { + "type": "long", + "_meta": { + "description": "total number of es machine learning anomaly layers in cluster" + } + } + } + }, "es_point_to_point": { "properties": { "min": { From aea46fd3726c0efda3bc866e34659653e0fcc45a Mon Sep 17 00:00:00 2001 From: Alexey Antonov Date: Mon, 18 Jul 2022 18:23:12 +0300 Subject: [PATCH 099/111] [Lens] renderMode="preview" should be used for suggestions (#136546) --- .../editor_frame_service/editor_frame/suggestion_panel.tsx | 1 + 1 file changed, 1 insertion(+) diff --git a/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx b/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx index e64cdd9bd33dc..f3f4ed3c39e4e 100644 --- a/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx +++ b/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx @@ -113,6 +113,7 @@ const PreviewRenderer = ({ { From 031729e81aab40d1955c820b62dd749d7d4364fd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cau=C3=AA=20Marcondes?= <55978943+cauemarcondes@users.noreply.github.com> Date: Mon, 18 Jul 2022 11:28:54 -0400 Subject: [PATCH 100/111] [APM] Rename backends to dependencies in URLs and APIs (#136330) * renaming api endpoints * renaming route functions * GET /internal/apm/dependencies/top_dependencies * GET /internal/apm/dependencies/upstream_services * server changes * renaming route params * refactoring * refactoring client * refactogin client * refactoring routes * fixing redirection * refactoring component * renaming nodetype * renaming backend link * backend template * renaming backends operations * dependency operation * DependencyMetricCharts * DependencyMetricCharts * DependencyOperationDetailView * DependencyDetailOverview * remaining * updating tests and i18n --- x-pack/plugins/apm/common/connections.ts | 14 +- .../common/{backends.ts => dependencies.ts} | 8 +- .../power_user/feature_flag/comparison.ts | 4 +- .../read_only_user/dependencies.spec.ts | 8 +- .../app/backend_detail_operations/index.tsx | 16 -- .../dependencies_inventory_table}/index.tsx | 22 +-- .../index.tsx | 10 +- .../index.tsx | 36 ++-- .../dependency_detail_operations/index.tsx | 16 ++ .../dependencies_detail_table.tsx} | 25 ++- .../index.tsx | 25 +-- .../index.tsx | 21 +- .../dependency_operation_detail_link.tsx} | 6 +- ...ependency_operation_detail_trace_list.tsx} | 32 ++-- ...ndendecy_operation_distribution_chart.tsx} | 26 ++- .../index.tsx | 24 +-- ...d_contents.tsx => dependency_contents.tsx} | 27 +-- .../app/service_map/popover/index.tsx | 4 +- .../service_map/popover/popover.stories.tsx | 8 +- .../app/service_map/popover/popover.test.tsx | 7 +- .../index.tsx | 10 +- .../span_flyout/sticky_span_properties.tsx | 8 +- .../public/components/routing/app_root.tsx | 6 +- .../components/routing/home/dependencies.tsx | 90 +++++++++ .../public/components/routing/home/index.tsx | 104 ++-------- .../routing/home/legacy_backends.tsx | 82 ++++++++ ...direct_backends_to_backend_detail_view.tsx | 19 -- ...ependencies_to_dependencies_inventory.tsx} | 4 +- .../redirect_path_backend_detail_view.tsx | 22 --- ...ate.tsx => dependency_detail_template.tsx} | 35 ++-- .../shared/charts/timeseries_chart.tsx | 6 +- ...tories.tsx => dependency_link.stories.tsx} | 12 +- ...link.test.tsx => dependency_link.test.tsx} | 4 +- .../{backend_link.tsx => dependency_link.tsx} | 15 +- ...endency_failed_transaction_rate_chart.tsx} | 16 +- .../dependency_latency_chart.tsx} | 16 +- .../dependency_metric_charts_route_params.ts} | 6 +- .../dependency_throughput_chart.tsx} | 21 +- .../index.tsx | 35 ++-- .../shared/is_route_with_time_range.ts | 8 +- .../shared/time_comparison/index.tsx | 6 +- .../time_range_metadata_context.tsx | 3 +- ...ependency_detail_operations_breadcrumb.ts} | 12 +- .../public/hooks/use_previous_period_text.ts | 6 +- x-pack/plugins/apm/public/plugin.ts | 8 +- .../get_destination_map.ts | 24 +-- .../get_connection_stats/get_stats.ts | 10 +- .../connections/get_connection_stats/index.ts | 3 +- .../get_global_apm_server_route_repository.ts | 4 +- .../get_error_rate_charts_for_backend.ts | 145 -------------- .../get_dependency_latency_distribution.ts} | 8 +- .../get_error_rate_charts_for_dependency.ts | 148 ++++++++++++++ .../get_latency_charts_for_dependency.ts} | 10 +- .../get_metadata_for_dependency.ts} | 49 ++--- .../get_throughput_charts_for_dependency.ts} | 95 ++++----- .../get_top_dependencies.ts} | 2 +- .../get_top_dependency_operations.ts} | 83 ++++---- .../get_top_dependency_spans.ts} | 18 +- .../get_upstream_services_for_dependency.ts} | 8 +- .../{backends => dependencies}/route.ts | 181 +++++++++--------- ...> get_service_map_dependency_node_info.ts} | 14 +- .../apm/server/routes/service_map/route.ts | 18 +- .../translations/translations/fr-FR.json | 9 - .../translations/translations/ja-JP.json | 9 - .../translations/translations/zh-CN.json | 9 - .../dependencies/dependency_metrics.spec.ts | 36 ++-- .../tests/dependencies/metadata.spec.ts | 4 +- .../dependencies/service_dependencies.spec.ts | 16 +- .../dependencies/top_dependencies.spec.ts | 34 ++-- .../tests/dependencies/top_operations.spec.ts | 20 +- .../tests/dependencies/top_spans.spec.ts | 24 +-- .../dependencies/upstream_services.spec.ts | 6 +- .../tests/service_maps/service_maps.spec.ts | 26 +-- .../dependencies/index.spec.ts | 8 +- .../throughput/dependencies_apis.spec.ts | 128 +++++++------ 75 files changed, 1052 insertions(+), 990 deletions(-) rename x-pack/plugins/apm/common/{backends.ts => dependencies.ts} (87%) delete mode 100644 x-pack/plugins/apm/public/components/app/backend_detail_operations/index.tsx rename x-pack/plugins/apm/public/components/app/{backend_inventory/backend_inventory_dependencies_table => dependencies_inventory/dependencies_inventory_table}/index.tsx (81%) rename x-pack/plugins/apm/public/components/app/{backend_inventory => dependencies_inventory}/index.tsx (76%) rename x-pack/plugins/apm/public/components/app/{backend_detail_operations/backend_detail_operations_list => dependency_detail_operations/dependency_detail_operations_list}/index.tsx (81%) create mode 100644 x-pack/plugins/apm/public/components/app/dependency_detail_operations/index.tsx rename x-pack/plugins/apm/public/components/app/{backend_detail_overview/backend_detail_dependencies_table.tsx => dependency_detail_overview/dependencies_detail_table.tsx} (83%) rename x-pack/plugins/apm/public/components/app/{backend_detail_overview => dependency_detail_overview}/index.tsx (69%) rename x-pack/plugins/apm/public/components/app/{backend_detail_view => dependency_detail_view}/index.tsx (70%) rename x-pack/plugins/apm/public/components/app/{backend_operation_detail_view/backend_operation_detail_link.tsx => dependency_operation_detail_view/dependency_operation_detail_link.tsx} (77%) rename x-pack/plugins/apm/public/components/app/{backend_operation_detail_view/backend_operation_detail_trace_list.tsx => dependency_operation_detail_view/dependency_operation_detail_trace_list.tsx} (87%) rename x-pack/plugins/apm/public/components/app/{backend_operation_detail_view/backend_operation_distribution_chart.tsx => dependency_operation_detail_view/dependendecy_operation_distribution_chart.tsx} (82%) rename x-pack/plugins/apm/public/components/app/{backend_operation_detail_view => dependency_operation_detail_view}/index.tsx (63%) rename x-pack/plugins/apm/public/components/app/service_map/popover/{backend_contents.tsx => dependency_contents.tsx} (80%) create mode 100644 x-pack/plugins/apm/public/components/routing/home/dependencies.tsx create mode 100644 x-pack/plugins/apm/public/components/routing/home/legacy_backends.tsx delete mode 100644 x-pack/plugins/apm/public/components/routing/home/redirect_backends_to_backend_detail_view.tsx rename x-pack/plugins/apm/public/components/routing/home/{redirect_backends_to_backend_inventory.tsx => redirect_dependencies_to_dependencies_inventory.tsx} (84%) delete mode 100644 x-pack/plugins/apm/public/components/routing/home/redirect_path_backend_detail_view.tsx rename x-pack/plugins/apm/public/components/routing/templates/{backend_detail_template.tsx => dependency_detail_template.tsx} (74%) rename x-pack/plugins/apm/public/components/shared/{backend_link.stories.tsx => dependency_link.stories.tsx} (78%) rename x-pack/plugins/apm/public/components/shared/{backend_link.test.tsx => dependency_link.test.tsx} (85%) rename x-pack/plugins/apm/public/components/shared/{backend_link.tsx => dependency_link.tsx} (81%) rename x-pack/plugins/apm/public/components/shared/{backend_metric_charts/backend_error_rate_chart.tsx => dependency_metric_charts/dependency_failed_transaction_rate_chart.tsx} (88%) rename x-pack/plugins/apm/public/components/shared/{backend_metric_charts/backend_latency_chart.tsx => dependency_metric_charts/dependency_latency_chart.tsx} (89%) rename x-pack/plugins/apm/public/components/shared/{backend_metric_charts/backend_metric_charts_route_params.ts => dependency_metric_charts/dependency_metric_charts_route_params.ts} (81%) rename x-pack/plugins/apm/public/components/shared/{backend_metric_charts/backend_throughput_chart.tsx => dependency_metric_charts/dependency_throughput_chart.tsx} (86%) rename x-pack/plugins/apm/public/components/shared/{backend_metric_charts => dependency_metric_charts}/index.tsx (63%) rename x-pack/plugins/apm/public/hooks/{use_backend_detail_operations_breadcrumb.ts => use_dependency_detail_operations_breadcrumb.ts} (76%) delete mode 100644 x-pack/plugins/apm/server/routes/backends/get_error_rate_charts_for_backend.ts rename x-pack/plugins/apm/server/routes/{backends/get_backend_latency_distribution.ts => dependencies/get_dependency_latency_distribution.ts} (92%) create mode 100644 x-pack/plugins/apm/server/routes/dependencies/get_error_rate_charts_for_dependency.ts rename x-pack/plugins/apm/server/routes/{backends/get_latency_charts_for_backend.ts => dependencies/get_latency_charts_for_dependency.ts} (94%) rename x-pack/plugins/apm/server/routes/{backends/get_metadata_for_backend.ts => dependencies/get_metadata_for_dependency.ts} (60%) rename x-pack/plugins/apm/server/routes/{backends/get_throughput_charts_for_backend.ts => dependencies/get_throughput_charts_for_dependency.ts} (53%) rename x-pack/plugins/apm/server/routes/{backends/get_top_backends.ts => dependencies/get_top_dependencies.ts} (96%) rename x-pack/plugins/apm/server/routes/{backends/get_top_backend_operations.ts => dependencies/get_top_dependency_operations.ts} (75%) rename x-pack/plugins/apm/server/routes/{backends/get_top_backend_spans.ts => dependencies/get_top_dependency_spans.ts} (90%) rename x-pack/plugins/apm/server/routes/{backends/get_upstream_services_for_backend.ts => dependencies/get_upstream_services_for_dependency.ts} (88%) rename x-pack/plugins/apm/server/routes/{backends => dependencies}/route.ts (73%) rename x-pack/plugins/apm/server/routes/service_map/{get_service_map_backend_node_info.ts => get_service_map_dependency_node_info.ts} (93%) diff --git a/x-pack/plugins/apm/common/connections.ts b/x-pack/plugins/apm/common/connections.ts index 1fde50ce5489e..ca040c73afc59 100644 --- a/x-pack/plugins/apm/common/connections.ts +++ b/x-pack/plugins/apm/common/connections.ts @@ -9,7 +9,7 @@ import { Coordinate } from '../typings/timeseries'; export enum NodeType { service = 'service', - backend = 'backend', + dependency = 'dependency', } interface NodeBase { @@ -23,14 +23,14 @@ export interface ServiceNode extends NodeBase { environment: string; } -export interface BackendNode extends NodeBase { - type: NodeType.backend; - backendName: string; +export interface DependencyNode extends NodeBase { + type: NodeType.dependency; + dependencyName: string; spanType: string; spanSubtype: string; } -export type Node = ServiceNode | BackendNode; +export type Node = ServiceNode | DependencyNode; export interface ConnectionStatsItem { location: Node; @@ -67,5 +67,7 @@ export interface ConnectionStatsItemWithComparisonData { } export function getNodeName(node: Node) { - return node.type === NodeType.service ? node.serviceName : node.backendName; + return node.type === NodeType.service + ? node.serviceName + : node.dependencyName; } diff --git a/x-pack/plugins/apm/common/backends.ts b/x-pack/plugins/apm/common/dependencies.ts similarity index 87% rename from x-pack/plugins/apm/common/backends.ts rename to x-pack/plugins/apm/common/dependencies.ts index 53418fe7f9b62..51f0d505d5df8 100644 --- a/x-pack/plugins/apm/common/backends.ts +++ b/x-pack/plugins/apm/common/dependencies.ts @@ -21,17 +21,17 @@ export const kueryBarPlaceholder = i18n.translate( ); export const getKueryBarBoolFilter = ({ - backendName, + dependencyName, environment, }: { - backendName?: string; + dependencyName?: string; environment: string; }) => { return [ { term: { [PROCESSOR_EVENT]: ProcessorEvent.metric } }, { exists: { field: SPAN_DESTINATION_SERVICE_RESOURCE } }, - ...(backendName - ? [{ term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: backendName } }] + ...(dependencyName + ? [{ term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: dependencyName } }] : []), ...environmentQuery(environment), ]; diff --git a/x-pack/plugins/apm/ftr_e2e/cypress/integration/power_user/feature_flag/comparison.ts b/x-pack/plugins/apm/ftr_e2e/cypress/integration/power_user/feature_flag/comparison.ts index 198ac9d110556..5dfb121a921e6 100644 --- a/x-pack/plugins/apm/ftr_e2e/cypress/integration/power_user/feature_flag/comparison.ts +++ b/x-pack/plugins/apm/ftr_e2e/cypress/integration/power_user/feature_flag/comparison.ts @@ -49,7 +49,7 @@ describe('Comparison feature flag', () => { }); it('shows the comparison feature enabled in services overview', () => { - cy.visit('/app/apm/backends'); + cy.visit('/app/apm/dependencies'); cy.get('input[type="checkbox"]#comparison').should('be.checked'); cy.get('[data-test-subj="comparisonSelect"]').should('not.be.disabled'); }); @@ -89,7 +89,7 @@ describe('Comparison feature flag', () => { }); it('shows the comparison feature disabled in dependencies overview page', () => { - cy.visit('/app/apm/backends'); + cy.visit('/app/apm/dependencies'); cy.get('input[type="checkbox"]#comparison').should('not.be.checked'); cy.get('[data-test-subj="comparisonSelect"]').should('be.disabled'); }); diff --git a/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/dependencies.spec.ts b/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/dependencies.spec.ts index 72a3a3854ce8d..67cf0c14e111e 100644 --- a/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/dependencies.spec.ts +++ b/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/dependencies.spec.ts @@ -60,9 +60,9 @@ describe('Dependencies', () => { describe.skip('dependency overview page', () => { it('shows dependency information and you can navigate to a page for an upstream service', () => { cy.visit( - `/app/apm/backends/overview?${new URLSearchParams({ + `/app/apm/dependencies/overview?${new URLSearchParams({ ...timeRange, - backendName: 'postgresql', + dependencyName: 'postgresql', })}` ); @@ -77,9 +77,9 @@ describe('Dependencies', () => { it('has no detectable a11y violations on load', () => { cy.visit( - `/app/apm/backends/overview?${new URLSearchParams({ + `/app/apm/dependencies/overview?${new URLSearchParams({ ...timeRange, - backendName: 'postgresql', + dependencyName: 'postgresql', })}` ); cy.contains('h1', 'postgresql'); diff --git a/x-pack/plugins/apm/public/components/app/backend_detail_operations/index.tsx b/x-pack/plugins/apm/public/components/app/backend_detail_operations/index.tsx deleted file mode 100644 index 7b4fd37973811..0000000000000 --- a/x-pack/plugins/apm/public/components/app/backend_detail_operations/index.tsx +++ /dev/null @@ -1,16 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import React from 'react'; -import { useBackendDetailOperationsBreadcrumb } from '../../../hooks/use_backend_detail_operations_breadcrumb'; -import { BackendDetailOperationsList } from './backend_detail_operations_list'; - -export function BackendDetailOperations() { - useBackendDetailOperationsBreadcrumb(); - - return ; -} diff --git a/x-pack/plugins/apm/public/components/app/backend_inventory/backend_inventory_dependencies_table/index.tsx b/x-pack/plugins/apm/public/components/app/dependencies_inventory/dependencies_inventory_table/index.tsx similarity index 81% rename from x-pack/plugins/apm/public/components/app/backend_inventory/backend_inventory_dependencies_table/index.tsx rename to x-pack/plugins/apm/public/components/app/dependencies_inventory/dependencies_inventory_table/index.tsx index eff0f1c4474cc..87985db3addd4 100644 --- a/x-pack/plugins/apm/public/components/app/backend_inventory/backend_inventory_dependencies_table/index.tsx +++ b/x-pack/plugins/apm/public/components/app/dependencies_inventory/dependencies_inventory_table/index.tsx @@ -14,10 +14,10 @@ import { getNodeName, NodeType } from '../../../../../common/connections'; import { useApmParams } from '../../../../hooks/use_apm_params'; import { useFetcher } from '../../../../hooks/use_fetcher'; import { useTimeRange } from '../../../../hooks/use_time_range'; -import { BackendLink } from '../../../shared/backend_link'; +import { DependencyLink } from '../../../shared/dependency_link'; import { DependenciesTable } from '../../../shared/dependencies_table'; -export function BackendInventoryDependenciesTable() { +export function DependenciesInventoryTable() { const { query: { rangeFrom, @@ -27,7 +27,7 @@ export function BackendInventoryDependenciesTable() { comparisonEnabled, offset, }, - } = useApmParams('/backends/inventory'); + } = useApmParams('/dependencies/inventory'); const { start, end } = useTimeRange({ rangeFrom, rangeTo }); @@ -39,7 +39,7 @@ export function BackendInventoryDependenciesTable() { return; } - return callApmApi('GET /internal/apm/backends/top_backends', { + return callApmApi('GET /internal/apm/dependencies/top_dependencies', { params: { query: { start, @@ -59,19 +59,19 @@ export function BackendInventoryDependenciesTable() { ); const dependencies = - data?.backends.map((dependency) => { + data?.dependencies.map((dependency) => { const { location } = dependency; const name = getNodeName(location); - if (location.type !== NodeType.backend) { - throw new Error('Expected a backend node'); + if (location.type !== NodeType.dependency) { + throw new Error('Expected a dependency node'); } const link = ( - @@ -102,7 +102,7 @@ export function BackendInventoryDependenciesTable() { dependencies={dependencies} title={null} nameColumnTitle={i18n.translate( - 'xpack.apm.backendInventory.dependencyTableColumn', + 'xpack.apm.dependenciesInventory.dependencyTableColumn', { defaultMessage: 'Dependency', } diff --git a/x-pack/plugins/apm/public/components/app/backend_inventory/index.tsx b/x-pack/plugins/apm/public/components/app/dependencies_inventory/index.tsx similarity index 76% rename from x-pack/plugins/apm/public/components/app/backend_inventory/index.tsx rename to x-pack/plugins/apm/public/components/app/dependencies_inventory/index.tsx index f29724fa7cdcb..0e999f7e9aa46 100644 --- a/x-pack/plugins/apm/public/components/app/backend_inventory/index.tsx +++ b/x-pack/plugins/apm/public/components/app/dependencies_inventory/index.tsx @@ -10,15 +10,15 @@ import React from 'react'; import { getKueryBarBoolFilter, kueryBarPlaceholder, -} from '../../../../common/backends'; +} from '../../../../common/dependencies'; import { useApmParams } from '../../../hooks/use_apm_params'; import { SearchBar } from '../../shared/search_bar'; -import { BackendInventoryDependenciesTable } from './backend_inventory_dependencies_table'; +import { DependenciesInventoryTable } from './dependencies_inventory_table'; -export function BackendInventory() { +export function DependenciesInventory() { const { query: { environment }, - } = useApmParams('/backends/inventory'); + } = useApmParams('/dependencies/inventory'); const kueryBarBoolFilter = getKueryBarBoolFilter({ environment, }); @@ -31,7 +31,7 @@ export function BackendInventory() { kueryBarBoolFilter={kueryBarBoolFilter} /> - + ); } diff --git a/x-pack/plugins/apm/public/components/app/backend_detail_operations/backend_detail_operations_list/index.tsx b/x-pack/plugins/apm/public/components/app/dependency_detail_operations/dependency_detail_operations_list/index.tsx similarity index 81% rename from x-pack/plugins/apm/public/components/app/backend_detail_operations/backend_detail_operations_list/index.tsx rename to x-pack/plugins/apm/public/components/app/dependency_detail_operations/dependency_detail_operations_list/index.tsx index 5b2c624af48b4..cbfbcac2c2de5 100644 --- a/x-pack/plugins/apm/public/components/app/backend_detail_operations/backend_detail_operations_list/index.tsx +++ b/x-pack/plugins/apm/public/components/app/dependency_detail_operations/dependency_detail_operations_list/index.tsx @@ -21,36 +21,36 @@ import { EmptyMessage } from '../../../shared/empty_message'; import { ITableColumn, ManagedTable } from '../../../shared/managed_table'; import { getComparisonEnabled } from '../../../shared/time_comparison/get_comparison_enabled'; import { TruncateWithTooltip } from '../../../shared/truncate_with_tooltip'; -import { BackendOperationDetailLink } from '../../backend_operation_detail_view/backend_operation_detail_link'; +import { DependencyOperationDetailLink } from '../../dependency_operation_detail_view/dependency_operation_detail_link'; interface OperationStatisticsItem extends SpanMetricGroup { spanName: string; } function OperationLink({ spanName }: { spanName: string }) { - const { query } = useApmParams('/backends/operations'); + const { query } = useApmParams('/dependencies/operations'); return ( } + content={} /> ); } -export function BackendDetailOperationsList() { +export function DependencyDetailOperationsList() { const { query: { rangeFrom, rangeTo, - backendName, + dependencyName, environment, kuery, comparisonEnabled: urlComparisonEnabled, offset, }, - } = useApmParams('/backends/operations'); + } = useApmParams('/dependencies/operations'); const { core } = useApmPluginContext(); @@ -68,10 +68,10 @@ export function BackendDetailOperationsList() { const primaryStatsFetch = useFetcher( (callApmApi) => { - return callApmApi('GET /internal/apm/backends/operations', { + return callApmApi('GET /internal/apm/dependencies/operations', { params: { query: { - backendName, + dependencyName, start, end, environment, @@ -80,7 +80,7 @@ export function BackendDetailOperationsList() { }, }); }, - [backendName, start, end, environment, kuery] + [dependencyName, start, end, environment, kuery] ); const comparisonStatsFetch = useFetcher( @@ -90,10 +90,10 @@ export function BackendDetailOperationsList() { operations: [], }); } - return callApmApi('GET /internal/apm/backends/operations', { + return callApmApi('GET /internal/apm/dependencies/operations', { params: { query: { - backendName, + dependencyName, start, end, offset, @@ -103,16 +103,14 @@ export function BackendDetailOperationsList() { }, }); }, - [backendName, start, end, offset, environment, kuery, comparisonEnabled] + [dependencyName, start, end, offset, environment, kuery, comparisonEnabled] ); const columns: Array> = [ { name: i18n.translate( - 'xpack.apm.backendDetailOperationsList.spanNameColumnLabel', - { - defaultMessage: 'Span name', - } + 'xpack.apm.dependencyDetailOperationsList.spanNameColumnLabel', + { defaultMessage: 'Span name' } ), field: 'spanName', sortable: true, @@ -132,10 +130,8 @@ export function BackendDetailOperationsList() { const noItemsMessage = ( ); diff --git a/x-pack/plugins/apm/public/components/app/dependency_detail_operations/index.tsx b/x-pack/plugins/apm/public/components/app/dependency_detail_operations/index.tsx new file mode 100644 index 0000000000000..a7f2d26548dc2 --- /dev/null +++ b/x-pack/plugins/apm/public/components/app/dependency_detail_operations/index.tsx @@ -0,0 +1,16 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; +import { useDependencyDetailOperationsBreadcrumb } from '../../../hooks/use_dependency_detail_operations_breadcrumb'; +import { DependencyDetailOperationsList } from './dependency_detail_operations_list'; + +export function DependencyDetailOperations() { + useDependencyDetailOperationsBreadcrumb(); + + return ; +} diff --git a/x-pack/plugins/apm/public/components/app/backend_detail_overview/backend_detail_dependencies_table.tsx b/x-pack/plugins/apm/public/components/app/dependency_detail_overview/dependencies_detail_table.tsx similarity index 83% rename from x-pack/plugins/apm/public/components/app/backend_detail_overview/backend_detail_dependencies_table.tsx rename to x-pack/plugins/apm/public/components/app/dependency_detail_overview/dependencies_detail_table.tsx index 87733a69930d6..4a40e10fcf36d 100644 --- a/x-pack/plugins/apm/public/components/app/backend_detail_overview/backend_detail_dependencies_table.tsx +++ b/x-pack/plugins/apm/public/components/app/dependency_detail_overview/dependencies_detail_table.tsx @@ -17,10 +17,10 @@ import { useTimeRange } from '../../../hooks/use_time_range'; import { getComparisonEnabled } from '../../shared/time_comparison/get_comparison_enabled'; import { useApmPluginContext } from '../../../context/apm_plugin/use_apm_plugin_context'; -export function BackendDetailDependenciesTable() { +export function DependenciesDetailTable() { const { query: { - backendName, + dependencyName, rangeFrom, rangeTo, kuery, @@ -28,7 +28,7 @@ export function BackendDetailDependenciesTable() { comparisonEnabled: urlComparisonEnabled, offset, }, - } = useApmParams('/backends/overview'); + } = useApmParams('/dependencies/overview'); const { core } = useApmPluginContext(); @@ -41,10 +41,10 @@ export function BackendDetailDependenciesTable() { const { data, status } = useFetcher( (callApmApi) => { - return callApmApi('GET /internal/apm/backends/upstream_services', { + return callApmApi('GET /internal/apm/dependencies/upstream_services', { params: { query: { - backendName, + dependencyName, start, end, environment, @@ -58,7 +58,7 @@ export function BackendDetailDependenciesTable() { }, }); }, - [start, end, environment, offset, backendName, kuery, comparisonEnabled] + [start, end, environment, offset, dependencyName, kuery, comparisonEnabled] ); const dependencies = @@ -97,14 +97,13 @@ export function BackendDetailDependenciesTable() { return ( - + - + ); } diff --git a/x-pack/plugins/apm/public/components/app/backend_detail_view/index.tsx b/x-pack/plugins/apm/public/components/app/dependency_detail_view/index.tsx similarity index 70% rename from x-pack/plugins/apm/public/components/app/backend_detail_view/index.tsx rename to x-pack/plugins/apm/public/components/app/dependency_detail_view/index.tsx index 086e5dbea36a2..a586546cab835 100644 --- a/x-pack/plugins/apm/public/components/app/backend_detail_view/index.tsx +++ b/x-pack/plugins/apm/public/components/app/dependency_detail_view/index.tsx @@ -8,17 +8,17 @@ import React from 'react'; import { useBreadcrumb } from '../../../context/breadcrumbs/use_breadcrumb'; import { useApmParams } from '../../../hooks/use_apm_params'; import { useApmRouter } from '../../../hooks/use_apm_router'; -import { DependenciesInventoryTitle } from '../../routing/home'; -import { BackendDetailTemplate } from '../../routing/templates/backend_detail_template'; +import { DependenciesInventoryTitle } from '../../routing/home/dependencies'; +import { DependencyDetailTemplate } from '../../routing/templates/dependency_detail_template'; -export function BackendDetailView({ +export function DependencyDetailView({ children, }: { children: React.ReactChild; }) { const { query: { - backendName, + dependencyName, rangeFrom, rangeTo, refreshInterval, @@ -27,14 +27,14 @@ export function BackendDetailView({ kuery, comparisonEnabled, }, - } = useApmParams('/backends'); + } = useApmParams('/dependencies'); const apmRouter = useApmRouter(); useBreadcrumb([ { title: DependenciesInventoryTitle, - href: apmRouter.link('/backends/inventory', { + href: apmRouter.link('/dependencies/inventory', { query: { rangeFrom, rangeTo, @@ -47,10 +47,10 @@ export function BackendDetailView({ }), }, { - title: backendName, - href: apmRouter.link('/backends', { + title: dependencyName, + href: apmRouter.link('/dependencies', { query: { - backendName, + dependencyName, rangeFrom, rangeTo, refreshInterval, @@ -62,6 +62,5 @@ export function BackendDetailView({ }), }, ]); - - return {children}; + return {children}; } diff --git a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_detail_link.tsx b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependency_operation_detail_link.tsx similarity index 77% rename from x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_detail_link.tsx rename to x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependency_operation_detail_link.tsx index da3c4e0645f0c..9f6d8d9b27e61 100644 --- a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_detail_link.tsx +++ b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependency_operation_detail_link.tsx @@ -10,14 +10,14 @@ import { TypeOf } from '@kbn/typed-react-router-config'; import { useApmRouter } from '../../../hooks/use_apm_router'; import { ApmRoutes } from '../../routing/apm_route_config'; -type Query = TypeOf['query']; +type Query = TypeOf['query']; -export function BackendOperationDetailLink(query: Query) { +export function DependencyOperationDetailLink(query: Query) { const router = useApmRouter(); const { spanName } = query; - const link = router.link('/backends/operation', { + const link = router.link('/dependencies/operation', { query, }); diff --git a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_detail_trace_list.tsx b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependency_operation_detail_trace_list.tsx similarity index 87% rename from x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_detail_trace_list.tsx rename to x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependency_operation_detail_trace_list.tsx index d0069fcc7447f..cf51fe6cf75e5 100644 --- a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_detail_trace_list.tsx +++ b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependency_operation_detail_trace_list.tsx @@ -28,18 +28,18 @@ import { ITableColumn, ManagedTable } from '../../shared/managed_table'; import { ServiceLink } from '../../shared/service_link'; import { TimestampTooltip } from '../../shared/timestamp_tooltip'; -type BackendSpan = ValuesType< - APIReturnType<'GET /internal/apm/backends/operations/spans'>['spans'] +type DependencySpan = ValuesType< + APIReturnType<'GET /internal/apm/dependencies/operations/spans'>['spans'] >; -export function BackendOperationDetailTraceList() { +export function DependencyOperationDetailTraceList() { const router = useApmRouter(); const theme = useTheme(); const { query: { - backendName, + dependencyName, spanName, comparisonEnabled, environment, @@ -52,7 +52,7 @@ export function BackendOperationDetailTraceList() { sampleRangeFrom, sampleRangeTo, }, - } = useApmParams('/backends/operation'); + } = useApmParams('/dependencies/operation'); function getTraceLink({ transactionName, @@ -101,10 +101,10 @@ export function BackendOperationDetailTraceList() { const { start, end } = useTimeRange({ rangeFrom, rangeTo }); - const columns: Array> = [ + const columns: Array> = [ { name: i18n.translate( - 'xpack.apm.backendOperationDetailTraceListOutcomeColumn', + 'xpack.apm.dependencyOperationDetailTraceListOutcomeColumn', { defaultMessage: 'Outcome' } ), field: 'outcome', @@ -123,7 +123,7 @@ export function BackendOperationDetailTraceList() { }, { name: i18n.translate( - 'xpack.apm.backendOperationDetailTraceListTraceIdColumn', + 'xpack.apm.dependencyOperationDetailTraceListTraceIdColumn', { defaultMessage: 'Trace' } ), field: 'traceId', @@ -154,7 +154,7 @@ export function BackendOperationDetailTraceList() { }, { name: i18n.translate( - 'xpack.apm.backendOperationDetailTraceListServiceNameColumn', + 'xpack.apm.dependencyOperationDetailTraceListServiceNameColumn', { defaultMessage: 'Originating service' } ), field: 'serviceName', @@ -183,7 +183,7 @@ export function BackendOperationDetailTraceList() { }, { name: i18n.translate( - 'xpack.apm.backendOperationDetailTraceListTransactionNameColumn', + 'xpack.apm.dependencyOperationDetailTraceListTransactionNameColumn', { defaultMessage: 'Transaction name' } ), field: 'transactionName', @@ -211,7 +211,7 @@ export function BackendOperationDetailTraceList() { }, { name: i18n.translate( - 'xpack.apm.backendOperationDetailTraceListDurationColumn', + 'xpack.apm.dependencyOperationDetailTraceListDurationColumn', { defaultMessage: 'Duration' } ), field: 'duration', @@ -223,7 +223,7 @@ export function BackendOperationDetailTraceList() { }, { name: i18n.translate( - 'xpack.apm.backendOperationDetailTraceListTimestampColumn', + 'xpack.apm.dependencyOperationDetailTraceListTimestampColumn', { defaultMessage: 'Timestamp' } ), field: '@timestamp', @@ -237,10 +237,10 @@ export function BackendOperationDetailTraceList() { const { data = { spans: [] }, status } = useFetcher( (callApmApi) => { - return callApmApi('GET /internal/apm/backends/operations/spans', { + return callApmApi('GET /internal/apm/dependencies/operations/spans', { params: { query: { - backendName, + dependencyName, spanName, start, end, @@ -253,7 +253,7 @@ export function BackendOperationDetailTraceList() { }); }, [ - backendName, + dependencyName, spanName, start, end, @@ -269,7 +269,7 @@ export function BackendOperationDetailTraceList() { - {i18n.translate('xpack.apm.backendOperationDetailTraceList', { + {i18n.translate('xpack.apm.dependencyOperationDetailTraceList', { defaultMessage: 'Traces', })} diff --git a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_distribution_chart.tsx b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependendecy_operation_distribution_chart.tsx similarity index 82% rename from x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_distribution_chart.tsx rename to x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependendecy_operation_distribution_chart.tsx index 165b3da7ebe32..57fb735e0e982 100644 --- a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/backend_operation_distribution_chart.tsx +++ b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/dependendecy_operation_distribution_chart.tsx @@ -16,18 +16,18 @@ import { useTimeRange } from '../../../hooks/use_time_range'; import { DurationDistributionChartData } from '../../shared/charts/duration_distribution_chart'; import { DurationDistributionChartWithScrubber } from '../../shared/charts/duration_distribution_chart_with_scrubber'; -export function BackendOperationDistributionChart() { +export function DependencyOperationDistributionChart() { const { clearChartSelection, selectSampleFromChartSelection } = useSampleChartSelection(); - // there is no "current" event in the backend operation detail view + // there is no "current" event in the dependency operation detail view const markerCurrentEvent = undefined; const euiTheme = useTheme(); const { query: { - backendName, + dependencyName, spanName, environment, kuery, @@ -36,7 +36,7 @@ export function BackendOperationDistributionChart() { sampleRangeFrom = 0, sampleRangeTo = 0, }, - } = useApmParams('/backends/operation'); + } = useApmParams('/dependencies/operation'); const selection: [number, number] | undefined = sampleRangeFrom >= 0 && sampleRangeTo > 0 @@ -47,11 +47,11 @@ export function BackendOperationDistributionChart() { const { status, data } = useFetcher( (callApmApi) => { - return callApmApi('GET /internal/apm/backends/charts/distribution', { + return callApmApi('GET /internal/apm/dependencies/charts/distribution', { params: { query: { percentileThreshold: DEFAULT_PERCENTILE_THRESHOLD, - backendName, + dependencyName, spanName, environment, kuery, @@ -61,7 +61,7 @@ export function BackendOperationDistributionChart() { }, }); }, - [backendName, spanName, environment, kuery, start, end] + [dependencyName, spanName, environment, kuery, start, end] ); const hasData = @@ -73,20 +73,16 @@ export function BackendOperationDistributionChart() { areaSeriesColor: euiTheme.eui.euiColorVis1, histogram: data?.allSpansDistribution.overallHistogram ?? [], id: i18n.translate( - 'xpack.apm.backendOperationDistributionChart.allSpansLegendLabel', - { - defaultMessage: 'All spans', - } + 'xpack.apm.dependencyOperationDistributionChart.allSpansLegendLabel', + { defaultMessage: 'All spans' } ), }, { areaSeriesColor: euiTheme.eui.euiColorVis7, histogram: data?.failedSpansDistribution?.overallHistogram ?? [], id: i18n.translate( - 'xpack.apm.backendOperationDistributionChart.failedSpansLegendLabel', - { - defaultMessage: 'Failed spans', - } + 'xpack.apm.dependencyOperationDistributionChart.failedSpansLegendLabel', + { defaultMessage: 'Failed spans' } ), }, ]; diff --git a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/index.tsx b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/index.tsx similarity index 63% rename from x-pack/plugins/apm/public/components/app/backend_operation_detail_view/index.tsx rename to x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/index.tsx index 9e82f4a71ee69..c824a61f019b2 100644 --- a/x-pack/plugins/apm/public/components/app/backend_operation_detail_view/index.tsx +++ b/x-pack/plugins/apm/public/components/app/dependency_operation_detail_view/index.tsx @@ -10,47 +10,47 @@ import React from 'react'; import { ChartPointerEventContextProvider } from '../../../context/chart_pointer_event/chart_pointer_event_context'; import { useApmParams } from '../../../hooks/use_apm_params'; import { useApmRouter } from '../../../hooks/use_apm_router'; -import { useBackendDetailOperationsBreadcrumb } from '../../../hooks/use_backend_detail_operations_breadcrumb'; -import { BackendMetricCharts } from '../../shared/backend_metric_charts'; +import { useDependencyDetailOperationsBreadcrumb } from '../../../hooks/use_dependency_detail_operations_breadcrumb'; +import { DependencyMetricCharts } from '../../shared/dependency_metric_charts'; import { DetailViewHeader } from '../../shared/detail_view_header'; -import { BackendOperationDistributionChart } from './backend_operation_distribution_chart'; -import { BackendOperationDetailTraceList } from './backend_operation_detail_trace_list'; +import { DependencyOperationDistributionChart } from './dependendecy_operation_distribution_chart'; +import { DependencyOperationDetailTraceList } from './dependency_operation_detail_trace_list'; -export function BackendOperationDetailView() { +export function DependencyOperationDetailView() { const router = useApmRouter(); const { query: { spanName, ...query }, - } = useApmParams('/backends/operation'); + } = useApmParams('/dependencies/operation'); - useBackendDetailOperationsBreadcrumb(); + useDependencyDetailOperationsBreadcrumb(); return ( - + - + - + diff --git a/x-pack/plugins/apm/public/components/app/service_map/popover/backend_contents.tsx b/x-pack/plugins/apm/public/components/app/service_map/popover/dependency_contents.tsx similarity index 80% rename from x-pack/plugins/apm/public/components/app/service_map/popover/backend_contents.tsx rename to x-pack/plugins/apm/public/components/app/service_map/popover/dependency_contents.tsx index aa40ada254dd2..e7e678c4c528f 100644 --- a/x-pack/plugins/apm/public/components/app/service_map/popover/backend_contents.tsx +++ b/x-pack/plugins/apm/public/components/app/service_map/popover/dependency_contents.tsx @@ -21,14 +21,15 @@ import { ApmRoutes } from '../../../routing/apm_route_config'; import { StatsList } from './stats_list'; import { APIReturnType } from '../../../../services/rest/create_call_apm_api'; -type BackendReturn = APIReturnType<'GET /internal/apm/service-map/backend'>; +type DependencyReturn = + APIReturnType<'GET /internal/apm/service-map/dependency'>; -const INITIAL_STATE: Partial = { +const INITIAL_STATE: Partial = { currentPeriod: undefined, previousPeriod: undefined, }; -export function BackendContents({ +export function DependencyContents({ elementData, environment, start, @@ -45,15 +46,15 @@ export function BackendContents({ const apmRouter = useApmRouter(); - const backendName = nodeData.label; + const dependencyName = nodeData.label; const { data = INITIAL_STATE, status } = useFetcher( (callApmApi) => { - if (backendName) { - return callApmApi('GET /internal/apm/service-map/backend', { + if (dependencyName) { + return callApmApi('GET /internal/apm/service-map/dependency', { params: { query: { - backendName, + dependencyName, environment, start, end, @@ -66,16 +67,16 @@ export function BackendContents({ }); } }, - [environment, backendName, start, end, offset, comparisonEnabled] + [environment, dependencyName, start, end, offset, comparisonEnabled] ); const isLoading = status === FETCH_STATUS.LOADING; - const detailsUrl = backendName - ? apmRouter.link('/backends/overview', { + const detailsUrl = dependencyName + ? apmRouter.link('/dependencies/overview', { query: { ...query, - backendName, - } as TypeOf['query'], + dependencyName, + } as TypeOf['query'], }) : undefined; @@ -96,7 +97,7 @@ export function BackendContents({ trackEvent({ app: 'apm', metricType: METRIC_TYPE.CLICK, - metric: 'service_map_to_backend_detail', + metric: 'service_map_to_dependency_detail', }); }} > diff --git a/x-pack/plugins/apm/public/components/app/service_map/popover/index.tsx b/x-pack/plugins/apm/public/components/app/service_map/popover/index.tsx index 78543fa18cb7b..de00aa906b141 100644 --- a/x-pack/plugins/apm/public/components/app/service_map/popover/index.tsx +++ b/x-pack/plugins/apm/public/components/app/service_map/popover/index.tsx @@ -31,7 +31,7 @@ import { useTheme } from '../../../../hooks/use_theme'; import { useTraceExplorerEnabledSetting } from '../../../../hooks/use_trace_explorer_enabled_setting'; import { CytoscapeContext } from '../cytoscape'; import { getAnimationOptions, popoverWidth } from '../cytoscape_options'; -import { BackendContents } from './backend_contents'; +import { DependencyContents } from './dependency_contents'; import { EdgeContents } from './edge_contents'; import { ExternalsListContents } from './externals_list_contents'; import { ResourceContents } from './resource_contents'; @@ -64,7 +64,7 @@ function getContentsComponent( return EdgeContents; } - return BackendContents; + return DependencyContents; } export interface ContentsProps { diff --git a/x-pack/plugins/apm/public/components/app/service_map/popover/popover.stories.tsx b/x-pack/plugins/apm/public/components/app/service_map/popover/popover.stories.tsx index 44429ad67a141..0f96b77dcf1dc 100644 --- a/x-pack/plugins/apm/public/components/app/service_map/popover/popover.stories.tsx +++ b/x-pack/plugins/apm/public/components/app/service_map/popover/popover.stories.tsx @@ -99,7 +99,7 @@ const stories: Meta = { }; export default stories; -export const Backend: Story = () => { +export const Dependency: Story = () => { return ( = () => { /> ); }; -Backend.args = { +Dependency.args = { nodeData: { 'span.subtype': 'postgresql', 'span.destination.service.resource': 'postgresql', @@ -119,7 +119,7 @@ Backend.args = { }, }; -export const BackendWithLongTitle: Story = () => { +export const DependencyWithLongTitle: Story = () => { return ( = () => { /> ); }; -BackendWithLongTitle.args = { +DependencyWithLongTitle.args = { nodeData: { 'span.subtype': 'http', 'span.destination.service.resource': diff --git a/x-pack/plugins/apm/public/components/app/service_map/popover/popover.test.tsx b/x-pack/plugins/apm/public/components/app/service_map/popover/popover.test.tsx index 417d239a852a8..6e4d6a9e6730c 100644 --- a/x-pack/plugins/apm/public/components/app/service_map/popover/popover.test.tsx +++ b/x-pack/plugins/apm/public/components/app/service_map/popover/popover.test.tsx @@ -10,12 +10,13 @@ import { render, screen, waitFor } from '@testing-library/react'; import React from 'react'; import * as stories from './popover.stories'; -const { Backend, ExternalsList, Resource, Service } = composeStories(stories); +const { Dependency, ExternalsList, Resource, Service } = + composeStories(stories); describe('Popover', () => { - describe('with backend data', () => { + describe('with dependency data', () => { it('renders a dependency link', async () => { - render(); + render(); await waitFor(() => { expect( diff --git a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx index 7fb66b60a1788..7bfdfb59a9c7d 100644 --- a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx +++ b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_dependencies_table/index.tsx @@ -16,7 +16,7 @@ import { useApmServiceContext } from '../../../../context/apm_service/use_apm_se import { useApmParams } from '../../../../hooks/use_apm_params'; import { useFetcher } from '../../../../hooks/use_fetcher'; import { useTimeRange } from '../../../../hooks/use_time_range'; -import { BackendLink } from '../../../shared/backend_link'; +import { DependencyLink } from '../../../shared/dependency_link'; import { DependenciesTable } from '../../../shared/dependencies_table'; import { ServiceLink } from '../../../shared/service_link'; @@ -83,12 +83,12 @@ export function ServiceOverviewDependenciesTable({ const { location } = dependency; const name = getNodeName(location); const itemLink = - location.type === NodeType.backend ? ( - diff --git a/x-pack/plugins/apm/public/components/app/transaction_details/waterfall_with_summary/waterfall_container/waterfall/span_flyout/sticky_span_properties.tsx b/x-pack/plugins/apm/public/components/app/transaction_details/waterfall_with_summary/waterfall_container/waterfall/span_flyout/sticky_span_properties.tsx index ecf121b777ff5..0b500cb79a746 100644 --- a/x-pack/plugins/apm/public/components/app/transaction_details/waterfall_with_summary/waterfall_container/waterfall/span_flyout/sticky_span_properties.tsx +++ b/x-pack/plugins/apm/public/components/app/transaction_details/waterfall_with_summary/waterfall_container/waterfall/span_flyout/sticky_span_properties.tsx @@ -19,7 +19,7 @@ import { NOT_AVAILABLE_LABEL } from '../../../../../../../../common/i18n'; import { Span } from '../../../../../../../../typings/es_schemas/ui/span'; import { Transaction } from '../../../../../../../../typings/es_schemas/ui/transaction'; import { useAnyOfApmParams } from '../../../../../../../hooks/use_apm_params'; -import { BackendLink } from '../../../../../../shared/backend_link'; +import { DependencyLink } from '../../../../../../shared/dependency_link'; import { TransactionDetailLink } from '../../../../../../shared/links/apm/transaction_detail_link'; import { ServiceLink } from '../../../../../../shared/service_link'; import { StickyProperties } from '../../../../../../shared/sticky_properties'; @@ -112,10 +112,10 @@ export function StickySpanProperties({ span, transaction }: Props) { ), fieldName: SPAN_DESTINATION_SERVICE_RESOURCE, val: ( - diff --git a/x-pack/plugins/apm/public/components/routing/app_root.tsx b/x-pack/plugins/apm/public/components/routing/app_root.tsx index 595b3c527ab20..0c8511cd1b277 100644 --- a/x-pack/plugins/apm/public/components/routing/app_root.tsx +++ b/x-pack/plugins/apm/public/components/routing/app_root.tsx @@ -39,7 +39,7 @@ import { apmRouter } from './apm_route_config'; import { TrackPageview } from './track_pageview'; import { RedirectWithDefaultEnvironment } from '../shared/redirect_with_default_environment'; import { RedirectWithOffset } from '../shared/redirect_with_offset'; -import { RedirectBackendsToBackendInventory } from './home/redirect_backends_to_backend_inventory'; +import { RedirectDependenciesToDependenciesInventory } from './home/redirect_dependencies_to_dependencies_inventory'; const storage = new Storage(localStorage); @@ -66,7 +66,7 @@ export function ApmAppRoot({ - + @@ -93,7 +93,7 @@ export function ApmAppRoot({ - + diff --git a/x-pack/plugins/apm/public/components/routing/home/dependencies.tsx b/x-pack/plugins/apm/public/components/routing/home/dependencies.tsx new file mode 100644 index 0000000000000..a20634c31912c --- /dev/null +++ b/x-pack/plugins/apm/public/components/routing/home/dependencies.tsx @@ -0,0 +1,90 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { i18n } from '@kbn/i18n'; +import { toBooleanRt, toNumberRt } from '@kbn/io-ts-utils'; +import { Outlet } from '@kbn/typed-react-router-config'; +import * as t from 'io-ts'; +import React from 'react'; +import { Redirect } from 'react-router-dom'; +import qs from 'query-string'; +import { page } from '.'; +import { offsetRt } from '../../../../common/comparison_rt'; +import { DependencyDetailOperations } from '../../app/dependency_detail_operations'; +import { DependencyDetailOverview } from '../../app/dependency_detail_overview'; +import { DependencyDetailView } from '../../app/dependency_detail_view'; +import { DependenciesInventory } from '../../app/dependencies_inventory'; +import { DependencyOperationDetailView } from '../../app/dependency_operation_detail_view'; +import { useApmParams } from '../../../hooks/use_apm_params'; + +export const DependenciesInventoryTitle = i18n.translate( + 'xpack.apm.views.dependenciesInventory.title', + { defaultMessage: 'Dependencies' } +); + +function RedirectDependenciesToDependenciesOverview() { + const { query } = useApmParams('/dependencies'); + const search = qs.stringify(query); + return ; +} + +export const dependencies = { + ...page({ + path: '/dependencies/inventory', + title: DependenciesInventoryTitle, + element: , + params: t.partial({ + query: t.intersection([ + t.type({ + comparisonEnabled: toBooleanRt, + }), + offsetRt, + ]), + }), + }), + '/dependencies': { + element: ( + + + + ), + params: t.partial({ + query: t.intersection([ + t.type({ + comparisonEnabled: toBooleanRt, + dependencyName: t.string, + }), + offsetRt, + ]), + }), + children: { + '/dependencies': { + element: , + }, + '/dependencies/operations': { + element: , + }, + '/dependencies/operation': { + params: t.type({ + query: t.intersection([ + t.type({ + spanName: t.string, + }), + t.partial({ + sampleRangeFrom: toNumberRt, + sampleRangeTo: toNumberRt, + }), + ]), + }), + element: , + }, + '/dependencies/overview': { + element: , + }, + }, + }, +}; diff --git a/x-pack/plugins/apm/public/components/routing/home/index.tsx b/x-pack/plugins/apm/public/components/routing/home/index.tsx index 8642561fd19e8..6b9a996890d9a 100644 --- a/x-pack/plugins/apm/public/components/routing/home/index.tsx +++ b/x-pack/plugins/apm/public/components/routing/home/index.tsx @@ -5,35 +5,30 @@ * 2.0. */ import { i18n } from '@kbn/i18n'; +import { toBooleanRt, toNumberRt } from '@kbn/io-ts-utils'; import { Outlet, Route } from '@kbn/typed-react-router-config'; import * as t from 'io-ts'; import React, { ComponentProps } from 'react'; -import { toBooleanRt, toNumberRt } from '@kbn/io-ts-utils'; +import { offsetRt } from '../../../../common/comparison_rt'; import { ENVIRONMENT_ALL } from '../../../../common/environment_filter_values'; import { environmentRt } from '../../../../common/environment_rt'; import { TraceSearchType } from '../../../../common/trace_explorer'; -import { BackendDetailOverview } from '../../app/backend_detail_overview'; -import { BackendInventory } from '../../app/backend_inventory'; +import { TimeRangeMetadataContextProvider } from '../../../context/time_range_metadata/time_range_metadata_context'; import { Breadcrumb } from '../../app/breadcrumb'; import { ServiceInventory } from '../../app/service_inventory'; import { ServiceMapHome } from '../../app/service_map'; -import { TraceOverview } from '../../app/trace_overview'; -import { TraceExplorer } from '../../app/trace_explorer'; import { TopTracesOverview } from '../../app/top_traces_overview'; +import { TraceExplorer } from '../../app/trace_explorer'; +import { TraceOverview } from '../../app/trace_overview'; +import { TransactionTab } from '../../app/transaction_details/waterfall_with_summary/transaction_tabs'; +import { RedirectTo } from '../redirect_to'; +import { ServiceGroupsRedirect } from '../service_groups_redirect'; import { ApmMainTemplate } from '../templates/apm_main_template'; import { ServiceGroupTemplate } from '../templates/service_group_template'; -import { ServiceGroupsRedirect } from '../service_groups_redirect'; -import { RedirectTo } from '../redirect_to'; -import { offsetRt } from '../../../../common/comparison_rt'; -import { TransactionTab } from '../../app/transaction_details/waterfall_with_summary/transaction_tabs'; -import { BackendDetailOperations } from '../../app/backend_detail_operations'; -import { BackendDetailView } from '../../app/backend_detail_view'; -import { RedirectPathBackendDetailView } from './redirect_path_backend_detail_view'; -import { RedirectBackendsToBackendDetailOverview } from './redirect_backends_to_backend_detail_view'; -import { BackendOperationDetailView } from '../../app/backend_operation_detail_view'; -import { TimeRangeMetadataContextProvider } from '../../../context/time_range_metadata/time_range_metadata_context'; +import { dependencies } from './dependencies'; +import { legacyBackends } from './legacy_backends'; -function page< +export function page< TPath extends string, TChildren extends Record | undefined = undefined, TParams extends t.Type | undefined = undefined @@ -136,13 +131,6 @@ export const ServiceMapTitle = i18n.translate( } ); -export const DependenciesInventoryTitle = i18n.translate( - 'xpack.apm.views.dependenciesInventory.title', - { - defaultMessage: 'Dependencies', - } -); - export const DependenciesOperationsTitle = i18n.translate( 'xpack.apm.views.dependenciesOperations.title', { @@ -242,74 +230,8 @@ export const home = { }, }, }), - ...page({ - path: '/backends/inventory', - title: DependenciesInventoryTitle, - element: , - params: t.partial({ - query: t.intersection([ - t.type({ - comparisonEnabled: toBooleanRt, - }), - offsetRt, - ]), - }), - }), - '/backends/{backendName}/overview': { - element: , - params: t.type({ - path: t.type({ - backendName: t.string, - }), - }), - }, - '/backends': { - element: , - params: t.partial({ - query: t.intersection([ - t.type({ - comparisonEnabled: toBooleanRt, - backendName: t.string, - }), - offsetRt, - ]), - }), - children: { - '/backends': { - element: ( - - - - ), - children: { - '/backends/operations': { - element: , - }, - - '/backends/operation': { - params: t.type({ - query: t.intersection([ - t.type({ - spanName: t.string, - }), - t.partial({ - sampleRangeFrom: toNumberRt, - sampleRangeTo: toNumberRt, - }), - ]), - }), - element: , - }, - '/backends/overview': { - element: , - }, - '/backends': { - element: , - }, - }, - }, - }, - }, + ...dependencies, + ...legacyBackends, '/': { element: ( diff --git a/x-pack/plugins/apm/public/components/routing/home/legacy_backends.tsx b/x-pack/plugins/apm/public/components/routing/home/legacy_backends.tsx new file mode 100644 index 0000000000000..90050f9dc46b8 --- /dev/null +++ b/x-pack/plugins/apm/public/components/routing/home/legacy_backends.tsx @@ -0,0 +1,82 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import { toBooleanRt, toNumberRt } from '@kbn/io-ts-utils'; +import { Outlet } from '@kbn/typed-react-router-config'; +import * as t from 'io-ts'; +import React from 'react'; +import { Redirect } from 'react-router-dom'; +import qs from 'query-string'; +import { offsetRt } from '../../../../common/comparison_rt'; +import { useApmParams } from '../../../hooks/use_apm_params'; + +function RedirectBackends({ to }: { to: string }) { + const { query } = useApmParams('/backends/*'); + const search = qs.stringify(query); + return ; +} + +function RedirectBackendsOverviewToDependenciesOverview() { + const { + path: { dependencyName }, + query, + } = useApmParams('/backends/{dependencyName}/overview'); + + const search = qs.stringify({ ...query, dependencyName }); + + return ; +} + +export const legacyBackends = { + '/backends/inventory': { + element: , + params: t.partial({ + query: t.intersection([ + t.type({ comparisonEnabled: toBooleanRt }), + offsetRt, + ]), + }), + }, + '/backends/{dependencyName}/overview': { + element: , + params: t.type({ path: t.type({ dependencyName: t.string }) }), + }, + '/backends': { + element: , + params: t.partial({ + query: t.intersection([ + t.type({ + comparisonEnabled: toBooleanRt, + dependencyName: t.string, + }), + offsetRt, + ]), + }), + children: { + '/backends': { + element: , + }, + '/backends/operations': { + element: , + }, + '/backends/operation': { + params: t.type({ + query: t.intersection([ + t.type({ spanName: t.string }), + t.partial({ + sampleRangeFrom: toNumberRt, + sampleRangeTo: toNumberRt, + }), + ]), + }), + element: , + }, + '/backends/overview': { + element: , + }, + }, + }, +}; diff --git a/x-pack/plugins/apm/public/components/routing/home/redirect_backends_to_backend_detail_view.tsx b/x-pack/plugins/apm/public/components/routing/home/redirect_backends_to_backend_detail_view.tsx deleted file mode 100644 index 34dfde53d210c..0000000000000 --- a/x-pack/plugins/apm/public/components/routing/home/redirect_backends_to_backend_detail_view.tsx +++ /dev/null @@ -1,19 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import qs from 'query-string'; -import React from 'react'; -import { Redirect } from 'react-router-dom'; -import { useApmParams } from '../../../hooks/use_apm_params'; - -export function RedirectBackendsToBackendDetailOverview() { - const { query } = useApmParams('/backends'); - - const search = qs.stringify(query); - - return ; -} diff --git a/x-pack/plugins/apm/public/components/routing/home/redirect_backends_to_backend_inventory.tsx b/x-pack/plugins/apm/public/components/routing/home/redirect_dependencies_to_dependencies_inventory.tsx similarity index 84% rename from x-pack/plugins/apm/public/components/routing/home/redirect_backends_to_backend_inventory.tsx rename to x-pack/plugins/apm/public/components/routing/home/redirect_dependencies_to_dependencies_inventory.tsx index 654b63a310d2f..4b2cdd257d7a4 100644 --- a/x-pack/plugins/apm/public/components/routing/home/redirect_backends_to_backend_inventory.tsx +++ b/x-pack/plugins/apm/public/components/routing/home/redirect_dependencies_to_dependencies_inventory.tsx @@ -9,7 +9,7 @@ import { useLocation, Redirect } from 'react-router-dom'; import qs from 'query-string'; import React from 'react'; -export function RedirectBackendsToBackendInventory({ +export function RedirectDependenciesToDependenciesInventory({ children, }: { children: React.ReactElement; @@ -19,7 +19,7 @@ export function RedirectBackendsToBackendInventory({ const query = qs.parse(location.search); const normalizedPathname = location.pathname.replace(/\/$/, ''); - if (normalizedPathname === '/backends' && !('backendName' in query)) { + if (normalizedPathname === '/dependencies' && !('dependencyName' in query)) { return ( ; -} diff --git a/x-pack/plugins/apm/public/components/routing/templates/backend_detail_template.tsx b/x-pack/plugins/apm/public/components/routing/templates/dependency_detail_template.tsx similarity index 74% rename from x-pack/plugins/apm/public/components/routing/templates/backend_detail_template.tsx rename to x-pack/plugins/apm/public/components/routing/templates/dependency_detail_template.tsx index 1ed738cba2e1f..57ff4ba98a04a 100644 --- a/x-pack/plugins/apm/public/components/routing/templates/backend_detail_template.tsx +++ b/x-pack/plugins/apm/public/components/routing/templates/dependency_detail_template.tsx @@ -19,18 +19,18 @@ import { SearchBar } from '../../shared/search_bar'; import { getKueryBarBoolFilter, kueryBarPlaceholder, -} from '../../../../common/backends'; +} from '../../../../common/dependencies'; import { useOperationBreakdownEnabledSetting } from '../../../hooks/use_operations_breakdown_enabled_setting'; interface Props { children: React.ReactNode; } -export function BackendDetailTemplate({ children }: Props) { +export function DependencyDetailTemplate({ children }: Props) { const { query, - query: { backendName, rangeFrom, rangeTo, environment }, - } = useApmParams('/backends'); + query: { dependencyName, rangeFrom, rangeTo, environment }, + } = useApmParams('/dependencies'); const router = useApmRouter(); @@ -43,52 +43,53 @@ export function BackendDetailTemplate({ children }: Props) { const kueryBarBoolFilter = getKueryBarBoolFilter({ environment, - backendName, + dependencyName, }); - const backendMetadataFetch = useFetcher( + const dependencyMetadataFetch = useFetcher( (callApmApi) => { if (!start || !end) { return; } - return callApmApi('GET /internal/apm/backends/metadata', { + return callApmApi('GET /internal/apm/dependencies/metadata', { params: { query: { - backendName, + dependencyName, start, end, }, }, }); }, - [backendName, start, end] + [dependencyName, start, end] ); - const { data: { metadata } = {} } = backendMetadataFetch; + const { data: { metadata } = {} } = dependencyMetadataFetch; const tabs = isOperationsBreakdownFeatureEnabled ? [ { key: 'overview', - href: router.link('/backends/overview', { + href: router.link('/dependencies/overview', { query, }), - label: i18n.translate('xpack.apm.backendDetailOverview.title', { + label: i18n.translate('xpack.apm.DependencyDetailOverview.title', { defaultMessage: 'Overview', }), - isSelected: path === '/backends/overview', + isSelected: path === '/dependencies/overview', }, { key: 'operations', - href: router.link('/backends/operations', { + href: router.link('/dependencies/operations', { query, }), - label: i18n.translate('xpack.apm.backendDetailOperations.title', { + label: i18n.translate('xpack.apm.DependencyDetailOperations.title', { defaultMessage: 'Operations', }), isSelected: - path === '/backends/operations' || path === '/backends/operation', + path === '/dependencies/operations' || + path === '/dependencies/operation', }, ] : []; @@ -101,7 +102,7 @@ export function BackendDetailTemplate({ children }: Props) { -

    {backendName}

    +

    {dependencyName}

    diff --git a/x-pack/plugins/apm/public/components/shared/charts/timeseries_chart.tsx b/x-pack/plugins/apm/public/components/shared/charts/timeseries_chart.tsx index 1773f0a612729..7402f42e82a1b 100644 --- a/x-pack/plugins/apm/public/components/shared/charts/timeseries_chart.tsx +++ b/x-pack/plugins/apm/public/components/shared/charts/timeseries_chart.tsx @@ -91,7 +91,11 @@ export function TimeseriesChart({ const chartTheme = useChartTheme(); const { query: { comparisonEnabled, offset }, - } = useAnyOfApmParams('/services', '/backends/*', '/services/{serviceName}'); + } = useAnyOfApmParams( + '/services', + '/dependencies/*', + '/services/{serviceName}' + ); const anomalyChartTimeseries = getChartAnomalyTimeseries({ anomalyTimeseries, diff --git a/x-pack/plugins/apm/public/components/shared/backend_link.stories.tsx b/x-pack/plugins/apm/public/components/shared/dependency_link.stories.tsx similarity index 78% rename from x-pack/plugins/apm/public/components/shared/backend_link.stories.tsx rename to x-pack/plugins/apm/public/components/shared/dependency_link.stories.tsx index 1eca596a86c67..f61e08ce0364c 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_link.stories.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependency_link.stories.tsx @@ -8,13 +8,13 @@ import { Story } from '@storybook/react'; import React, { ComponentProps, ComponentType } from 'react'; import { MockApmPluginContextWrapper } from '../../context/apm_plugin/mock_apm_plugin_context'; -import { BackendLink } from './backend_link'; +import { DependencyLink } from './dependency_link'; -type Args = ComponentProps; +type Args = ComponentProps; export default { - title: 'shared/BackendLink', - component: BackendLink, + title: 'shared/DependencyLink', + component: DependencyLink, decorators: [ (StoryComponent: ComponentType) => { return ( @@ -27,11 +27,11 @@ export default { }; export const Example: Story = (args) => { - return ; + return ; }; Example.args = { query: { - backendName: 'postgres', + dependencyName: 'postgres', environment: 'ENVIRONMENT_ALL', kuery: '', rangeFrom: 'now-15m', diff --git a/x-pack/plugins/apm/public/components/shared/backend_link.test.tsx b/x-pack/plugins/apm/public/components/shared/dependency_link.test.tsx similarity index 85% rename from x-pack/plugins/apm/public/components/shared/backend_link.test.tsx rename to x-pack/plugins/apm/public/components/shared/dependency_link.test.tsx index 683fec3a41725..22576b545ada4 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_link.test.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependency_link.test.tsx @@ -8,11 +8,11 @@ import { composeStories } from '@storybook/testing-react'; import { render } from '@testing-library/react'; import React from 'react'; -import * as stories from './backend_link.stories'; +import * as stories from './dependency_link.stories'; const { Example } = composeStories(stories); -describe('BackendLink', () => { +describe('DependencyLink', () => { it('renders', () => { expect(() => render()).not.toThrowError(); }); diff --git a/x-pack/plugins/apm/public/components/shared/backend_link.tsx b/x-pack/plugins/apm/public/components/shared/dependency_link.tsx similarity index 81% rename from x-pack/plugins/apm/public/components/shared/backend_link.tsx rename to x-pack/plugins/apm/public/components/shared/dependency_link.tsx index ac93228c76bcd..77901974e81d2 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_link.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependency_link.tsx @@ -16,24 +16,19 @@ import { SpanIcon } from './span_icon'; const StyledLink = euiStyled(EuiLink)`${truncate('100%')};`; -interface BackendLinkProps { - query: TypeOf['query']; +interface Props { + query: TypeOf['query']; subtype?: string; type?: string; onClick?: React.ComponentProps['onClick']; } -export function BackendLink({ - query, - subtype, - type, - onClick, -}: BackendLinkProps) { +export function DependencyLink({ query, subtype, type, onClick }: Props) { const { link } = useApmRouter(); return ( - {query.backendName} + {query.dependencyName}
    diff --git a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_error_rate_chart.tsx b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_failed_transaction_rate_chart.tsx similarity index 88% rename from x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_error_rate_chart.tsx rename to x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_failed_transaction_rate_chart.tsx index 1d8834157f4ca..b5fbcb0608956 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_error_rate_chart.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_failed_transaction_rate_chart.tsx @@ -18,16 +18,16 @@ import { getTimeSeriesColor, } from '../charts/helper/get_timeseries_color'; import { getComparisonChartTheme } from '../time_comparison/get_comparison_chart_theme'; -import { BackendMetricChartsRouteParams } from './backend_metric_charts_route_params'; +import { DependencyMetricChartsRouteParams } from './dependency_metric_charts_route_params'; import { useSearchServiceDestinationMetrics } from '../../../context/time_range_metadata/use_search_service_destination_metrics'; function yLabelFormat(y?: number | null) { return asPercent(y || 0, 1); } -export function BackendFailedTransactionRateChart({ +export function DependencyFailedTransactionRateChart({ height, - backendName, + dependencyName, kuery, environment, rangeFrom, @@ -37,7 +37,7 @@ export function BackendFailedTransactionRateChart({ spanName, }: { height: number; -} & BackendMetricChartsRouteParams) { +} & DependencyMetricChartsRouteParams) { const { start, end } = useTimeRange({ rangeFrom, rangeTo }); const comparisonChartTheme = getComparisonChartTheme(); @@ -51,10 +51,10 @@ export function BackendFailedTransactionRateChart({ return; } - return callApmApi('GET /internal/apm/backends/charts/error_rate', { + return callApmApi('GET /internal/apm/dependencies/charts/error_rate', { params: { query: { - backendName, + dependencyName, start, end, offset: @@ -70,7 +70,7 @@ export function BackendFailedTransactionRateChart({ }); }, [ - backendName, + dependencyName, start, end, offset, @@ -96,7 +96,7 @@ export function BackendFailedTransactionRateChart({ data: data.currentTimeseries, type: 'linemark', color: currentPeriodColor, - title: i18n.translate('xpack.apm.backendErrorRateChart.chartTitle', { + title: i18n.translate('xpack.apm.dependencyErrorRateChart.chartTitle', { defaultMessage: 'Failed transaction rate', }), }); diff --git a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_latency_chart.tsx b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_latency_chart.tsx similarity index 89% rename from x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_latency_chart.tsx rename to x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_latency_chart.tsx index 03a6fbc81e0fb..3932bbd6e2a54 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_latency_chart.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_latency_chart.tsx @@ -22,12 +22,12 @@ import { getTimeSeriesColor, } from '../charts/helper/get_timeseries_color'; import { getComparisonChartTheme } from '../time_comparison/get_comparison_chart_theme'; -import { BackendMetricChartsRouteParams } from './backend_metric_charts_route_params'; +import { DependencyMetricChartsRouteParams } from './dependency_metric_charts_route_params'; import { useSearchServiceDestinationMetrics } from '../../../context/time_range_metadata/use_search_service_destination_metrics'; -export function BackendLatencyChart({ +export function DependencyLatencyChart({ height, - backendName, + dependencyName, rangeFrom, rangeTo, kuery, @@ -35,7 +35,7 @@ export function BackendLatencyChart({ offset, comparisonEnabled, spanName, -}: { height: number } & BackendMetricChartsRouteParams) { +}: { height: number } & DependencyMetricChartsRouteParams) { const { start, end } = useTimeRange({ rangeFrom, rangeTo }); const comparisonChartTheme = getComparisonChartTheme(); @@ -49,10 +49,10 @@ export function BackendLatencyChart({ return; } - return callApmApi('GET /internal/apm/backends/charts/latency', { + return callApmApi('GET /internal/apm/dependencies/charts/latency', { params: { query: { - backendName, + dependencyName, start, end, offset: @@ -68,7 +68,7 @@ export function BackendLatencyChart({ }); }, [ - backendName, + dependencyName, start, end, offset, @@ -95,7 +95,7 @@ export function BackendLatencyChart({ data: data.currentTimeseries, type: 'linemark', color: currentPeriodColor, - title: i18n.translate('xpack.apm.backendLatencyChart.chartTitle', { + title: i18n.translate('xpack.apm.dependencyLatencyChart.chartTitle', { defaultMessage: 'Latency', }), }); diff --git a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_metric_charts_route_params.ts b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_metric_charts_route_params.ts similarity index 81% rename from x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_metric_charts_route_params.ts rename to x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_metric_charts_route_params.ts index 7c947fe81db06..f348a257462e0 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_metric_charts_route_params.ts +++ b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_metric_charts_route_params.ts @@ -7,12 +7,12 @@ import { TypeOf } from '@kbn/typed-react-router-config'; import { ApmRoutes } from '../../routing/apm_route_config'; -export type BackendMetricChartsRouteParams = Pick< +export type DependencyMetricChartsRouteParams = Pick< { spanName?: string } & TypeOf< ApmRoutes, - '/backends/operation' | '/backends/overview' + '/dependencies/operation' | '/dependencies/overview' >['query'], - | 'backendName' + | 'dependencyName' | 'comparisonEnabled' | 'spanName' | 'rangeFrom' diff --git a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_throughput_chart.tsx b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_throughput_chart.tsx similarity index 86% rename from x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_throughput_chart.tsx rename to x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_throughput_chart.tsx index bd461e49eeaf6..20a906ab291f3 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/backend_throughput_chart.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/dependency_throughput_chart.tsx @@ -18,12 +18,12 @@ import { getTimeSeriesColor, } from '../charts/helper/get_timeseries_color'; import { getComparisonChartTheme } from '../time_comparison/get_comparison_chart_theme'; -import { BackendMetricChartsRouteParams } from './backend_metric_charts_route_params'; +import { DependencyMetricChartsRouteParams } from './dependency_metric_charts_route_params'; import { useSearchServiceDestinationMetrics } from '../../../context/time_range_metadata/use_search_service_destination_metrics'; -export function BackendThroughputChart({ +export function DependencyThroughputChart({ height, - backendName, + dependencyName, rangeFrom, rangeTo, kuery, @@ -31,7 +31,7 @@ export function BackendThroughputChart({ offset, comparisonEnabled, spanName, -}: { height: number } & BackendMetricChartsRouteParams) { +}: { height: number } & DependencyMetricChartsRouteParams) { const { start, end } = useTimeRange({ rangeFrom, rangeTo }); const comparisonChartTheme = getComparisonChartTheme(); @@ -45,10 +45,10 @@ export function BackendThroughputChart({ return; } - return callApmApi('GET /internal/apm/backends/charts/throughput', { + return callApmApi('GET /internal/apm/dependencies/charts/throughput', { params: { query: { - backendName, + dependencyName, start, end, offset: @@ -64,7 +64,7 @@ export function BackendThroughputChart({ }); }, [ - backendName, + dependencyName, start, end, offset, @@ -91,9 +91,10 @@ export function BackendThroughputChart({ data: data.currentTimeseries, type: 'linemark', color: currentPeriodColor, - title: i18n.translate('xpack.apm.backendThroughputChart.chartTitle', { - defaultMessage: 'Throughput', - }), + title: i18n.translate( + 'xpack.apm.dependencyThroughputChart.chartTitle', + { defaultMessage: 'Throughput' } + ), }); } diff --git a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/index.tsx b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/index.tsx similarity index 63% rename from x-pack/plugins/apm/public/components/shared/backend_metric_charts/index.tsx rename to x-pack/plugins/apm/public/components/shared/dependency_metric_charts/index.tsx index c13ddde4ff1fb..36004506c8438 100644 --- a/x-pack/plugins/apm/public/components/shared/backend_metric_charts/index.tsx +++ b/x-pack/plugins/apm/public/components/shared/dependency_metric_charts/index.tsx @@ -10,18 +10,18 @@ import { i18n } from '@kbn/i18n'; import React from 'react'; import { useAnyOfApmParams } from '../../../hooks/use_apm_params'; import { useBreakpoints } from '../../../hooks/use_breakpoints'; -import { BackendFailedTransactionRateChart } from './backend_error_rate_chart'; -import { BackendLatencyChart } from './backend_latency_chart'; -import { BackendMetricChartsRouteParams } from './backend_metric_charts_route_params'; -import { BackendThroughputChart } from './backend_throughput_chart'; +import { DependencyFailedTransactionRateChart } from './dependency_failed_transaction_rate_chart'; +import { DependencyLatencyChart } from './dependency_latency_chart'; +import { DependencyMetricChartsRouteParams } from './dependency_metric_charts_route_params'; +import { DependencyThroughputChart } from './dependency_throughput_chart'; -export function BackendMetricCharts() { +export function DependencyMetricCharts() { const largeScreenOrSmaller = useBreakpoints().isLarge; const { query, query: { - backendName, + dependencyName, rangeFrom, rangeTo, kuery, @@ -29,12 +29,12 @@ export function BackendMetricCharts() { comparisonEnabled, offset, }, - } = useAnyOfApmParams('/backends/overview', '/backends/operation'); + } = useAnyOfApmParams('/dependencies/overview', '/dependencies/operation'); const spanName = 'spanName' in query ? query.spanName : undefined; - const props: BackendMetricChartsRouteParams = { - backendName, + const props: DependencyMetricChartsRouteParams = { + dependencyName, rangeFrom, rangeTo, kuery, @@ -53,24 +53,25 @@ export function BackendMetricCharts() {

    - {i18n.translate('xpack.apm.backendDetailLatencyChartTitle', { + {i18n.translate('xpack.apm.dependencyDetailLatencyChartTitle', { defaultMessage: 'Latency', })}

    - +

    - {i18n.translate('xpack.apm.backendDetailThroughputChartTitle', { - defaultMessage: 'Throughput', - })} + {i18n.translate( + 'xpack.apm.dependencyDetailThroughputChartTitle', + { defaultMessage: 'Throughput' } + )}

    - +
    @@ -78,12 +79,12 @@ export function BackendMetricCharts() {

    {i18n.translate( - 'xpack.apm.backendDetailFailedTransactionRateChartTitle', + 'xpack.apm.dependencyDetailFailedTransactionRateChartTitle', { defaultMessage: 'Failed transaction rate' } )}

    - +
    diff --git a/x-pack/plugins/apm/public/components/shared/is_route_with_time_range.ts b/x-pack/plugins/apm/public/components/shared/is_route_with_time_range.ts index 81aa567140ed4..68e5d7be00783 100644 --- a/x-pack/plugins/apm/public/components/shared/is_route_with_time_range.ts +++ b/x-pack/plugins/apm/public/components/shared/is_route_with_time_range.ts @@ -20,8 +20,8 @@ export function isRouteWithTimeRange({ route.path === '/services' || route.path === '/traces' || route.path === '/service-map' || - route.path === '/backends' || - route.path === '/backends/inventory' || + route.path === '/dependencies' || + route.path === '/dependencies/inventory' || route.path === '/services/{serviceName}' || route.path === '/service-groups' || location.pathname === '/' || @@ -44,8 +44,8 @@ export function isRouteWithComparison({ return ( route.path === '/services' || route.path === '/service-map' || - route.path === '/backends' || - route.path === '/backends/inventory' || + route.path === '/dependencies' || + route.path === '/dependencies/inventory' || route.path === '/services/{serviceName}' || route.path === '/service-groups' || location.pathname === '/' || diff --git a/x-pack/plugins/apm/public/components/shared/time_comparison/index.tsx b/x-pack/plugins/apm/public/components/shared/time_comparison/index.tsx index ed157810f0617..6a72731a74236 100644 --- a/x-pack/plugins/apm/public/components/shared/time_comparison/index.tsx +++ b/x-pack/plugins/apm/public/components/shared/time_comparison/index.tsx @@ -39,7 +39,11 @@ export function TimeComparison() { const { isSmall } = useBreakpoints(); const { query: { rangeFrom, rangeTo, comparisonEnabled, offset }, - } = useAnyOfApmParams('/services', '/backends/*', '/services/{serviceName}'); + } = useAnyOfApmParams( + '/services', + '/dependencies/*', + '/services/{serviceName}' + ); const location = useLocation(); const apmRouter = useApmRouter(); diff --git a/x-pack/plugins/apm/public/context/time_range_metadata/time_range_metadata_context.tsx b/x-pack/plugins/apm/public/context/time_range_metadata/time_range_metadata_context.tsx index acb21a20620d0..53b8f3c5a55ab 100644 --- a/x-pack/plugins/apm/public/context/time_range_metadata/time_range_metadata_context.tsx +++ b/x-pack/plugins/apm/public/context/time_range_metadata/time_range_metadata_context.tsx @@ -38,7 +38,8 @@ export function TimeRangeMetadataContextProvider({ const routePath = useApmRoutePath(); const isOperationView = - routePath === '/backends/operation' || routePath === '/backends/operations'; + routePath === '/dependencies/operation' || + routePath === '/dependencies/operations'; const fetcherResult = useFetcher( (callApmApi) => { diff --git a/x-pack/plugins/apm/public/hooks/use_backend_detail_operations_breadcrumb.ts b/x-pack/plugins/apm/public/hooks/use_dependency_detail_operations_breadcrumb.ts similarity index 76% rename from x-pack/plugins/apm/public/hooks/use_backend_detail_operations_breadcrumb.ts rename to x-pack/plugins/apm/public/hooks/use_dependency_detail_operations_breadcrumb.ts index c5235333e8426..1364b2a38231d 100644 --- a/x-pack/plugins/apm/public/hooks/use_backend_detail_operations_breadcrumb.ts +++ b/x-pack/plugins/apm/public/hooks/use_dependency_detail_operations_breadcrumb.ts @@ -10,10 +10,10 @@ import { useBreadcrumb } from '../context/breadcrumbs/use_breadcrumb'; import { useAnyOfApmParams } from './use_apm_params'; import { useApmRouter } from './use_apm_router'; -export function useBackendDetailOperationsBreadcrumb() { +export function useDependencyDetailOperationsBreadcrumb() { const { query: { - backendName, + dependencyName, rangeFrom, rangeTo, refreshInterval, @@ -22,19 +22,19 @@ export function useBackendDetailOperationsBreadcrumb() { kuery, comparisonEnabled, }, - } = useAnyOfApmParams('/backends/operations', '/backends/operation'); + } = useAnyOfApmParams('/dependencies/operations', '/dependencies/operation'); const apmRouter = useApmRouter(); useBreadcrumb([ { title: i18n.translate( - 'xpack.apm.backendDetailOperations.breadcrumbTitle', + 'xpack.apm.dependencyDetailOperations.breadcrumbTitle', { defaultMessage: 'Operations' } ), - href: apmRouter.link('/backends/operations', { + href: apmRouter.link('/dependencies/operations', { query: { - backendName, + dependencyName, rangeFrom, rangeTo, refreshInterval, diff --git a/x-pack/plugins/apm/public/hooks/use_previous_period_text.ts b/x-pack/plugins/apm/public/hooks/use_previous_period_text.ts index 6a33b5c42a50f..822fa8d630230 100644 --- a/x-pack/plugins/apm/public/hooks/use_previous_period_text.ts +++ b/x-pack/plugins/apm/public/hooks/use_previous_period_text.ts @@ -19,7 +19,11 @@ const fallbackPreviousPeriodText = i18n.translate( export const usePreviousPeriodLabel = () => { const { query: { rangeFrom, rangeTo, offset }, - } = useAnyOfApmParams('/services', '/backends/*', '/services/{serviceName}'); + } = useAnyOfApmParams( + '/services', + '/dependencies/*', + '/services/{serviceName}' + ); const { start, end } = useTimeRange({ rangeFrom, rangeTo }); diff --git a/x-pack/plugins/apm/public/plugin.ts b/x-pack/plugins/apm/public/plugin.ts index 9edc7fe6f5d28..69e35f1146536 100644 --- a/x-pack/plugins/apm/public/plugin.ts +++ b/x-pack/plugins/apm/public/plugin.ts @@ -178,7 +178,7 @@ export class ApmPlugin implements Plugin { { label: dependenciesTitle, app: 'apm', - path: '/backends/inventory', + path: '/dependencies/inventory', onClick: () => { const { usageCollection } = pluginsStart as { usageCollection?: UsageCollectionStart; @@ -188,7 +188,7 @@ export class ApmPlugin implements Plugin { usageCollection.reportUiCounter( 'apm', METRIC_TYPE.CLICK, - 'side_nav_backend' + 'side_nav_dependency' ); } }, @@ -299,9 +299,9 @@ export class ApmPlugin implements Plugin { { id: 'traces', title: tracesTitle, path: '/traces' }, { id: 'service-map', title: serviceMapTitle, path: '/service-map' }, { - id: 'backends', + id: 'dependencies', title: dependenciesTitle, - path: '/backends/inventory', + path: '/dependencies/inventory', }, ], diff --git a/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_destination_map.ts b/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_destination_map.ts index 4e3dd452276d5..bb3defa93ac0c 100644 --- a/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_destination_map.ts +++ b/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_destination_map.ts @@ -30,7 +30,7 @@ import { Node, NodeType } from '../../../../common/connections'; import { excludeRumExitSpansQuery } from '../exclude_rum_exit_spans_query'; type Destination = { - backendName: string; + dependencyName: string; spanId: string; spanType: string; spanSubtype: string; @@ -43,10 +43,10 @@ type Destination = { } ); -// This operation tries to find a service for a backend, by: +// This operation tries to find a service for a dependency, by: // - getting a span for each value of span.destination.service.resource (which indicates an outgoing call) // - for each span, find the transaction it creates -// - if there is a transaction, match the backend name (span.destination.service.resource) to a service +// - if there is a transaction, match the dependency name (span.destination.service.resource) to a service export const getDestinationMap = ({ setup, start, @@ -91,7 +91,7 @@ export const getDestinationMap = ({ size: 10000, sources: asMutableArray([ { - backendName: { + dependencyName: { terms: { field: SPAN_DESTINATION_SERVICE_RESOURCE }, }, }, @@ -130,7 +130,7 @@ export const getDestinationMap = ({ const spanId = sample[SPAN_ID] as string; destinationsBySpanId.set(spanId, { - backendName: bucket.key.backendName as string, + dependencyName: bucket.key.dependencyName as string, spanId, spanType: (sample[SPAN_TYPE] as string | null) || '', spanSubtype: (sample[SPAN_SUBTYPE] as string | null) || '', @@ -189,11 +189,11 @@ export const getDestinationMap = ({ } }); - const nodesByBackendName = new Map(); + const nodesBydependencyName = new Map(); destinationsBySpanId.forEach((destination) => { const existingDestination = - nodesByBackendName.get(destination.backendName) ?? {}; + nodesBydependencyName.get(destination.dependencyName) ?? {}; const mergedDestination = { ...existingDestination, @@ -211,17 +211,17 @@ export const getDestinationMap = ({ }; } else { node = { - backendName: mergedDestination.backendName, + dependencyName: mergedDestination.dependencyName, spanType: mergedDestination.spanType, spanSubtype: mergedDestination.spanSubtype, - id: objectHash({ backendName: mergedDestination.backendName }), - type: NodeType.backend, + id: objectHash({ dependencyName: mergedDestination.dependencyName }), + type: NodeType.dependency, }; } - nodesByBackendName.set(destination.backendName, node); + nodesBydependencyName.set(destination.dependencyName, node); }); - return nodesByBackendName; + return nodesBydependencyName; }); }; diff --git a/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_stats.ts b/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_stats.ts index a0cd85c857a05..3f7fe3d168a9a 100644 --- a/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_stats.ts +++ b/x-pack/plugins/apm/server/lib/connections/get_connection_stats/get_stats.ts @@ -88,7 +88,7 @@ export const getStats = async ({ }, }, { - backendName: { + dependencyName: { terms: { field: SPAN_DESTINATION_SERVICE_RESOURCE, }, @@ -178,7 +178,7 @@ export const getStats = async ({ response.aggregations?.connections.buckets.map((bucket) => { const sample = bucket.sample.top[0].metrics; const serviceName = bucket.key.serviceName as string; - const backendName = bucket.key.backendName as string; + const dependencyName = bucket.key.dependencyName as string; return { from: { @@ -190,11 +190,11 @@ export const getStats = async ({ type: NodeType.service as const, }, to: { - id: objectHash({ backendName }), - backendName, + id: objectHash({ dependencyName }), + dependencyName, spanType: sample[SPAN_TYPE] as string, spanSubtype: (sample[SPAN_SUBTYPE] || '') as string, - type: NodeType.backend as const, + type: NodeType.dependency as const, }, value: { count: sum( diff --git a/x-pack/plugins/apm/server/lib/connections/get_connection_stats/index.ts b/x-pack/plugins/apm/server/lib/connections/get_connection_stats/index.ts index 5c1c628762edb..35d2a063325cf 100644 --- a/x-pack/plugins/apm/server/lib/connections/get_connection_stats/index.ts +++ b/x-pack/plugins/apm/server/lib/connections/get_connection_stats/index.ts @@ -53,7 +53,8 @@ export function getConnectionStats({ const statsWithLocationIds = allMetrics.map((statsItem) => { const { from, timeseries, value } = statsItem; - const to = destinationMap.get(statsItem.to.backendName) ?? statsItem.to; + const to = + destinationMap.get(statsItem.to.dependencyName) ?? statsItem.to; const location = collapseBy === 'upstream' ? from : to; diff --git a/x-pack/plugins/apm/server/routes/apm_routes/get_global_apm_server_route_repository.ts b/x-pack/plugins/apm/server/routes/apm_routes/get_global_apm_server_route_repository.ts index f906d6d95feb0..a7e41f86ded87 100644 --- a/x-pack/plugins/apm/server/routes/apm_routes/get_global_apm_server_route_repository.ts +++ b/x-pack/plugins/apm/server/routes/apm_routes/get_global_apm_server_route_repository.ts @@ -12,7 +12,7 @@ import type { import { PickByValue } from 'utility-types'; import { agentKeysRouteRepository } from '../agent_keys/route'; import { alertsChartPreviewRouteRepository } from '../alerts/route'; -import { backendsRouteRepository } from '../backends/route'; +import { dependencisRouteRepository } from '../dependencies/route'; import { correlationsRouteRepository } from '../correlations/route'; import { dataViewRouteRepository } from '../data_view/route'; import { debugTelemetryRoute } from '../debug_telemetry/route'; @@ -63,7 +63,7 @@ function getTypedGlobalApmServerRouteRepository() { ...customLinkRouteRepository, ...sourceMapsRouteRepository, ...apmFleetRouteRepository, - ...backendsRouteRepository, + ...dependencisRouteRepository, ...correlationsRouteRepository, ...fallbackToTransactionsRouteRepository, ...historicalDataRouteRepository, diff --git a/x-pack/plugins/apm/server/routes/backends/get_error_rate_charts_for_backend.ts b/x-pack/plugins/apm/server/routes/backends/get_error_rate_charts_for_backend.ts deleted file mode 100644 index a1890e103d412..0000000000000 --- a/x-pack/plugins/apm/server/routes/backends/get_error_rate_charts_for_backend.ts +++ /dev/null @@ -1,145 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { - kqlQuery, - rangeQuery, - termQuery, -} from '@kbn/observability-plugin/server'; -import { EventOutcome } from '../../../common/event_outcome'; -import { - EVENT_OUTCOME, - SPAN_DESTINATION_SERVICE_RESOURCE, - SPAN_NAME, -} from '../../../common/elasticsearch_fieldnames'; -import { environmentQuery } from '../../../common/utils/environment_query'; -import { Setup } from '../../lib/helpers/setup_request'; -import { getMetricsDateHistogramParams } from '../../lib/helpers/metrics'; -import { getOffsetInMs } from '../../../common/utils/get_offset_in_ms'; -import { - getDocCountFieldForServiceDestinationStatistics, - getDocumentTypeFilterForServiceDestinationStatistics, - getProcessorEventForServiceDestinationStatistics, -} from '../../lib/helpers/spans/get_is_using_service_destination_metrics'; - -export async function getErrorRateChartsForBackend({ - backendName, - spanName, - setup, - start, - end, - environment, - kuery, - searchServiceDestinationMetrics, - offset, -}: { - backendName: string; - spanName: string; - setup: Setup; - start: number; - end: number; - environment: string; - kuery: string; - searchServiceDestinationMetrics: boolean; - offset?: string; -}) { - const { apmEventClient } = setup; - - const { offsetInMs, startWithOffset, endWithOffset } = getOffsetInMs({ - start, - end, - offset, - }); - - const response = await apmEventClient.search('get_error_rate_for_backend', { - apm: { - events: [ - getProcessorEventForServiceDestinationStatistics( - searchServiceDestinationMetrics - ), - ], - }, - body: { - size: 0, - query: { - bool: { - filter: [ - ...environmentQuery(environment), - ...kqlQuery(kuery), - ...rangeQuery(startWithOffset, endWithOffset), - ...termQuery(SPAN_NAME, spanName || null), - ...getDocumentTypeFilterForServiceDestinationStatistics( - searchServiceDestinationMetrics - ), - { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: backendName } }, - { - terms: { - [EVENT_OUTCOME]: [EventOutcome.success, EventOutcome.failure], - }, - }, - ], - }, - }, - aggs: { - timeseries: { - date_histogram: getMetricsDateHistogramParams({ - start: startWithOffset, - end: endWithOffset, - metricsInterval: 60, - }), - aggs: { - ...(searchServiceDestinationMetrics - ? { - total_count: { - sum: { - field: getDocCountFieldForServiceDestinationStatistics( - searchServiceDestinationMetrics - ), - }, - }, - } - : {}), - failures: { - filter: { - term: { - [EVENT_OUTCOME]: EventOutcome.failure, - }, - }, - aggs: { - ...(searchServiceDestinationMetrics - ? { - total_count: { - sum: { - field: - getDocCountFieldForServiceDestinationStatistics( - searchServiceDestinationMetrics - ), - }, - }, - } - : {}), - }, - }, - }, - }, - }, - }, - }); - - return ( - response.aggregations?.timeseries.buckets.map((bucket) => { - const totalCount = bucket.total_count?.value ?? bucket.doc_count; - const failureCount = - bucket.failures.total_count?.value ?? bucket.failures.doc_count; - - return { - x: bucket.key + offsetInMs, - y: failureCount / totalCount, - }; - }) ?? [] - ); -} diff --git a/x-pack/plugins/apm/server/routes/backends/get_backend_latency_distribution.ts b/x-pack/plugins/apm/server/routes/dependencies/get_dependency_latency_distribution.ts similarity index 92% rename from x-pack/plugins/apm/server/routes/backends/get_backend_latency_distribution.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_dependency_latency_distribution.ts index c67b64273ae5b..ea7f5f53c7df4 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_backend_latency_distribution.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_dependency_latency_distribution.ts @@ -18,9 +18,9 @@ import { Setup } from '../../lib/helpers/setup_request'; import { getOverallLatencyDistribution } from '../latency_distribution/get_overall_latency_distribution'; import { OverallLatencyDistributionResponse } from '../latency_distribution/types'; -export async function getBackendLatencyDistribution({ +export async function getDependencyLatencyDistribution({ setup, - backendName, + dependencyName, spanName, kuery, environment, @@ -29,7 +29,7 @@ export async function getBackendLatencyDistribution({ percentileThreshold, }: { setup: Setup; - backendName: string; + dependencyName: string; spanName: string; kuery: string; environment: Environment; @@ -54,7 +54,7 @@ export async function getBackendLatencyDistribution({ bool: { filter: [ ...termQuery(SPAN_NAME, spanName), - ...termQuery(SPAN_DESTINATION_SERVICE_RESOURCE, backendName), + ...termQuery(SPAN_DESTINATION_SERVICE_RESOURCE, dependencyName), ], }, }; diff --git a/x-pack/plugins/apm/server/routes/dependencies/get_error_rate_charts_for_dependency.ts b/x-pack/plugins/apm/server/routes/dependencies/get_error_rate_charts_for_dependency.ts new file mode 100644 index 0000000000000..97e117535a4f7 --- /dev/null +++ b/x-pack/plugins/apm/server/routes/dependencies/get_error_rate_charts_for_dependency.ts @@ -0,0 +1,148 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { + kqlQuery, + rangeQuery, + termQuery, +} from '@kbn/observability-plugin/server'; +import { EventOutcome } from '../../../common/event_outcome'; +import { + EVENT_OUTCOME, + SPAN_DESTINATION_SERVICE_RESOURCE, + SPAN_NAME, +} from '../../../common/elasticsearch_fieldnames'; +import { environmentQuery } from '../../../common/utils/environment_query'; +import { Setup } from '../../lib/helpers/setup_request'; +import { getMetricsDateHistogramParams } from '../../lib/helpers/metrics'; +import { getOffsetInMs } from '../../../common/utils/get_offset_in_ms'; +import { + getDocCountFieldForServiceDestinationStatistics, + getDocumentTypeFilterForServiceDestinationStatistics, + getProcessorEventForServiceDestinationStatistics, +} from '../../lib/helpers/spans/get_is_using_service_destination_metrics'; + +export async function getErrorRateChartsForDependency({ + dependencyName, + spanName, + setup, + start, + end, + environment, + kuery, + searchServiceDestinationMetrics, + offset, +}: { + dependencyName: string; + spanName: string; + setup: Setup; + start: number; + end: number; + environment: string; + kuery: string; + searchServiceDestinationMetrics: boolean; + offset?: string; +}) { + const { apmEventClient } = setup; + + const { offsetInMs, startWithOffset, endWithOffset } = getOffsetInMs({ + start, + end, + offset, + }); + + const response = await apmEventClient.search( + 'get_error_rate_for_dependency', + { + apm: { + events: [ + getProcessorEventForServiceDestinationStatistics( + searchServiceDestinationMetrics + ), + ], + }, + body: { + size: 0, + query: { + bool: { + filter: [ + ...environmentQuery(environment), + ...kqlQuery(kuery), + ...rangeQuery(startWithOffset, endWithOffset), + ...termQuery(SPAN_NAME, spanName || null), + ...getDocumentTypeFilterForServiceDestinationStatistics( + searchServiceDestinationMetrics + ), + { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: dependencyName } }, + { + terms: { + [EVENT_OUTCOME]: [EventOutcome.success, EventOutcome.failure], + }, + }, + ], + }, + }, + aggs: { + timeseries: { + date_histogram: getMetricsDateHistogramParams({ + start: startWithOffset, + end: endWithOffset, + metricsInterval: 60, + }), + aggs: { + ...(searchServiceDestinationMetrics + ? { + total_count: { + sum: { + field: getDocCountFieldForServiceDestinationStatistics( + searchServiceDestinationMetrics + ), + }, + }, + } + : {}), + failures: { + filter: { + term: { + [EVENT_OUTCOME]: EventOutcome.failure, + }, + }, + aggs: { + ...(searchServiceDestinationMetrics + ? { + total_count: { + sum: { + field: + getDocCountFieldForServiceDestinationStatistics( + searchServiceDestinationMetrics + ), + }, + }, + } + : {}), + }, + }, + }, + }, + }, + }, + } + ); + + return ( + response.aggregations?.timeseries.buckets.map((bucket) => { + const totalCount = bucket.total_count?.value ?? bucket.doc_count; + const failureCount = + bucket.failures.total_count?.value ?? bucket.failures.doc_count; + + return { + x: bucket.key + offsetInMs, + y: failureCount / totalCount, + }; + }) ?? [] + ); +} diff --git a/x-pack/plugins/apm/server/routes/backends/get_latency_charts_for_backend.ts b/x-pack/plugins/apm/server/routes/dependencies/get_latency_charts_for_dependency.ts similarity index 94% rename from x-pack/plugins/apm/server/routes/backends/get_latency_charts_for_backend.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_latency_charts_for_dependency.ts index 1dfe61904112c..afbbd33fa6b9a 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_latency_charts_for_backend.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_latency_charts_for_dependency.ts @@ -25,8 +25,8 @@ import { getProcessorEventForServiceDestinationStatistics, } from '../../lib/helpers/spans/get_is_using_service_destination_metrics'; -export async function getLatencyChartsForBackend({ - backendName, +export async function getLatencyChartsForDependency({ + dependencyName, spanName, searchServiceDestinationMetrics, setup, @@ -36,7 +36,7 @@ export async function getLatencyChartsForBackend({ kuery, offset, }: { - backendName: string; + dependencyName: string; spanName: string; searchServiceDestinationMetrics: boolean; setup: Setup; @@ -54,7 +54,7 @@ export async function getLatencyChartsForBackend({ offset, }); - const response = await apmEventClient.search('get_latency_for_backend', { + const response = await apmEventClient.search('get_latency_for_dependency', { apm: { events: [ getProcessorEventForServiceDestinationStatistics( @@ -74,7 +74,7 @@ export async function getLatencyChartsForBackend({ ...getDocumentTypeFilterForServiceDestinationStatistics( searchServiceDestinationMetrics ), - { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: backendName } }, + { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: dependencyName } }, ], }, }, diff --git a/x-pack/plugins/apm/server/routes/backends/get_metadata_for_backend.ts b/x-pack/plugins/apm/server/routes/dependencies/get_metadata_for_dependency.ts similarity index 60% rename from x-pack/plugins/apm/server/routes/backends/get_metadata_for_backend.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_metadata_for_dependency.ts index 3392b4f2d1622..5c18d57d11c49 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_metadata_for_backend.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_metadata_for_dependency.ts @@ -11,42 +11,45 @@ import { ProcessorEvent } from '../../../common/processor_event'; import { SPAN_DESTINATION_SERVICE_RESOURCE } from '../../../common/elasticsearch_fieldnames'; import { Setup } from '../../lib/helpers/setup_request'; -export async function getMetadataForBackend({ +export async function getMetadataForDependency({ setup, - backendName, + dependencyName, start, end, }: { setup: Setup; - backendName: string; + dependencyName: string; start: number; end: number; }) { const { apmEventClient } = setup; - const sampleResponse = await apmEventClient.search('get_backend_sample', { - apm: { - events: [ProcessorEvent.span], - }, - body: { - size: 1, - query: { - bool: { - filter: [ - { - term: { - [SPAN_DESTINATION_SERVICE_RESOURCE]: backendName, + const sampleResponse = await apmEventClient.search( + 'get_metadata_for_dependency', + { + apm: { + events: [ProcessorEvent.span], + }, + body: { + size: 1, + query: { + bool: { + filter: [ + { + term: { + [SPAN_DESTINATION_SERVICE_RESOURCE]: dependencyName, + }, }, - }, - ...rangeQuery(start, end), - ], + ...rangeQuery(start, end), + ], + }, + }, + sort: { + '@timestamp': 'desc', }, }, - sort: { - '@timestamp': 'desc', - }, - }, - }); + } + ); const sample = maybe(sampleResponse.hits.hits[0])?._source; diff --git a/x-pack/plugins/apm/server/routes/backends/get_throughput_charts_for_backend.ts b/x-pack/plugins/apm/server/routes/dependencies/get_throughput_charts_for_dependency.ts similarity index 53% rename from x-pack/plugins/apm/server/routes/backends/get_throughput_charts_for_backend.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_throughput_charts_for_dependency.ts index 55930ad918646..fd4dee60f932b 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_throughput_charts_for_backend.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_throughput_charts_for_dependency.ts @@ -24,8 +24,8 @@ import { getProcessorEventForServiceDestinationStatistics, } from '../../lib/helpers/spans/get_is_using_service_destination_metrics'; -export async function getThroughputChartsForBackend({ - backendName, +export async function getThroughputChartsForDependency({ + dependencyName, spanName, setup, start, @@ -35,7 +35,7 @@ export async function getThroughputChartsForBackend({ searchServiceDestinationMetrics, offset, }: { - backendName: string; + dependencyName: string; spanName: string; setup: Setup; start: number; @@ -59,56 +59,59 @@ export async function getThroughputChartsForBackend({ minBucketSize: 60, }); - const response = await apmEventClient.search('get_throughput_for_backend', { - apm: { - events: [ - getProcessorEventForServiceDestinationStatistics( - searchServiceDestinationMetrics - ), - ], - }, - body: { - size: 0, - query: { - bool: { - filter: [ - ...environmentQuery(environment), - ...kqlQuery(kuery), - ...rangeQuery(startWithOffset, endWithOffset), - ...termQuery(SPAN_NAME, spanName || null), - ...getDocumentTypeFilterForServiceDestinationStatistics( - searchServiceDestinationMetrics - ), - { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: backendName } }, - ], - }, + const response = await apmEventClient.search( + 'get_throughput_for_dependency', + { + apm: { + events: [ + getProcessorEventForServiceDestinationStatistics( + searchServiceDestinationMetrics + ), + ], }, - aggs: { - timeseries: { - date_histogram: { - field: '@timestamp', - fixed_interval: intervalString, - min_doc_count: 0, - extended_bounds: { min: startWithOffset, max: endWithOffset }, + body: { + size: 0, + query: { + bool: { + filter: [ + ...environmentQuery(environment), + ...kqlQuery(kuery), + ...rangeQuery(startWithOffset, endWithOffset), + ...termQuery(SPAN_NAME, spanName || null), + ...getDocumentTypeFilterForServiceDestinationStatistics( + searchServiceDestinationMetrics + ), + { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: dependencyName } }, + ], }, - aggs: { - throughput: { - rate: { - ...(searchServiceDestinationMetrics - ? { - field: getDocCountFieldForServiceDestinationStatistics( - searchServiceDestinationMetrics - ), - } - : {}), - unit: 'minute', + }, + aggs: { + timeseries: { + date_histogram: { + field: '@timestamp', + fixed_interval: intervalString, + min_doc_count: 0, + extended_bounds: { min: startWithOffset, max: endWithOffset }, + }, + aggs: { + throughput: { + rate: { + ...(searchServiceDestinationMetrics + ? { + field: getDocCountFieldForServiceDestinationStatistics( + searchServiceDestinationMetrics + ), + } + : {}), + unit: 'minute', + }, }, }, }, }, }, - }, - }); + } + ); return ( response.aggregations?.timeseries.buckets.map((bucket) => { diff --git a/x-pack/plugins/apm/server/routes/backends/get_top_backends.ts b/x-pack/plugins/apm/server/routes/dependencies/get_top_dependencies.ts similarity index 96% rename from x-pack/plugins/apm/server/routes/backends/get_top_backends.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_top_dependencies.ts index 573d4792be429..08e2f6183303e 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_top_backends.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_top_dependencies.ts @@ -12,7 +12,7 @@ import { getConnectionStats } from '../../lib/connections/get_connection_stats'; import { getConnectionStatsItemsWithRelativeImpact } from '../../lib/connections/get_connection_stats/get_connection_stats_items_with_relative_impact'; import { Setup } from '../../lib/helpers/setup_request'; -export async function getTopBackends({ +export async function getTopDependencies({ setup, start, end, diff --git a/x-pack/plugins/apm/server/routes/backends/get_top_backend_operations.ts b/x-pack/plugins/apm/server/routes/dependencies/get_top_dependency_operations.ts similarity index 75% rename from x-pack/plugins/apm/server/routes/backends/get_top_backend_operations.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_top_dependency_operations.ts index d7e163bb1686e..dcf9ce40515c0 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_top_backend_operations.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_top_dependency_operations.ts @@ -31,7 +31,7 @@ import { calculateImpactBuilder } from '../traces/calculate_impact_builder'; const MAX_NUM_OPERATIONS = 500; -export interface BackendOperation { +export interface DependencyOperation { spanName: string; latency: number | null; throughput: number; @@ -43,9 +43,9 @@ export interface BackendOperation { >; } -export async function getTopBackendOperations({ +export async function getTopDependencyOperations({ setup, - backendName, + dependencyName, start, end, offset, @@ -53,7 +53,7 @@ export async function getTopBackendOperations({ kuery, }: { setup: Setup; - backendName: string; + dependencyName: string; start: number; end: number; offset?: string; @@ -90,48 +90,51 @@ export async function getTopBackendOperations({ }, }; - const response = await apmEventClient.search('get_top_backend_operations', { - apm: { - events: [ProcessorEvent.span], - }, - body: { - size: 0, - query: { - bool: { - filter: [ - ...rangeQuery(startWithOffset, endWithOffset), - ...environmentQuery(environment), - ...kqlQuery(kuery), - ...termQuery(SPAN_DESTINATION_SERVICE_RESOURCE, backendName), - ], - }, + const response = await apmEventClient.search( + 'get_top_dependency_operations', + { + apm: { + events: [ProcessorEvent.span], }, - aggs: { - operationName: { - terms: { - field: SPAN_NAME, - size: MAX_NUM_OPERATIONS, + body: { + size: 0, + query: { + bool: { + filter: [ + ...rangeQuery(startWithOffset, endWithOffset), + ...environmentQuery(environment), + ...kqlQuery(kuery), + ...termQuery(SPAN_DESTINATION_SERVICE_RESOURCE, dependencyName), + ], }, - aggs: { - over_time: { - date_histogram: getMetricsDateHistogramParams({ - start: startWithOffset, - end: endWithOffset, - metricsInterval: 60, - }), - aggs, + }, + aggs: { + operationName: { + terms: { + field: SPAN_NAME, + size: MAX_NUM_OPERATIONS, }, - ...aggs, - total_time: { - sum: { - field: SPAN_DURATION, + aggs: { + over_time: { + date_histogram: getMetricsDateHistogramParams({ + start: startWithOffset, + end: endWithOffset, + metricsInterval: 60, + }), + aggs, + }, + ...aggs, + total_time: { + sum: { + field: SPAN_DURATION, + }, }, }, }, }, }, - }, - }); + } + ); const getImpact = calculateImpactBuilder( response.aggregations?.operationName.buckets.map( @@ -141,8 +144,8 @@ export async function getTopBackendOperations({ return ( response.aggregations?.operationName.buckets.map( - (bucket): BackendOperation => { - const timeseries: BackendOperation['timeseries'] = { + (bucket): DependencyOperation => { + const timeseries: DependencyOperation['timeseries'] = { latency: [], throughput: [], failureRate: [], diff --git a/x-pack/plugins/apm/server/routes/backends/get_top_backend_spans.ts b/x-pack/plugins/apm/server/routes/dependencies/get_top_dependency_spans.ts similarity index 90% rename from x-pack/plugins/apm/server/routes/backends/get_top_backend_spans.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_top_dependency_spans.ts index e6d6b99986af9..86a6dfb0aaf8e 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_top_backend_spans.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_top_dependency_spans.ts @@ -34,7 +34,7 @@ import { Setup } from '../../lib/helpers/setup_request'; const MAX_NUM_SPANS = 1000; -export interface BackendSpan { +export interface DependencySpan { '@timestamp': number; spanName: string; serviceName: string; @@ -47,9 +47,9 @@ export interface BackendSpan { outcome: EventOutcome; } -export async function getTopBackendSpans({ +export async function getTopDependencySpans({ setup, - backendName, + dependencyName, spanName, start, end, @@ -59,7 +59,7 @@ export async function getTopBackendSpans({ sampleRangeTo, }: { setup: Setup; - backendName: string; + dependencyName: string; spanName: string; start: number; end: number; @@ -67,11 +67,11 @@ export async function getTopBackendSpans({ kuery: string; sampleRangeFrom?: number; sampleRangeTo?: number; -}): Promise { +}): Promise { const { apmEventClient } = setup; const spans = ( - await apmEventClient.search('get_top_backend_spans', { + await apmEventClient.search('get_top_dependency_spans', { apm: { events: [ProcessorEvent.span], }, @@ -83,7 +83,7 @@ export async function getTopBackendSpans({ ...rangeQuery(start, end), ...environmentQuery(environment), ...kqlQuery(kuery), - ...termQuery(SPAN_DESTINATION_SERVICE_RESOURCE, backendName), + ...termQuery(SPAN_DESTINATION_SERVICE_RESOURCE, dependencyName), ...termQuery(SPAN_NAME, spanName), ...((sampleRangeFrom ?? 0) >= 0 && (sampleRangeTo ?? 0) > 0 ? [ @@ -118,7 +118,7 @@ export async function getTopBackendSpans({ const transactionIds = compact(spans.map((span) => span.transaction?.id)); const transactions = ( - await apmEventClient.search('get_transactions_for_backend_spans', { + await apmEventClient.search('get_transactions_for_dependency_spans', { apm: { events: [ProcessorEvent.transaction], }, @@ -142,7 +142,7 @@ export async function getTopBackendSpans({ (transaction) => transaction.transaction.id ); - return spans.map((span): BackendSpan => { + return spans.map((span): DependencySpan => { const transaction = span.transaction ? transactionsById[span.transaction.id] : undefined; diff --git a/x-pack/plugins/apm/server/routes/backends/get_upstream_services_for_backend.ts b/x-pack/plugins/apm/server/routes/dependencies/get_upstream_services_for_dependency.ts similarity index 88% rename from x-pack/plugins/apm/server/routes/backends/get_upstream_services_for_backend.ts rename to x-pack/plugins/apm/server/routes/dependencies/get_upstream_services_for_dependency.ts index c9ccb0ef476de..4d620619e2eb1 100644 --- a/x-pack/plugins/apm/server/routes/backends/get_upstream_services_for_backend.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/get_upstream_services_for_dependency.ts @@ -12,11 +12,11 @@ import { getConnectionStats } from '../../lib/connections/get_connection_stats'; import { getConnectionStatsItemsWithRelativeImpact } from '../../lib/connections/get_connection_stats/get_connection_stats_items_with_relative_impact'; import { Setup } from '../../lib/helpers/setup_request'; -export async function getUpstreamServicesForBackend({ +export async function getUpstreamServicesForDependency({ setup, start, end, - backendName, + dependencyName, numBuckets, kuery, environment, @@ -25,7 +25,7 @@ export async function getUpstreamServicesForBackend({ setup: Setup; start: number; end: number; - backendName: string; + dependencyName: string; numBuckets: number; kuery: string; environment: string; @@ -36,7 +36,7 @@ export async function getUpstreamServicesForBackend({ start, end, filter: [ - { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: backendName } }, + { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: dependencyName } }, ...environmentQuery(environment), ...kqlQuery(kuery), ], diff --git a/x-pack/plugins/apm/server/routes/backends/route.ts b/x-pack/plugins/apm/server/routes/dependencies/route.ts similarity index 73% rename from x-pack/plugins/apm/server/routes/backends/route.ts rename to x-pack/plugins/apm/server/routes/dependencies/route.ts index fe14bdf27af0a..22a8c44e0de5a 100644 --- a/x-pack/plugins/apm/server/routes/backends/route.ts +++ b/x-pack/plugins/apm/server/routes/dependencies/route.ts @@ -10,24 +10,27 @@ import { toBooleanRt, toNumberRt } from '@kbn/io-ts-utils'; import { setupRequest } from '../../lib/helpers/setup_request'; import { environmentRt, kueryRt, rangeRt } from '../default_api_types'; import { createApmServerRoute } from '../apm_routes/create_apm_server_route'; -import { getMetadataForBackend } from './get_metadata_for_backend'; -import { getLatencyChartsForBackend } from './get_latency_charts_for_backend'; -import { getTopBackends } from './get_top_backends'; -import { getUpstreamServicesForBackend } from './get_upstream_services_for_backend'; -import { getThroughputChartsForBackend } from './get_throughput_charts_for_backend'; -import { getErrorRateChartsForBackend } from './get_error_rate_charts_for_backend'; +import { getMetadataForDependency } from './get_metadata_for_dependency'; +import { getLatencyChartsForDependency } from './get_latency_charts_for_dependency'; +import { getTopDependencies } from './get_top_dependencies'; +import { getUpstreamServicesForDependency } from './get_upstream_services_for_dependency'; +import { getThroughputChartsForDependency } from './get_throughput_charts_for_dependency'; +import { getErrorRateChartsForDependency } from './get_error_rate_charts_for_dependency'; import { ConnectionStatsItemWithImpact } from '../../../common/connections'; import { offsetRt } from '../../../common/comparison_rt'; import { - BackendOperation, - getTopBackendOperations, -} from './get_top_backend_operations'; -import { getBackendLatencyDistribution } from './get_backend_latency_distribution'; + DependencyOperation, + getTopDependencyOperations, +} from './get_top_dependency_operations'; +import { getDependencyLatencyDistribution } from './get_dependency_latency_distribution'; import { OverallLatencyDistributionResponse } from '../latency_distribution/types'; -import { BackendSpan, getTopBackendSpans } from './get_top_backend_spans'; +import { + DependencySpan, + getTopDependencySpans, +} from './get_top_dependency_spans'; -const topBackendsRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/top_backends', +const topDependenciesRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/top_dependencies', params: t.intersection([ t.type({ query: t.intersection([ @@ -47,7 +50,7 @@ const topBackendsRoute = createApmServerRoute({ handler: async ( resources ): Promise<{ - backends: Array<{ + dependencies: Array<{ currentStats: { latency: { value: number | null; @@ -103,17 +106,17 @@ const topBackendsRoute = createApmServerRoute({ const opts = { setup, start, end, numBuckets, environment, kuery }; - const [currentBackends, previousBackends] = await Promise.all([ - getTopBackends(opts), - offset ? getTopBackends({ ...opts, offset }) : Promise.resolve([]), + const [currentDependencies, previousDependencies] = await Promise.all([ + getTopDependencies(opts), + offset ? getTopDependencies({ ...opts, offset }) : Promise.resolve([]), ]); return { // eslint-disable-next-line @typescript-eslint/explicit-function-return-type - backends: currentBackends.map((backend) => { - const { stats, ...rest } = backend; - const prev = previousBackends.find( - (item): boolean => item.location.id === backend.location.id + dependencies: currentDependencies.map((dependency) => { + const { stats, ...rest } = dependency; + const prev = previousDependencies.find( + (item): boolean => item.location.id === dependency.location.id ); return { ...rest, @@ -125,12 +128,12 @@ const topBackendsRoute = createApmServerRoute({ }, }); -const upstreamServicesForBackendRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/upstream_services', +const upstreamServicesForDependencyRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/upstream_services', params: t.intersection([ t.type({ query: t.intersection([ - t.type({ backendName: t.string }), + t.type({ dependencyName: t.string }), rangeRt, t.type({ numBuckets: toNumberRt }), ]), @@ -198,7 +201,7 @@ const upstreamServicesForBackendRoute = createApmServerRoute({ const setup = await setupRequest(resources); const { query: { - backendName, + dependencyName, environment, offset, numBuckets, @@ -209,7 +212,7 @@ const upstreamServicesForBackendRoute = createApmServerRoute({ } = resources.params; const opts = { - backendName, + dependencyName, setup, start, end, @@ -219,9 +222,9 @@ const upstreamServicesForBackendRoute = createApmServerRoute({ }; const [currentServices, previousServices] = await Promise.all([ - getUpstreamServicesForBackend(opts), + getUpstreamServicesForDependency(opts), offset - ? getUpstreamServicesForBackend({ ...opts, offset }) + ? getUpstreamServicesForDependency({ ...opts, offset }) : Promise.resolve([]), ]); @@ -248,10 +251,10 @@ const upstreamServicesForBackendRoute = createApmServerRoute({ }, }); -const backendMetadataRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/metadata', +const dependencyMetadataRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/metadata', params: t.type({ - query: t.intersection([t.type({ backendName: t.string }), rangeRt]), + query: t.intersection([t.type({ dependencyName: t.string }), rangeRt]), }), options: { tags: ['access:apm'], @@ -264,10 +267,10 @@ const backendMetadataRoute = createApmServerRoute({ const setup = await setupRequest(resources); const { params } = resources; - const { backendName, start, end } = params.query; + const { dependencyName, start, end } = params.query; - const metadata = await getMetadataForBackend({ - backendName, + const metadata = await getMetadataForDependency({ + dependencyName, setup, start, end, @@ -277,12 +280,12 @@ const backendMetadataRoute = createApmServerRoute({ }, }); -const backendLatencyChartsRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/charts/latency', +const dependencyLatencyChartsRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/charts/latency', params: t.type({ query: t.intersection([ t.type({ - backendName: t.string, + dependencyName: t.string, spanName: t.string, searchServiceDestinationMetrics: toBooleanRt, }), @@ -304,7 +307,7 @@ const backendLatencyChartsRoute = createApmServerRoute({ const setup = await setupRequest(resources); const { params } = resources; const { - backendName, + dependencyName, searchServiceDestinationMetrics, spanName, kuery, @@ -315,8 +318,8 @@ const backendLatencyChartsRoute = createApmServerRoute({ } = params.query; const [currentTimeseries, comparisonTimeseries] = await Promise.all([ - getLatencyChartsForBackend({ - backendName, + getLatencyChartsForDependency({ + dependencyName, spanName, searchServiceDestinationMetrics, setup, @@ -326,8 +329,8 @@ const backendLatencyChartsRoute = createApmServerRoute({ environment, }), offset - ? getLatencyChartsForBackend({ - backendName, + ? getLatencyChartsForDependency({ + dependencyName, spanName, searchServiceDestinationMetrics, setup, @@ -344,12 +347,12 @@ const backendLatencyChartsRoute = createApmServerRoute({ }, }); -const backendThroughputChartsRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/charts/throughput', +const dependencyThroughputChartsRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/charts/throughput', params: t.type({ query: t.intersection([ t.type({ - backendName: t.string, + dependencyName: t.string, spanName: t.string, searchServiceDestinationMetrics: toBooleanRt, }), @@ -371,7 +374,7 @@ const backendThroughputChartsRoute = createApmServerRoute({ const setup = await setupRequest(resources); const { params } = resources; const { - backendName, + dependencyName, searchServiceDestinationMetrics, spanName, kuery, @@ -382,8 +385,8 @@ const backendThroughputChartsRoute = createApmServerRoute({ } = params.query; const [currentTimeseries, comparisonTimeseries] = await Promise.all([ - getThroughputChartsForBackend({ - backendName, + getThroughputChartsForDependency({ + dependencyName, spanName, setup, start, @@ -393,8 +396,8 @@ const backendThroughputChartsRoute = createApmServerRoute({ searchServiceDestinationMetrics, }), offset - ? getThroughputChartsForBackend({ - backendName, + ? getThroughputChartsForDependency({ + dependencyName, spanName, setup, start, @@ -411,12 +414,12 @@ const backendThroughputChartsRoute = createApmServerRoute({ }, }); -const backendFailedTransactionRateChartsRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/charts/error_rate', +const dependencyFailedTransactionRateChartsRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/charts/error_rate', params: t.type({ query: t.intersection([ t.type({ - backendName: t.string, + dependencyName: t.string, spanName: t.string, searchServiceDestinationMetrics: toBooleanRt, }), @@ -438,7 +441,7 @@ const backendFailedTransactionRateChartsRoute = createApmServerRoute({ const setup = await setupRequest(resources); const { params } = resources; const { - backendName, + dependencyName, spanName, searchServiceDestinationMetrics, kuery, @@ -449,8 +452,8 @@ const backendFailedTransactionRateChartsRoute = createApmServerRoute({ } = params.query; const [currentTimeseries, comparisonTimeseries] = await Promise.all([ - getErrorRateChartsForBackend({ - backendName, + getErrorRateChartsForDependency({ + dependencyName, spanName, setup, start, @@ -460,8 +463,8 @@ const backendFailedTransactionRateChartsRoute = createApmServerRoute({ searchServiceDestinationMetrics, }), offset - ? getErrorRateChartsForBackend({ - backendName, + ? getErrorRateChartsForDependency({ + dependencyName, spanName, setup, start, @@ -478,8 +481,8 @@ const backendFailedTransactionRateChartsRoute = createApmServerRoute({ }, }); -const backendOperationsRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/operations', +const dependencyOperationsRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/operations', options: { tags: ['access:apm'], }, @@ -489,19 +492,21 @@ const backendOperationsRoute = createApmServerRoute({ environmentRt, kueryRt, offsetRt, - t.type({ backendName: t.string }), + t.type({ dependencyName: t.string }), ]), }), - handler: async (resources): Promise<{ operations: BackendOperation[] }> => { + handler: async ( + resources + ): Promise<{ operations: DependencyOperation[] }> => { const setup = await setupRequest(resources); const { - query: { backendName, start, end, environment, kuery, offset }, + query: { dependencyName, start, end, environment, kuery, offset }, } = resources.params; - const operations = await getTopBackendOperations({ + const operations = await getTopDependencyOperations({ setup, - backendName, + dependencyName, start, end, offset, @@ -513,12 +518,12 @@ const backendOperationsRoute = createApmServerRoute({ }, }); -const backendLatencyDistributionChartsRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/charts/distribution', +const dependencyLatencyDistributionChartsRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/charts/distribution', params: t.type({ query: t.intersection([ t.type({ - backendName: t.string, + dependencyName: t.string, spanName: t.string, percentileThreshold: toNumberRt, }), @@ -539,7 +544,7 @@ const backendLatencyDistributionChartsRoute = createApmServerRoute({ const setup = await setupRequest(resources); const { params } = resources; const { - backendName, + dependencyName, spanName, percentileThreshold, kuery, @@ -548,9 +553,9 @@ const backendLatencyDistributionChartsRoute = createApmServerRoute({ end, } = params.query; - return getBackendLatencyDistribution({ + return getDependencyLatencyDistribution({ setup, - backendName, + dependencyName, spanName, percentileThreshold, kuery, @@ -561,8 +566,8 @@ const backendLatencyDistributionChartsRoute = createApmServerRoute({ }, }); -const topBackendSpansRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/backends/operations/spans', +const topDependencySpansRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/dependencies/operations/spans', options: { tags: ['access:apm'], }, @@ -571,16 +576,16 @@ const topBackendSpansRoute = createApmServerRoute({ rangeRt, environmentRt, kueryRt, - t.type({ backendName: t.string, spanName: t.string }), + t.type({ dependencyName: t.string, spanName: t.string }), t.partial({ sampleRangeFrom: toNumberRt, sampleRangeTo: toNumberRt }), ]), }), - handler: async (resources): Promise<{ spans: BackendSpan[] }> => { + handler: async (resources): Promise<{ spans: DependencySpan[] }> => { const setup = await setupRequest(resources); const { query: { - backendName, + dependencyName, spanName, start, end, @@ -591,9 +596,9 @@ const topBackendSpansRoute = createApmServerRoute({ }, } = resources.params; - const spans = await getTopBackendSpans({ + const spans = await getTopDependencySpans({ setup, - backendName, + dependencyName, spanName, start, end, @@ -607,14 +612,14 @@ const topBackendSpansRoute = createApmServerRoute({ }, }); -export const backendsRouteRepository = { - ...topBackendsRoute, - ...upstreamServicesForBackendRoute, - ...backendMetadataRoute, - ...backendLatencyChartsRoute, - ...backendThroughputChartsRoute, - ...backendFailedTransactionRateChartsRoute, - ...backendOperationsRoute, - ...backendLatencyDistributionChartsRoute, - ...topBackendSpansRoute, +export const dependencisRouteRepository = { + ...topDependenciesRoute, + ...upstreamServicesForDependencyRoute, + ...dependencyMetadataRoute, + ...dependencyLatencyChartsRoute, + ...dependencyThroughputChartsRoute, + ...dependencyFailedTransactionRateChartsRoute, + ...dependencyOperationsRoute, + ...dependencyLatencyDistributionChartsRoute, + ...topDependencySpansRoute, }; diff --git a/x-pack/plugins/apm/server/routes/service_map/get_service_map_backend_node_info.ts b/x-pack/plugins/apm/server/routes/service_map/get_service_map_dependency_node_info.ts similarity index 93% rename from x-pack/plugins/apm/server/routes/service_map/get_service_map_backend_node_info.ts rename to x-pack/plugins/apm/server/routes/service_map/get_service_map_dependency_node_info.ts index 76bccabc803ed..a757203b1c87b 100644 --- a/x-pack/plugins/apm/server/routes/service_map/get_service_map_backend_node_info.ts +++ b/x-pack/plugins/apm/server/routes/service_map/get_service_map_dependency_node_info.ts @@ -26,21 +26,21 @@ import { getOffsetInMs } from '../../../common/utils/get_offset_in_ms'; interface Options { setup: Setup; environment: string; - backendName: string; + dependencyName: string; start: number; end: number; offset?: string; } -export function getServiceMapBackendNodeInfo({ +export function getServiceMapDependencyNodeInfo({ environment, - backendName, + dependencyName, setup, start, end, offset, }: Options): Promise { - return withApmSpan('get_service_map_backend_node_stats', async () => { + return withApmSpan('get_service_map_dependency_node_stats', async () => { const { apmEventClient } = setup; const { offsetInMs, startWithOffset, endWithOffset } = getOffsetInMs({ start, @@ -67,7 +67,7 @@ export function getServiceMapBackendNodeInfo({ }; const response = await apmEventClient.search( - 'get_service_map_backend_node_stats', + 'get_service_map_dependency_node_stats', { apm: { events: [ProcessorEvent.metric], @@ -77,7 +77,9 @@ export function getServiceMapBackendNodeInfo({ query: { bool: { filter: [ - { term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: backendName } }, + { + term: { [SPAN_DESTINATION_SERVICE_RESOURCE]: dependencyName }, + }, ...rangeQuery(startWithOffset, endWithOffset), ...environmentQuery(environment), ], diff --git a/x-pack/plugins/apm/server/routes/service_map/route.ts b/x-pack/plugins/apm/server/routes/service_map/route.ts index e25dfb5bfa450..f4afa7efee5ef 100644 --- a/x-pack/plugins/apm/server/routes/service_map/route.ts +++ b/x-pack/plugins/apm/server/routes/service_map/route.ts @@ -13,7 +13,7 @@ import { notifyFeatureUsage } from '../../feature'; import { getSearchAggregatedTransactions } from '../../lib/helpers/transactions'; import { setupRequest } from '../../lib/helpers/setup_request'; import { getServiceMap } from './get_service_map'; -import { getServiceMapBackendNodeInfo } from './get_service_map_backend_node_info'; +import { getServiceMapDependencyNodeInfo } from './get_service_map_dependency_node_info'; import { getServiceMapServiceNodeInfo } from './get_service_map_service_node_info'; import { createApmServerRoute } from '../apm_routes/create_apm_server_route'; import { environmentRt, rangeRt } from '../default_api_types'; @@ -206,11 +206,11 @@ const serviceMapServiceNodeRoute = createApmServerRoute({ }, }); -const serviceMapBackendNodeRoute = createApmServerRoute({ - endpoint: 'GET /internal/apm/service-map/backend', +const serviceMapDependencyNodeRoute = createApmServerRoute({ + endpoint: 'GET /internal/apm/service-map/dependency', params: t.type({ query: t.intersection([ - t.type({ backendName: t.string }), + t.type({ dependencyName: t.string }), environmentRt, rangeRt, offsetRt, @@ -237,15 +237,15 @@ const serviceMapBackendNodeRoute = createApmServerRoute({ const setup = await setupRequest(resources); const { - query: { backendName, environment, start, end, offset }, + query: { dependencyName, environment, start, end, offset }, } = params; - const commonProps = { environment, setup, backendName, start, end }; + const commonProps = { environment, setup, dependencyName, start, end }; const [currentPeriod, previousPeriod] = await Promise.all([ - getServiceMapBackendNodeInfo(commonProps), + getServiceMapDependencyNodeInfo(commonProps), offset - ? getServiceMapBackendNodeInfo({ ...commonProps, offset }) + ? getServiceMapDependencyNodeInfo({ ...commonProps, offset }) : undefined, ]); @@ -256,5 +256,5 @@ const serviceMapBackendNodeRoute = createApmServerRoute({ export const serviceMapRouteRepository = { ...serviceMapRoute, ...serviceMapServiceNodeRoute, - ...serviceMapBackendNodeRoute, + ...serviceMapDependencyNodeRoute, }; diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index cb73b4bb74474..c2b568b87528b 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -7555,15 +7555,6 @@ "xpack.apm.apmSchema.index": "Schéma du serveur APM - Index", "xpack.apm.apmServiceGroups.index": "Groupes de services APM - Index", "xpack.apm.apmSettings.index": "Paramètres APM - Index", - "xpack.apm.backendDetail.dependenciesTableColumnBackend": "Service", - "xpack.apm.backendDetail.dependenciesTableTitle": "Services en amont", - "xpack.apm.backendDetailFailedTransactionRateChartTitle": "Taux de transactions ayant échoué", - "xpack.apm.backendDetailLatencyChartTitle": "Latence", - "xpack.apm.backendDetailThroughputChartTitle": "Rendement", - "xpack.apm.backendErrorRateChart.chartTitle": "Taux de transactions ayant échoué", - "xpack.apm.backendInventory.dependencyTableColumn": "Dépendance", - "xpack.apm.backendLatencyChart.chartTitle": "Latence", - "xpack.apm.backendThroughputChart.chartTitle": "Rendement", "xpack.apm.chart.annotation.version": "Version", "xpack.apm.chart.cpuSeries.processAverageLabel": "Moyenne de processus", "xpack.apm.chart.cpuSeries.processMaxLabel": "Max de processus", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index 292907d6b096f..0ddcc7feee2d0 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -7549,15 +7549,6 @@ "xpack.apm.apmSchema.index": "APMサーバースキーマ - インデックス", "xpack.apm.apmServiceGroups.index": "APMサービスグループ - インデックス", "xpack.apm.apmSettings.index": "APM 設定 - インデックス", - "xpack.apm.backendDetail.dependenciesTableColumnBackend": "サービス", - "xpack.apm.backendDetail.dependenciesTableTitle": "アップストリームサービス", - "xpack.apm.backendDetailFailedTransactionRateChartTitle": "失敗したトランザクション率", - "xpack.apm.backendDetailLatencyChartTitle": "レイテンシ", - "xpack.apm.backendDetailThroughputChartTitle": "スループット", - "xpack.apm.backendErrorRateChart.chartTitle": "失敗したトランザクション率", - "xpack.apm.backendInventory.dependencyTableColumn": "依存関係", - "xpack.apm.backendLatencyChart.chartTitle": "レイテンシ", - "xpack.apm.backendThroughputChart.chartTitle": "スループット", "xpack.apm.chart.annotation.version": "バージョン", "xpack.apm.chart.cpuSeries.processAverageLabel": "プロセス平均", "xpack.apm.chart.cpuSeries.processMaxLabel": "プロセス最大", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index 9fafcf0f11918..5ac4f914cbfe9 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -7561,15 +7561,6 @@ "xpack.apm.apmSchema.index": "APM Server 架构 - 索引", "xpack.apm.apmServiceGroups.index": "APM 服务组 - 索引", "xpack.apm.apmSettings.index": "APM 设置 - 索引", - "xpack.apm.backendDetail.dependenciesTableColumnBackend": "服务", - "xpack.apm.backendDetail.dependenciesTableTitle": "上游服务", - "xpack.apm.backendDetailFailedTransactionRateChartTitle": "失败事务率", - "xpack.apm.backendDetailLatencyChartTitle": "延迟", - "xpack.apm.backendDetailThroughputChartTitle": "吞吐量", - "xpack.apm.backendErrorRateChart.chartTitle": "失败事务率", - "xpack.apm.backendInventory.dependencyTableColumn": "依赖项", - "xpack.apm.backendLatencyChart.chartTitle": "延迟", - "xpack.apm.backendThroughputChart.chartTitle": "吞吐量", "xpack.apm.chart.annotation.version": "版本", "xpack.apm.chart.cpuSeries.processAverageLabel": "进程平均值", "xpack.apm.chart.cpuSeries.processMaxLabel": "进程最大值", diff --git a/x-pack/test/apm_api_integration/tests/dependencies/dependency_metrics.spec.ts b/x-pack/test/apm_api_integration/tests/dependencies/dependency_metrics.spec.ts index fb9f1ed9485e0..686f6ba313d7e 100644 --- a/x-pack/test/apm_api_integration/tests/dependencies/dependency_metrics.spec.ts +++ b/x-pack/test/apm_api_integration/tests/dependencies/dependency_metrics.spec.ts @@ -33,27 +33,27 @@ export default function ApiTest({ getService }: FtrProviderContext) { const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; async function callApi({ - backendName, + dependencyName, searchServiceDestinationMetrics, spanName = '', metric, kuery = '', environment = ENVIRONMENT_ALL.value, }: { - backendName: string; + dependencyName: string; searchServiceDestinationMetrics: boolean; spanName?: string; metric: TMetricName; kuery?: string; environment?: string; - }): Promise> { + }): Promise> { return await apmApiClient.readUser({ - endpoint: `GET /internal/apm/backends/charts/${ + endpoint: `GET /internal/apm/dependencies/charts/${ metric as 'latency' | 'throughput' | 'error_rate' }`, params: { query: { - backendName, + dependencyName, start: new Date(start).toISOString(), end: new Date(end).toISOString(), environment, @@ -80,7 +80,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { () => { it('handles empty state', async () => { const { body, status } = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', metric: 'latency', searchServiceDestinationMetrics: true, }); @@ -110,7 +110,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('without a kuery or environment', () => { it('returns the correct latency', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'latency', @@ -131,7 +131,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct throughput', async () => { const response = await callApi({ - backendName: 'redis', + dependencyName: 'redis', searchServiceDestinationMetrics: true, spanName: '', metric: 'throughput', @@ -142,7 +142,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct failure rate', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'error_rate', @@ -158,7 +158,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('with a kuery', () => { it('returns the correct latency', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'latency', @@ -179,7 +179,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct throughput', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'throughput', @@ -194,7 +194,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct failure rate', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'error_rate', @@ -208,7 +208,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('with an environment', () => { it('returns the correct latency', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'latency', @@ -229,7 +229,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct throughput', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'throughput', @@ -245,7 +245,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct failure rate', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: true, spanName: '', metric: 'error_rate', @@ -260,7 +260,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('with spanName', () => { it('returns the correct latency', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: false, spanName: '/_search', metric: 'latency', @@ -281,7 +281,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct throughput', async () => { const response = await callApi({ - backendName: 'redis', + dependencyName: 'redis', searchServiceDestinationMetrics: false, spanName: 'SET', metric: 'throughput', @@ -292,7 +292,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct failure rate', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', searchServiceDestinationMetrics: false, spanName: '/_bulk', metric: 'error_rate', diff --git a/x-pack/test/apm_api_integration/tests/dependencies/metadata.spec.ts b/x-pack/test/apm_api_integration/tests/dependencies/metadata.spec.ts index b47a4fb11bfbd..0d7e4f01733e2 100644 --- a/x-pack/test/apm_api_integration/tests/dependencies/metadata.spec.ts +++ b/x-pack/test/apm_api_integration/tests/dependencies/metadata.spec.ts @@ -18,10 +18,10 @@ export default function ApiTest({ getService }: FtrProviderContext) { async function callApi() { return await apmApiClient.readUser({ - endpoint: `GET /internal/apm/backends/metadata`, + endpoint: `GET /internal/apm/dependencies/metadata`, params: { query: { - backendName: dataConfig.span.destination, + dependencyName: dataConfig.span.destination, start: new Date(start).toISOString(), end: new Date(end).toISOString(), }, diff --git a/x-pack/test/apm_api_integration/tests/dependencies/service_dependencies.spec.ts b/x-pack/test/apm_api_integration/tests/dependencies/service_dependencies.spec.ts index bbec4088235c3..e5d3b8a436086 100644 --- a/x-pack/test/apm_api_integration/tests/dependencies/service_dependencies.spec.ts +++ b/x-pack/test/apm_api_integration/tests/dependencies/service_dependencies.spec.ts @@ -5,7 +5,7 @@ * 2.0. */ import expect from '@kbn/expect'; -import { BackendNode } from '@kbn/apm-plugin/common/connections'; +import { DependencyNode } from '@kbn/apm-plugin/common/connections'; import { FtrProviderContext } from '../../common/ftr_provider_context'; import { generateData } from './generate_data'; @@ -15,7 +15,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { const registry = getService('registry'); const start = new Date('2021-01-01T00:00:00.000Z').getTime(); const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; - const backendName = 'elasticsearch'; + const dependencyName = 'elasticsearch'; const serviceName = 'synth-go'; async function callApi() { @@ -62,8 +62,10 @@ export default function ApiTest({ getService }: FtrProviderContext) { expect(status).to.be(200); expect( - body.serviceDependencies.map(({ location }) => (location as BackendNode).backendName) - ).to.eql([backendName]); + body.serviceDependencies.map( + ({ location }) => (location as DependencyNode).dependencyName + ) + ).to.eql([dependencyName]); const currentStatsLatencyValues = body.serviceDependencies[0].currentStats.latency.timeseries; @@ -101,8 +103,10 @@ export default function ApiTest({ getService }: FtrProviderContext) { expect(status).to.be(200); expect( - body.serviceDependencies.map(({ location }) => (location as BackendNode).backendName) - ).to.eql([backendName]); + body.serviceDependencies.map( + ({ location }) => (location as DependencyNode).dependencyName + ) + ).to.eql([dependencyName]); const currentStatsLatencyValues = body.serviceDependencies[0].currentStats.latency.timeseries; diff --git a/x-pack/test/apm_api_integration/tests/dependencies/top_dependencies.spec.ts b/x-pack/test/apm_api_integration/tests/dependencies/top_dependencies.spec.ts index 53ff1b47981e6..5160ea52b094e 100644 --- a/x-pack/test/apm_api_integration/tests/dependencies/top_dependencies.spec.ts +++ b/x-pack/test/apm_api_integration/tests/dependencies/top_dependencies.spec.ts @@ -6,12 +6,12 @@ */ import expect from '@kbn/expect'; import { APIReturnType } from '@kbn/apm-plugin/public/services/rest/create_call_apm_api'; -import { NodeType, BackendNode } from '@kbn/apm-plugin/common/connections'; +import { NodeType, DependencyNode } from '@kbn/apm-plugin/common/connections'; import { FtrProviderContext } from '../../common/ftr_provider_context'; import { dataConfig, generateData } from './generate_data'; import { roundNumber } from '../../utils'; -type TopDependencies = APIReturnType<'GET /internal/apm/backends/top_backends'>; +type TopDependencies = APIReturnType<'GET /internal/apm/dependencies/top_dependencies'>; export default function ApiTest({ getService }: FtrProviderContext) { const registry = getService('registry'); @@ -23,7 +23,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { async function callApi() { return await apmApiClient.readUser({ - endpoint: 'GET /internal/apm/backends/top_backends', + endpoint: 'GET /internal/apm/dependencies/top_dependencies', params: { query: { start: new Date(start).toISOString(), @@ -44,7 +44,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('handles empty state', async () => { const { status, body } = await callApi(); expect(status).to.be(200); - expect(body.backends).to.empty(); + expect(body.dependencies).to.empty(); }); } ); @@ -65,40 +65,40 @@ export default function ApiTest({ getService }: FtrProviderContext) { after(() => synthtraceEsClient.clean()); it('returns an array of dependencies', () => { - expect(topDependencies).to.have.property('backends'); - expect(topDependencies.backends).to.have.length(1); + expect(topDependencies).to.have.property('dependencies'); + expect(topDependencies.dependencies).to.have.length(1); }); it('returns correct dependency information', () => { - const location = topDependencies.backends[0].location as BackendNode; + const location = topDependencies.dependencies[0].location as DependencyNode; const { span } = dataConfig; - expect(location.type).to.be(NodeType.backend); - expect(location.backendName).to.be(span.destination); + expect(location.type).to.be(NodeType.dependency); + expect(location.dependencyName).to.be(span.destination); expect(location.spanType).to.be(span.type); expect(location.spanSubtype).to.be(span.subType); expect(location).to.have.property('id'); }); describe('returns the correct stats', () => { - let backends: TopDependencies['backends'][number]; + let dependencies: TopDependencies['dependencies'][number]; before(() => { - backends = topDependencies.backends[0]; + dependencies = topDependencies.dependencies[0]; }); it("doesn't have previous stats", () => { - expect(backends.previousStats).to.be(null); + expect(dependencies.previousStats).to.be(null); }); it('has an "impact" property', () => { - expect(backends.currentStats).to.have.property('impact'); + expect(dependencies.currentStats).to.have.property('impact'); }); it('returns the correct latency', () => { const { currentStats: { latency }, - } = backends; + } = dependencies; const { transaction } = dataConfig; @@ -111,7 +111,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct throughput', () => { const { currentStats: { throughput }, - } = backends; + } = dependencies; const { rate } = dataConfig; expect(roundNumber(throughput.value)).to.be(roundNumber(rate)); @@ -120,7 +120,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct total time', () => { const { currentStats: { totalTime }, - } = backends; + } = dependencies; const { rate, transaction } = dataConfig; expect( @@ -131,7 +131,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { it('returns the correct error rate', () => { const { currentStats: { errorRate }, - } = backends; + } = dependencies; expect(errorRate.value).to.be(0); expect(errorRate.timeseries.every(({ y }) => y === 0)).to.be(true); }); diff --git a/x-pack/test/apm_api_integration/tests/dependencies/top_operations.spec.ts b/x-pack/test/apm_api_integration/tests/dependencies/top_operations.spec.ts index 638d9740cf17d..1040bd58417f5 100644 --- a/x-pack/test/apm_api_integration/tests/dependencies/top_operations.spec.ts +++ b/x-pack/test/apm_api_integration/tests/dependencies/top_operations.spec.ts @@ -12,7 +12,7 @@ import { FtrProviderContext } from '../../common/ftr_provider_context'; import { roundNumber } from '../../utils'; import { generateOperationData, generateOperationDataConfig } from './generate_operation_data'; -type TopOperations = APIReturnType<'GET /internal/apm/backends/operations'>['operations']; +type TopOperations = APIReturnType<'GET /internal/apm/dependencies/operations'>['operations']; const { ES_BULK_DURATION, @@ -34,24 +34,24 @@ export default function ApiTest({ getService }: FtrProviderContext) { const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; async function callApi({ - backendName, + dependencyName, environment = ENVIRONMENT_ALL.value, kuery = '', }: { - backendName: string; + dependencyName: string; environment?: string; kuery?: string; }) { return await apmApiClient .readUser({ - endpoint: 'GET /internal/apm/backends/operations', + endpoint: 'GET /internal/apm/dependencies/operations', params: { query: { start: new Date(start).toISOString(), end: new Date(end).toISOString(), environment, kuery, - backendName, + dependencyName, }, }, }) @@ -60,7 +60,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { registry.when('Top operations when data is not loaded', { config: 'basic', archives: [] }, () => { it('handles empty state', async () => { - const operations = await callApi({ backendName: 'elasticsearch' }); + const operations = await callApi({ dependencyName: 'elasticsearch' }); expect(operations).to.empty(); }); }); @@ -85,7 +85,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { let bulkOperation: ValuesType; before(async () => { - response = await callApi({ backendName: 'elasticsearch' }); + response = await callApi({ dependencyName: 'elasticsearch' }); searchOperation = response.find((op) => op.spanName === '/_search')!; bulkOperation = response.find((op) => op.spanName === '/_bulk')!; }); @@ -151,7 +151,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { let setOperation: ValuesType; before(async () => { - response = await callApi({ backendName: 'redis' }); + response = await callApi({ dependencyName: 'redis' }); setOperation = response.find((op) => op.spanName === 'SET')!; }); @@ -177,7 +177,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { before(async () => { response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', kuery: `service.name:"synth-go"`, }); searchOperation = response.find((op) => op.spanName === '/_search')!; @@ -199,7 +199,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { before(async () => { response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', environment: 'development', }); searchOperation = response.find((op) => op.spanName === '/_search'); diff --git a/x-pack/test/apm_api_integration/tests/dependencies/top_spans.spec.ts b/x-pack/test/apm_api_integration/tests/dependencies/top_spans.spec.ts index 5e497c969e920..ebc9fccc0904d 100644 --- a/x-pack/test/apm_api_integration/tests/dependencies/top_spans.spec.ts +++ b/x-pack/test/apm_api_integration/tests/dependencies/top_spans.spec.ts @@ -19,14 +19,14 @@ export default function ApiTest({ getService }: FtrProviderContext) { const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; async function callApi({ - backendName, + dependencyName, spanName, kuery = '', environment = ENVIRONMENT_ALL.value, sampleRangeFrom, sampleRangeTo, }: { - backendName: string; + dependencyName: string; spanName: string; kuery?: string; environment?: string; @@ -34,10 +34,10 @@ export default function ApiTest({ getService }: FtrProviderContext) { sampleRangeTo?: number; }) { return await apmApiClient.readUser({ - endpoint: `GET /internal/apm/backends/operations/spans`, + endpoint: `GET /internal/apm/dependencies/operations/spans`, params: { query: { - backendName, + dependencyName, start: new Date(start).toISOString(), end: new Date(end).toISOString(), environment, @@ -51,12 +51,12 @@ export default function ApiTest({ getService }: FtrProviderContext) { } registry.when( - 'Top backend spans when data is not loaded', + 'Top dependency spans when data is not loaded', { config: 'basic', archives: [] }, () => { it('handles empty state', async () => { const { body, status } = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', spanName: '/_search', }); @@ -67,7 +67,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { ); registry.when( - 'Top backend spans when data is loaded', + 'Top dependency spans when data is loaded', { config: 'basic', archives: ['apm_mappings_only_8.0.0'] }, () => { const javaInstance = apm.service('java', 'production', 'java').instance('instance-a'); @@ -126,7 +126,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('without a kuery or environment', () => { it('returns the correct spans for the requested spanName', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', spanName: '/_search', }); @@ -170,7 +170,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('with a kuery', () => { it('returns the correct spans for the requested spanName', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', spanName: '/_search', kuery: 'service.name:go', }); @@ -192,7 +192,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('with an environment', () => { it('returns the correct spans for the requested spanName', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', spanName: '/_search', environment: 'development', }); @@ -214,7 +214,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('when requesting spans without a transaction', () => { it('should return the spans without transaction metadata', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', spanName: 'without transaction', }); @@ -242,7 +242,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { describe('when requesting spans within a specific sample range', () => { it('returns only spans whose duration falls into the requested range', async () => { const response = await callApi({ - backendName: 'elasticsearch', + dependencyName: 'elasticsearch', spanName: '/_search', sampleRangeFrom: 50000, sampleRangeTo: 99999, diff --git a/x-pack/test/apm_api_integration/tests/dependencies/upstream_services.spec.ts b/x-pack/test/apm_api_integration/tests/dependencies/upstream_services.spec.ts index 6822048e4e685..2d3a51054541b 100644 --- a/x-pack/test/apm_api_integration/tests/dependencies/upstream_services.spec.ts +++ b/x-pack/test/apm_api_integration/tests/dependencies/upstream_services.spec.ts @@ -15,14 +15,14 @@ export default function ApiTest({ getService }: FtrProviderContext) { const registry = getService('registry'); const start = new Date('2021-01-01T00:00:00.000Z').getTime(); const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; - const backendName = 'elasticsearch'; + const dependencyName = 'elasticsearch'; async function callApi() { return await apmApiClient.readUser({ - endpoint: 'GET /internal/apm/backends/upstream_services', + endpoint: 'GET /internal/apm/dependencies/upstream_services', params: { query: { - backendName, + dependencyName, environment: 'production', kuery: '', numBuckets: 20, diff --git a/x-pack/test/apm_api_integration/tests/service_maps/service_maps.spec.ts b/x-pack/test/apm_api_integration/tests/service_maps/service_maps.spec.ts index 347dad2295565..c755f93d3b450 100644 --- a/x-pack/test/apm_api_integration/tests/service_maps/service_maps.spec.ts +++ b/x-pack/test/apm_api_integration/tests/service_maps/service_maps.spec.ts @@ -12,7 +12,7 @@ import { ApmApiError, SupertestReturnType } from '../../common/apm_api_supertest import archives_metadata from '../../common/fixtures/es_archiver/archives_metadata'; import { FtrProviderContext } from '../../common/ftr_provider_context'; -type BackendResponse = SupertestReturnType<'GET /internal/apm/service-map/backend'>; +type DependencyResponse = SupertestReturnType<'GET /internal/apm/service-map/dependency'>; type ServiceNodeResponse = SupertestReturnType<'GET /internal/apm/service-map/service/{serviceName}'>; type ServiceMapResponse = SupertestReturnType<'GET /internal/apm/service-map'>; @@ -101,14 +101,14 @@ export default function serviceMapsApiTests({ getService }: FtrProviderContext) }); }); - describe('/internal/apm/service-map/backend', () => { - let response: BackendResponse; + describe('/internal/apm/service-map/dependency', () => { + let response: DependencyResponse; before(async () => { response = await apmApiClient.readUser({ - endpoint: `GET /internal/apm/service-map/backend`, + endpoint: `GET /internal/apm/service-map/dependency`, params: { query: { - backendName: 'postgres', + dependencyName: 'postgres', start: metadata.start, end: metadata.end, environment: 'ENVIRONMENT_ALL', @@ -371,14 +371,14 @@ export default function serviceMapsApiTests({ getService }: FtrProviderContext) }); }); - describe('/internal/apm/service-map/backend', () => { - let response: BackendResponse; + describe('/internal/apm/service-map/dependency', () => { + let response: DependencyResponse; before(async () => { response = await apmApiClient.readUser({ - endpoint: `GET /internal/apm/service-map/backend`, + endpoint: `GET /internal/apm/service-map/dependency`, params: { query: { - backendName: 'postgresql', + dependencyName: 'postgresql', start: metadata.start, end: metadata.end, environment: 'ENVIRONMENT_ALL', @@ -416,14 +416,14 @@ export default function serviceMapsApiTests({ getService }: FtrProviderContext) }); describe('With comparison', () => { - describe('/internal/apm/service-map/backend', () => { - let response: BackendResponse; + describe('/internal/apm/service-map/dependency', () => { + let response: DependencyResponse; before(async () => { response = await apmApiClient.readUser({ - endpoint: `GET /internal/apm/service-map/backend`, + endpoint: `GET /internal/apm/service-map/dependency`, params: { query: { - backendName: 'postgresql', + dependencyName: 'postgresql', start: metadata.start, end: metadata.end, environment: 'ENVIRONMENT_ALL', diff --git a/x-pack/test/apm_api_integration/tests/service_overview/dependencies/index.spec.ts b/x-pack/test/apm_api_integration/tests/service_overview/dependencies/index.spec.ts index af04672913038..c3d5dbf6fe61c 100644 --- a/x-pack/test/apm_api_integration/tests/service_overview/dependencies/index.spec.ts +++ b/x-pack/test/apm_api_integration/tests/service_overview/dependencies/index.spec.ts @@ -28,7 +28,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { const { start, end } = archives[archiveName]; function getName(node: Node) { - return node.type === NodeType.service ? node.serviceName : node.backendName; + return node.type === NodeType.service ? node.serviceName : node.dependencyName; } registry.when( @@ -282,7 +282,7 @@ export default function ApiTest({ getService }: FtrProviderContext) { throughput: roundNumber(postgres?.currentStats.throughput.value), errorRate: roundNumber(postgres?.currentStats.errorRate.value), impact: postgres?.currentStats.impact, - ...pick(postgres?.location, 'spanType', 'spanSubtype', 'backendName', 'type'), + ...pick(postgres?.location, 'spanType', 'spanSubtype', 'dependencyName', 'type'), }; const count = 1; @@ -292,8 +292,8 @@ export default function ApiTest({ getService }: FtrProviderContext) { expect(values).to.eql({ spanType: 'external', spanSubtype: 'http', - backendName: 'postgres', - type: 'backend', + dependencyName: 'postgres', + type: 'dependency', errorRate: roundNumber(errors / count), latency: roundNumber(sum / count), throughput: roundNumber(count / ((endTime - startTime) / 1000 / 60)), diff --git a/x-pack/test/apm_api_integration/tests/throughput/dependencies_apis.spec.ts b/x-pack/test/apm_api_integration/tests/throughput/dependencies_apis.spec.ts index dd582238d4dd4..c46750d0d9d99 100644 --- a/x-pack/test/apm_api_integration/tests/throughput/dependencies_apis.spec.ts +++ b/x-pack/test/apm_api_integration/tests/throughput/dependencies_apis.spec.ts @@ -7,7 +7,7 @@ import { apm, timerange } from '@elastic/apm-synthtrace'; import expect from '@kbn/expect'; import { meanBy, sumBy } from 'lodash'; -import { BackendNode, ServiceNode } from '@kbn/apm-plugin/common/connections'; +import { DependencyNode, ServiceNode } from '@kbn/apm-plugin/common/connections'; import { FtrProviderContext } from '../../common/ftr_provider_context'; import { roundNumber } from '../../utils'; @@ -19,51 +19,57 @@ export default function ApiTest({ getService }: FtrProviderContext) { const start = new Date('2021-01-01T00:00:00.000Z').getTime(); const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; - async function getThroughputValues(overrides?: { serviceName?: string; backendName?: string }) { + async function getThroughputValues(overrides?: { + serviceName?: string; + dependencyName?: string; + }) { const commonQuery = { start: new Date(start).toISOString(), end: new Date(end).toISOString(), environment: 'ENVIRONMENT_ALL', }; - const [topBackendsAPIResponse, backendThroughputChartAPIResponse, upstreamServicesApiResponse] = - await Promise.all([ - apmApiClient.readUser({ - endpoint: `GET /internal/apm/backends/top_backends`, - params: { - query: { - ...commonQuery, - numBuckets: 20, - kuery: '', - }, + const [ + topDependenciesAPIResponse, + dependencyThroughputChartAPIResponse, + upstreamServicesApiResponse, + ] = await Promise.all([ + apmApiClient.readUser({ + endpoint: `GET /internal/apm/dependencies/top_dependencies`, + params: { + query: { + ...commonQuery, + numBuckets: 20, + kuery: '', }, - }), - apmApiClient.readUser({ - endpoint: `GET /internal/apm/backends/charts/throughput`, - params: { - query: { - ...commonQuery, - backendName: overrides?.backendName || 'elasticsearch', - spanName: '', - searchServiceDestinationMetrics: false, - kuery: '', - }, + }, + }), + apmApiClient.readUser({ + endpoint: `GET /internal/apm/dependencies/charts/throughput`, + params: { + query: { + ...commonQuery, + dependencyName: overrides?.dependencyName || 'elasticsearch', + spanName: '', + searchServiceDestinationMetrics: false, + kuery: '', }, - }), - apmApiClient.readUser({ - endpoint: `GET /internal/apm/backends/upstream_services`, - params: { - query: { - ...commonQuery, - backendName: overrides?.backendName || 'elasticsearch', - numBuckets: 20, - offset: '1d', - kuery: '', - }, + }, + }), + apmApiClient.readUser({ + endpoint: `GET /internal/apm/dependencies/upstream_services`, + params: { + query: { + ...commonQuery, + dependencyName: overrides?.dependencyName || 'elasticsearch', + numBuckets: 20, + offset: '1d', + kuery: '', }, - }), - ]); - const backendThroughputChartMean = roundNumber( - meanBy(backendThroughputChartAPIResponse.body.currentTimeseries, 'y') + }, + }), + ]); + const dependencyThroughputChartMean = roundNumber( + meanBy(dependencyThroughputChartAPIResponse.body.currentTimeseries, 'y') ); const upstreamServicesThroughput = upstreamServicesApiResponse.body.services.map( @@ -76,11 +82,11 @@ export default function ApiTest({ getService }: FtrProviderContext) { ); return { - topBackends: topBackendsAPIResponse.body.backends.map((item) => [ - (item.location as BackendNode).backendName, + topDependencies: topDependenciesAPIResponse.body.dependencies.map((item) => [ + (item.location as DependencyNode).dependencyName, roundNumber(item.currentStats.throughput.value), ]), - backendThroughputChartMean, + dependencyThroughputChartMean, upstreamServicesThroughput, }; } @@ -166,34 +172,34 @@ export default function ApiTest({ getService }: FtrProviderContext) { }); it('returns elasticsearch and postgresql as dependencies', () => { - const { topBackends } = throughputValues; - const topBackendsAsObj = Object.fromEntries(topBackends); - expect(topBackendsAsObj.elasticsearch).to.equal( + const { topDependencies } = throughputValues; + const topDependenciesAsObj = Object.fromEntries(topDependencies); + expect(topDependenciesAsObj.elasticsearch).to.equal( roundNumber(JAVA_PROD_RATE + GO_PROD_RATE) ); - expect(topBackendsAsObj.postgresql).to.equal(roundNumber(GO_PROD_RATE)); + expect(topDependenciesAsObj.postgresql).to.equal(roundNumber(GO_PROD_RATE)); }); }); describe('compare throughput value between top backends, backend throughput chart and upstream services apis', () => { describe('elasticsearch dependency', () => { before(async () => { - throughputValues = await getThroughputValues({ backendName: 'elasticsearch' }); + throughputValues = await getThroughputValues({ dependencyName: 'elasticsearch' }); }); it('matches throughput values between throughput chart and top dependency', () => { - const { topBackends, backendThroughputChartMean } = throughputValues; - const topBackendsAsObj = Object.fromEntries(topBackends); - const elasticsearchDependency = topBackendsAsObj.elasticsearch; - [elasticsearchDependency, backendThroughputChartMean].forEach((value) => + const { topDependencies, dependencyThroughputChartMean } = throughputValues; + const topDependenciesAsObj = Object.fromEntries(topDependencies); + const elasticsearchDependency = topDependenciesAsObj.elasticsearch; + [elasticsearchDependency, dependencyThroughputChartMean].forEach((value) => expect(value).to.be.equal(roundNumber(JAVA_PROD_RATE + GO_PROD_RATE)) ); }); it('matches throughput values between upstream services and top dependency', () => { - const { topBackends, upstreamServicesThroughput } = throughputValues; - const topBackendsAsObj = Object.fromEntries(topBackends); - const elasticsearchDependency = topBackendsAsObj.elasticsearch; + const { topDependencies, upstreamServicesThroughput } = throughputValues; + const topDependenciesAsObj = Object.fromEntries(topDependencies); + const elasticsearchDependency = topDependenciesAsObj.elasticsearch; const upstreamServiceThroughputSum = roundNumber( sumBy(upstreamServicesThroughput, 'throughput') ); @@ -204,22 +210,22 @@ export default function ApiTest({ getService }: FtrProviderContext) { }); describe('postgresql dependency', () => { before(async () => { - throughputValues = await getThroughputValues({ backendName: 'postgresql' }); + throughputValues = await getThroughputValues({ dependencyName: 'postgresql' }); }); it('matches throughput values between throughput chart and top dependency', () => { - const { topBackends, backendThroughputChartMean } = throughputValues; - const topBackendsAsObj = Object.fromEntries(topBackends); - const postgresqlDependency = topBackendsAsObj.postgresql; - [postgresqlDependency, backendThroughputChartMean].forEach((value) => + const { topDependencies, dependencyThroughputChartMean } = throughputValues; + const topDependenciesAsObj = Object.fromEntries(topDependencies); + const postgresqlDependency = topDependenciesAsObj.postgresql; + [postgresqlDependency, dependencyThroughputChartMean].forEach((value) => expect(value).to.be.equal(roundNumber(GO_PROD_RATE)) ); }); it('matches throughput values between upstream services and top dependency', () => { - const { topBackends, upstreamServicesThroughput } = throughputValues; - const topBackendsAsObj = Object.fromEntries(topBackends); - const postgresqlDependency = topBackendsAsObj.postgresql; + const { topDependencies, upstreamServicesThroughput } = throughputValues; + const topDependenciesAsObj = Object.fromEntries(topDependencies); + const postgresqlDependency = topDependenciesAsObj.postgresql; const upstreamServiceThroughputSum = roundNumber( sumBy(upstreamServicesThroughput, 'throughput') ); From 5a3f515e36009cd69ac565b7267a7c8d6fc681aa Mon Sep 17 00:00:00 2001 From: "Joey F. Poon" Date: Mon, 18 Jul 2022 10:36:52 -0500 Subject: [PATCH 101/111] [Security Solution] unskip and fix flaky tests (#136469) --- .../policy_response_wrapper.test.tsx | 49 +++++++------------ 1 file changed, 18 insertions(+), 31 deletions(-) diff --git a/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx b/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx index a4ef569c0a0c5..c5d29ef261369 100644 --- a/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/policy_response/policy_response_wrapper.test.tsx @@ -23,8 +23,7 @@ import { useGetEndpointDetails } from '../../hooks'; jest.mock('../../hooks/endpoint/use_get_endpoint_policy_response'); jest.mock('../../hooks/endpoint/use_get_endpoint_details'); -// FLAKY: https://github.com/elastic/kibana/issues/136272 -describe.skip('when on the policy response', () => { +describe('when on the policy response', () => { const docGenerator = new EndpointDocGenerator(); const createPolicyResponse = ( overallStatus: HostPolicyResponseActionStatus = HostPolicyResponseActionStatus.success, @@ -42,7 +41,21 @@ describe.skip('when on the policy response', () => { policyResponse.Endpoint.policy.applied.status = overallStatus; malwareResponseConfigurations.status = overallStatus; - for (const extraAction of extraActions) { + // remove existing extra actions so no dupes when we add them in later + Object.values(policyResponse.Endpoint.policy.applied.response.configurations).forEach( + (responseConfiguration) => { + extraActions.forEach((extraAction) => { + let extraActionIndex = responseConfiguration.concerned_actions.indexOf(extraAction.name); + // generator can pick same action multiple times + while (extraActionIndex !== -1) { + responseConfiguration.concerned_actions.splice(extraActionIndex, 1); + extraActionIndex = responseConfiguration.concerned_actions.indexOf(extraAction.name); + } + }); + } + ); + + extraActions.forEach((extraAction) => { let foundExtraAction = policyResponse.Endpoint.policy.applied.actions.find( (action) => action.name === extraAction.name ); @@ -53,13 +66,7 @@ describe.skip('when on the policy response', () => { } else { // Else, make sure the status of the generated action matches what was passed in foundExtraAction.status = overallStatus; - } - - if ( - overallStatus === HostPolicyResponseActionStatus.failure || - overallStatus === HostPolicyResponseActionStatus.warning - ) { - foundExtraAction.message = 'no action taken'; + foundExtraAction.message = extraAction.message; } // Make sure that at least one configuration has the above action, else @@ -67,27 +74,7 @@ describe.skip('when on the policy response', () => { if (malwareResponseConfigurations.concerned_actions.indexOf(foundExtraAction.name) === -1) { malwareResponseConfigurations.concerned_actions.push(foundExtraAction.name); } - } - - // if extra actions exist more than once, remove dupes to maintain exact counts - Object.entries(policyResponse.Endpoint.policy.applied.response.configurations).forEach( - ([responseConfigurationKey, responseConfiguration]) => { - if (responseConfigurationKey === 'malware') { - return; - } - - extraActions.forEach((extraAction) => { - const extraActionIndex = responseConfiguration.concerned_actions.indexOf( - extraAction.name - ); - if (extraActionIndex === -1) { - return; - } - - responseConfiguration.concerned_actions.splice(extraActionIndex, 1); - }); - } - ); + }); // Add an unknown Action Name - to ensure we handle the format of it on the UI const unknownAction: HostPolicyResponseAppliedAction = { From 11f7ace59f92a01f0ff496f3726a69d0929380fd Mon Sep 17 00:00:00 2001 From: Hannah Mudge Date: Mon, 18 Jul 2022 09:42:36 -0600 Subject: [PATCH 102/111] [Dashboard] Filter out experimental visualizations when labs setting is disabled (#136332) * Filter out experimental vis if labs disabled * Remove duplicated file * Add functional tests --- .../application/top_nav/editor_menu.tsx | 5 +- .../group_selection/group_selection.tsx | 6 +- .../group1/create_and_add_embeddables.ts | 27 +++ .../group6/create_and_add_embeddables.ts | 169 ------------------ 4 files changed, 36 insertions(+), 171 deletions(-) delete mode 100644 test/functional/apps/dashboard/group6/create_and_add_embeddables.ts diff --git a/src/plugins/dashboard/public/application/top_nav/editor_menu.tsx b/src/plugins/dashboard/public/application/top_nav/editor_menu.tsx index 5192759f2166a..0422149b54a88 100644 --- a/src/plugins/dashboard/public/application/top_nav/editor_menu.tsx +++ b/src/plugins/dashboard/public/application/top_nav/editor_menu.tsx @@ -46,6 +46,7 @@ export const EditorMenu = ({ dashboardContainer, createNewVisType }: Props) => { useKibana().services; const IS_DARK_THEME = uiSettings.get('theme:darkMode'); + const LABS_ENABLED = uiSettings.get('visualize:enableLabs'); const trackUiMetric = usageCollection?.reportUiCounter.bind( usageCollection, @@ -75,7 +76,9 @@ export const EditorMenu = ({ dashboardContainer, createNewVisType }: Props) => { } return 0; }) - .filter(({ hidden }: BaseVisType) => !hidden); + .filter( + ({ hidden, stage }: BaseVisType) => !(hidden || (!LABS_ENABLED && stage === 'experimental')) + ); const promotedVisTypes = getVisTypesByGroup(VisGroups.PROMOTED); const aggsBasedVisTypes = getVisTypesByGroup(VisGroups.AGGBASED); diff --git a/src/plugins/visualizations/public/wizard/group_selection/group_selection.tsx b/src/plugins/visualizations/public/wizard/group_selection/group_selection.tsx index 9dcb444368896..6bc982a824de1 100644 --- a/src/plugins/visualizations/public/wizard/group_selection/group_selection.tsx +++ b/src/plugins/visualizations/public/wizard/group_selection/group_selection.tsx @@ -227,7 +227,11 @@ const ToolsGroup = ({ visType, onVisTypeSelected, showExperimental }: VisCardPro - + {'titleInWizard' in visType && visType.titleInWizard ? visType.titleInWizard : visType.title} diff --git a/test/functional/apps/dashboard/group1/create_and_add_embeddables.ts b/test/functional/apps/dashboard/group1/create_and_add_embeddables.ts index c96e596a88ecf..c94ad298ef43f 100644 --- a/test/functional/apps/dashboard/group1/create_and_add_embeddables.ts +++ b/test/functional/apps/dashboard/group1/create_and_add_embeddables.ts @@ -18,6 +18,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { const browser = getService('browser'); const kibanaServer = getService('kibanaServer'); const dashboardAddPanel = getService('dashboardAddPanel'); + const testSubjects = getService('testSubjects'); describe('create and add embeddables', () => { before(async () => { @@ -133,6 +134,18 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { describe('visualize:enableLabs advanced setting', () => { const LAB_VIS_NAME = 'Rendering Test: input control'; + let experimentalTypes: string[] = []; + + before(async () => { + // get the data-test-subj values for all experimental visualizations for later tests + await PageObjects.visualize.gotoVisualizationLandingPage(); + await PageObjects.visualize.clickNewVisualization(); + const experimentalTypeWrappers = await PageObjects.visualize.getExperimentalTypeLinks(); + experimentalTypes = await Promise.all( + experimentalTypeWrappers.map((element) => element.getAttribute('data-test-subj')) + ); + }); + it('should display lab visualizations in add panel', async () => { await PageObjects.common.navigateToApp('dashboard'); await PageObjects.dashboard.clickNewDashboard(); @@ -141,6 +154,13 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { expect(exists).to.be(true); }); + it('should display lab visualizations in editor menu', async () => { + await dashboardAddPanel.clickEditorMenuButton(); + for (const dataTestSubj of experimentalTypes) { + await testSubjects.existOrFail(dataTestSubj); + } + }); + describe('is false', () => { before(async () => { await PageObjects.header.clickStackManagement(); @@ -157,6 +177,13 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { expect(exists).to.be(false); }); + it('should not display lab visualizations in editor menu', async () => { + await dashboardAddPanel.clickEditorMenuButton(); + for (const dataTestSubj of experimentalTypes) { + expect(await testSubjects.exists(dataTestSubj)).to.be(false); + } + }); + after(async () => { await PageObjects.header.clickStackManagement(); await PageObjects.settings.clickKibanaSettings(); diff --git a/test/functional/apps/dashboard/group6/create_and_add_embeddables.ts b/test/functional/apps/dashboard/group6/create_and_add_embeddables.ts deleted file mode 100644 index c96e596a88ecf..0000000000000 --- a/test/functional/apps/dashboard/group6/create_and_add_embeddables.ts +++ /dev/null @@ -1,169 +0,0 @@ -/* - * 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 expect from '@kbn/expect'; - -import { VisualizeConstants } from '@kbn/visualizations-plugin/common/constants'; -import { VISUALIZE_ENABLE_LABS_SETTING } from '@kbn/visualizations-plugin/common/constants'; -import { FtrProviderContext } from '../../../ftr_provider_context'; - -export default function ({ getService, getPageObjects }: FtrProviderContext) { - const retry = getService('retry'); - const PageObjects = getPageObjects(['dashboard', 'header', 'visualize', 'settings', 'common']); - const browser = getService('browser'); - const kibanaServer = getService('kibanaServer'); - const dashboardAddPanel = getService('dashboardAddPanel'); - - describe('create and add embeddables', () => { - before(async () => { - await kibanaServer.savedObjects.cleanStandardList(); - await kibanaServer.importExport.load( - 'test/functional/fixtures/kbn_archiver/dashboard/current/kibana' - ); - await kibanaServer.uiSettings.replace({ - defaultIndex: '0bf35f60-3dc9-11e8-8660-4d65aa086b3c', - }); - }); - - it('ensure toolbar popover closes on add', async () => { - await PageObjects.common.navigateToApp('dashboard'); - await PageObjects.dashboard.clickNewDashboard(); - await PageObjects.dashboard.switchToEditMode(); - await dashboardAddPanel.clickEditorMenuButton(); - await dashboardAddPanel.clickAddNewEmbeddableLink('LOG_STREAM_EMBEDDABLE'); - await dashboardAddPanel.expectEditorMenuClosed(); - }); - - after(async () => { - await kibanaServer.savedObjects.cleanStandardList(); - }); - - describe('add new visualization link', () => { - before(async () => { - await PageObjects.common.navigateToApp('dashboard'); - await PageObjects.dashboard.preserveCrossAppState(); - await PageObjects.dashboard.loadSavedDashboard('few panels'); - }); - - it('adds new visualization via the top nav link', async () => { - const originalPanelCount = await PageObjects.dashboard.getPanelCount(); - await PageObjects.dashboard.switchToEditMode(); - await dashboardAddPanel.clickEditorMenuButton(); - await dashboardAddPanel.clickAggBasedVisualizations(); - await PageObjects.visualize.clickAreaChart(); - await PageObjects.visualize.clickNewSearch(); - await PageObjects.visualize.saveVisualizationExpectSuccess( - 'visualization from top nav add new panel', - { redirectToOrigin: true } - ); - await retry.try(async () => { - const panelCount = await PageObjects.dashboard.getPanelCount(); - expect(panelCount).to.eql(originalPanelCount + 1); - }); - await PageObjects.dashboard.waitForRenderComplete(); - }); - - it('adds a new visualization', async () => { - const originalPanelCount = await PageObjects.dashboard.getPanelCount(); - await dashboardAddPanel.clickEditorMenuButton(); - await dashboardAddPanel.clickAggBasedVisualizations(); - await PageObjects.visualize.clickAreaChart(); - await PageObjects.visualize.clickNewSearch(); - await PageObjects.visualize.saveVisualizationExpectSuccess( - 'visualization from add new link', - { redirectToOrigin: true } - ); - - await retry.try(async () => { - const panelCount = await PageObjects.dashboard.getPanelCount(); - expect(panelCount).to.eql(originalPanelCount + 1); - }); - await PageObjects.dashboard.waitForRenderComplete(); - }); - - it('adds a new timelion visualization', async () => { - // adding this case, as the timelion agg-based viz doesn't need the `clickNewSearch()` step - const originalPanelCount = await PageObjects.dashboard.getPanelCount(); - await dashboardAddPanel.clickEditorMenuButton(); - await dashboardAddPanel.clickAggBasedVisualizations(); - await PageObjects.visualize.clickTimelion(); - await PageObjects.visualize.saveVisualizationExpectSuccess( - 'timelion visualization from add new link', - { redirectToOrigin: true } - ); - - await retry.try(async () => { - const panelCount = await PageObjects.dashboard.getPanelCount(); - expect(panelCount).to.eql(originalPanelCount + 1); - }); - await PageObjects.dashboard.waitForRenderComplete(); - }); - - it('adds a markdown visualization via the quick button', async () => { - const originalPanelCount = await PageObjects.dashboard.getPanelCount(); - await dashboardAddPanel.clickMarkdownQuickButton(); - await PageObjects.visualize.saveVisualizationExpectSuccess( - 'visualization from markdown quick button', - { redirectToOrigin: true } - ); - - await retry.try(async () => { - const panelCount = await PageObjects.dashboard.getPanelCount(); - expect(panelCount).to.eql(originalPanelCount + 1); - }); - await PageObjects.dashboard.waitForRenderComplete(); - }); - - it('saves the listing page instead of the visualization to the app link', async () => { - await PageObjects.header.clickVisualize(true); - const currentUrl = await browser.getCurrentUrl(); - expect(currentUrl).not.to.contain(VisualizeConstants.EDIT_PATH); - }); - - after(async () => { - await PageObjects.header.clickDashboard(); - }); - }); - - describe('visualize:enableLabs advanced setting', () => { - const LAB_VIS_NAME = 'Rendering Test: input control'; - - it('should display lab visualizations in add panel', async () => { - await PageObjects.common.navigateToApp('dashboard'); - await PageObjects.dashboard.clickNewDashboard(); - const exists = await dashboardAddPanel.panelAddLinkExists(LAB_VIS_NAME); - await dashboardAddPanel.closeAddPanel(); - expect(exists).to.be(true); - }); - - describe('is false', () => { - before(async () => { - await PageObjects.header.clickStackManagement(); - await PageObjects.settings.clickKibanaSettings(); - await PageObjects.settings.toggleAdvancedSettingCheckbox(VISUALIZE_ENABLE_LABS_SETTING); - }); - - it('should not display lab visualizations in add panel', async () => { - await PageObjects.common.navigateToApp('dashboard'); - await PageObjects.dashboard.clickNewDashboard(); - - const exists = await dashboardAddPanel.panelAddLinkExists(LAB_VIS_NAME); - await dashboardAddPanel.closeAddPanel(); - expect(exists).to.be(false); - }); - - after(async () => { - await PageObjects.header.clickStackManagement(); - await PageObjects.settings.clickKibanaSettings(); - await PageObjects.settings.clearAdvancedSettings(VISUALIZE_ENABLE_LABS_SETTING); - await PageObjects.header.clickDashboard(); - }); - }); - }); - }); -} From 4f817ad8a0747a22a40f6d0f9e87f9366c4a0e0c Mon Sep 17 00:00:00 2001 From: Spencer Date: Mon, 18 Jul 2022 10:46:13 -0500 Subject: [PATCH 103/111] [kbn/pm] rewrite to avoid needing a build process (#136207) * [kbn/pm] rewrite to avoid needing a build process * uncomment timing reporting * throw in a few missing comments * Update README.md * remove extra SomeDevLog interface from ci-stats-core * remove non-stdio logging from bazel_runner, improve output formatting * use private fields instead of just ts private props * promote args to a positional arg * optionally require the ci-stats-reporter after each command * allow opt-ing out of vscode config management * reduce to a single import * add bit of docs regarding weird imports and package deps of kbn/pm * clean extraDirs from Kibana's package.json file too * tweak logging of run-in-packages to use --quiet and not just CI=true * remove unlazy-loader * add readme for @kbn/yarn-lock-validator * convert @kbn/some-dev-logs docs to mdx * remove missing navigation id and fix id in dev-cli-runner docs * fix title of some-dev-logs docs page * typo --- .buildkite/scripts/steps/checks.sh | 1 - .../scripts/steps/checks/kbn_pm_dist.sh | 10 - .../scripts/steps/checks/test_projects.sh | 2 +- .../monorepo-packages.asciidoc | 12 +- kbn_pm/README.mdx | 44 + kbn_pm/src/cli.mjs | 130 + .../commands/bootstrap/bootstrap_command.mjs | 127 + .../src/commands/bootstrap/normalize_path.mjs | 61 + kbn_pm/src/commands/bootstrap/plugins.mjs | 51 + .../bootstrap/regenerate_base_tsconfig.mjs | 21 +- .../regenerate_synthetic_package_map.mjs | 34 + .../commands/bootstrap/setup_remote_cache.mjs | 50 +- .../commands/bootstrap/sort_package_json.mjs | 14 +- kbn_pm/src/commands/bootstrap/yarn.mjs | 53 + kbn_pm/src/commands/clean_command.mjs | 44 + kbn_pm/src/commands/index.mjs | 15 + kbn_pm/src/commands/reset_command.mjs | 47 + .../src/commands/run_in_packages_command.mjs | 76 + kbn_pm/src/commands/watch_command.mjs | 31 + kbn_pm/src/lib/args.mjs | 182 + kbn_pm/src/lib/bazel.mjs | 260 + kbn_pm/src/lib/clean.mjs | 30 + kbn_pm/src/lib/cli_error.mjs | 48 + kbn_pm/src/lib/colors.mjs | 49 + kbn_pm/src/lib/command.ts | 71 + kbn_pm/src/lib/find_clean_paths.mjs | 75 + kbn_pm/src/lib/fs.mjs | 51 + kbn_pm/src/lib/help.mjs | 56 + kbn_pm/src/lib/indent.mjs | 55 + kbn_pm/src/lib/log.mjs | 120 + kbn_pm/src/lib/obj_helpers.mjs | 13 + .../index.d.ts => kbn_pm/src/lib/paths.mjs | 4 +- kbn_pm/src/lib/spawn.mjs | 113 + kbn_pm/tsconfig.json | 16 + nav-kibana-dev.docnav.json | 15 +- package.json | 17 +- packages/BUILD.bazel | 4 + packages/README.md | 3 - .../kbn-bazel-packages/src/bazel_package.ts | 10 +- .../src/parse_package_json.ts | 4 + packages/kbn-bazel-runner/BUILD.bazel | 2 + packages/kbn-bazel-runner/README.mdx | 29 +- packages/kbn-bazel-runner/src/bazel_runner.js | 128 + packages/kbn-bazel-runner/src/bazel_runner.ts | 76 - .../src/index.js} | 6 +- packages/kbn-bazel-runner/src/types.ts | 34 + packages/kbn-bazel-runner/tsconfig.json | 2 + packages/kbn-ci-stats-core/BUILD.bazel | 1 + .../kbn-ci-stats-core/src/ci_stats_config.ts | 6 +- packages/kbn-ci-stats-reporter/BUILD.bazel | 1 + .../src/ci_stats_reporter.ts | 26 +- .../{README.md => README.mdx} | 15 +- packages/kbn-eslint-config/javascript.js | 2 +- packages/kbn-plugin-discovery/BUILD.bazel | 11 +- packages/kbn-plugin-discovery/README.mdx | 14 +- .../src/find_kibana_json_files.js | 65 + packages/kbn-plugin-discovery/src/index.js | 19 + .../src/load_json_file.js | 30 + ...gin.ts => parse_kibana_platform_plugin.js} | 50 +- ...search_paths.ts => plugin_search_paths.js} | 17 +- ...simple_kibana_platform_plugin_discovery.js | 29 + ...simple_kibana_platform_plugin_discovery.ts | 49 - packages/kbn-plugin-discovery/src/types.ts | 44 + packages/kbn-plugin-discovery/tsconfig.json | 5 +- packages/kbn-pm/.babelrc | 15 - packages/kbn-pm/README.md | 266 - packages/kbn-pm/dist/index.js | 63187 ---------------- packages/kbn-pm/package.json | 15 - .../kbn-pm/src/__snapshots__/run.test.ts.snap | 97 - packages/kbn-pm/src/cli.ts | 108 - packages/kbn-pm/src/commands/bootstrap.ts | 148 - packages/kbn-pm/src/commands/build.ts | 30 - packages/kbn-pm/src/commands/clean.ts | 94 - packages/kbn-pm/src/commands/index.ts | 44 - packages/kbn-pm/src/commands/reset.ts | 112 - packages/kbn-pm/src/commands/run.ts | 60 - packages/kbn-pm/src/commands/watch.ts | 35 - packages/kbn-pm/src/config.ts | 54 - packages/kbn-pm/src/index.ts | 12 - packages/kbn-pm/src/run.test.ts | 121 - packages/kbn-pm/src/run.ts | 162 - .../absolute_path_snapshot_serializer.ts | 40 - packages/kbn-pm/src/test_helpers/index.ts | 11 - .../strip_ansi_snapshot_serializer.ts | 20 - .../additional_projects/package.json | 4 - .../packages/baz/package.json | 7 - .../plugins/quux/package.json | 8 - .../utils/__fixtures__/kibana/package.json | 7 - .../kibana/packages/bar/package.json | 4 - .../kibana/packages/foo/package.json | 4 - .../other-plugins/baz/package.json | 4 - .../__fixtures__/plugins/baz/package.json | 4 - .../__fixtures__/plugins/quux/package.json | 4 - .../__fixtures__/plugins/zorge/package.json | 4 - .../symlinked-plugins/corge/package.json | 4 - .../link_project_executables.test.ts.snap | 35 - .../utils/__snapshots__/project.test.ts.snap | 3 - .../utils/__snapshots__/projects.test.ts.snap | 41 - .../__snapshots__/projects_tree.test.ts.snap | 29 - .../src/utils/bazel/get_cache_folders.ts | 25 - .../kbn-pm/src/utils/bazel/install_tools.ts | 105 - packages/kbn-pm/src/utils/bazel/yarn.ts | 53 - packages/kbn-pm/src/utils/child_process.ts | 67 - .../utils/convert_plugin_id_to_package_id.ts | 21 - packages/kbn-pm/src/utils/errors.ts | 13 - packages/kbn-pm/src/utils/fs.ts | 113 - packages/kbn-pm/src/utils/kibana.ts | 162 - .../utils/link_project_executables.test.ts | 114 - .../src/utils/link_project_executables.ts | 70 - packages/kbn-pm/src/utils/log.ts | 42 - packages/kbn-pm/src/utils/package_json.ts | 30 - packages/kbn-pm/src/utils/parallelize.test.ts | 122 - packages/kbn-pm/src/utils/parallelize.ts | 49 - packages/kbn-pm/src/utils/project.test.ts | 88 - packages/kbn-pm/src/utils/project.ts | 166 - packages/kbn-pm/src/utils/projects.test.ts | 254 - packages/kbn-pm/src/utils/projects.ts | 214 - .../kbn-pm/src/utils/projects_tree.test.ts | 40 - packages/kbn-pm/src/utils/projects_tree.ts | 150 - .../utils/regenerate_synthetic_package_map.ts | 33 - packages/kbn-pm/src/utils/scripts.ts | 47 - .../kbn-pm/src/utils/validate_dependencies.ts | 201 - packages/kbn-pm/src/utils/watch.ts | 102 - packages/kbn-pm/src/utils/yarn_lock.ts | 133 - packages/kbn-pm/tsconfig.json | 14 - packages/kbn-pm/webpack.config.js | 81 - packages/kbn-some-dev-log/BUILD.bazel | 116 + packages/kbn-some-dev-log/README.mdx | 19 + .../jest.config.js | 4 +- packages/kbn-some-dev-log/package.json | 10 + .../src/index.ts | 2 +- packages/kbn-some-dev-log/src/some_dev_log.ts | 45 + packages/kbn-some-dev-log/tsconfig.json | 18 + packages/kbn-tooling-log/BUILD.bazel | 3 +- packages/kbn-tooling-log/src/tooling_log.ts | 3 +- packages/kbn-utils/src/package_json/index.ts | 42 +- packages/kbn-yarn-lock-validator/BUILD.bazel | 121 + packages/kbn-yarn-lock-validator/README.mdx | 17 + .../kbn-yarn-lock-validator/jest.config.js | 13 + packages/kbn-yarn-lock-validator/package.json | 10 + .../src/find_production_dependencies.ts | 53 + .../src/index.ts | 6 +- .../src/validate_yarn_lock.ts | 115 + .../kbn-yarn-lock-validator/src/yarn_lock.ts | 73 + .../kbn-yarn-lock-validator/tsconfig.json | 18 + scripts/kbn.js | 5 +- src/dev/build/lib/config.test.ts | 2 +- src/dev/build/tasks/build_packages_task.ts | 5 +- src/dev/typescript/projects.ts | 1 + src/dev/typescript/run_type_check_cli.ts | 18 +- test/scripts/checks/kbn_pm_dist.sh | 19 - test/scripts/checks/test_projects.sh | 2 +- .../install_all_packages.ts | 4 +- yarn.lock | 161 +- 154 files changed, 3093 insertions(+), 67794 deletions(-) delete mode 100755 .buildkite/scripts/steps/checks/kbn_pm_dist.sh create mode 100644 kbn_pm/README.mdx create mode 100644 kbn_pm/src/cli.mjs create mode 100644 kbn_pm/src/commands/bootstrap/bootstrap_command.mjs create mode 100644 kbn_pm/src/commands/bootstrap/normalize_path.mjs create mode 100644 kbn_pm/src/commands/bootstrap/plugins.mjs rename packages/kbn-pm/src/utils/regenerate_base_tsconfig.ts => kbn_pm/src/commands/bootstrap/regenerate_base_tsconfig.mjs (63%) create mode 100644 kbn_pm/src/commands/bootstrap/regenerate_synthetic_package_map.mjs rename packages/kbn-pm/src/utils/bazel/setup_remote_cache.ts => kbn_pm/src/commands/bootstrap/setup_remote_cache.mjs (52%) rename packages/kbn-pm/src/utils/regenerate_package_json.ts => kbn_pm/src/commands/bootstrap/sort_package_json.mjs (53%) create mode 100644 kbn_pm/src/commands/bootstrap/yarn.mjs create mode 100644 kbn_pm/src/commands/clean_command.mjs create mode 100644 kbn_pm/src/commands/index.mjs create mode 100644 kbn_pm/src/commands/reset_command.mjs create mode 100644 kbn_pm/src/commands/run_in_packages_command.mjs create mode 100644 kbn_pm/src/commands/watch_command.mjs create mode 100644 kbn_pm/src/lib/args.mjs create mode 100644 kbn_pm/src/lib/bazel.mjs create mode 100644 kbn_pm/src/lib/clean.mjs create mode 100644 kbn_pm/src/lib/cli_error.mjs create mode 100644 kbn_pm/src/lib/colors.mjs create mode 100644 kbn_pm/src/lib/command.ts create mode 100644 kbn_pm/src/lib/find_clean_paths.mjs create mode 100644 kbn_pm/src/lib/fs.mjs create mode 100644 kbn_pm/src/lib/help.mjs create mode 100644 kbn_pm/src/lib/indent.mjs create mode 100644 kbn_pm/src/lib/log.mjs create mode 100644 kbn_pm/src/lib/obj_helpers.mjs rename packages/kbn-pm/index.d.ts => kbn_pm/src/lib/paths.mjs (73%) create mode 100644 kbn_pm/src/lib/spawn.mjs create mode 100644 kbn_pm/tsconfig.json create mode 100644 packages/kbn-bazel-runner/src/bazel_runner.js delete mode 100644 packages/kbn-bazel-runner/src/bazel_runner.ts rename packages/{kbn-pm/src/utils/bazel/index.ts => kbn-bazel-runner/src/index.js} (77%) create mode 100644 packages/kbn-bazel-runner/src/types.ts rename packages/kbn-dev-cli-runner/{README.md => README.mdx} (93%) create mode 100644 packages/kbn-plugin-discovery/src/find_kibana_json_files.js create mode 100644 packages/kbn-plugin-discovery/src/index.js create mode 100644 packages/kbn-plugin-discovery/src/load_json_file.js rename packages/kbn-plugin-discovery/src/{parse_kibana_platform_plugin.ts => parse_kibana_platform_plugin.js} (65%) rename packages/kbn-plugin-discovery/src/{plugin_search_paths.ts => plugin_search_paths.js} (85%) create mode 100644 packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.js delete mode 100644 packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.ts create mode 100644 packages/kbn-plugin-discovery/src/types.ts delete mode 100644 packages/kbn-pm/.babelrc delete mode 100644 packages/kbn-pm/README.md delete mode 100644 packages/kbn-pm/dist/index.js delete mode 100644 packages/kbn-pm/package.json delete mode 100644 packages/kbn-pm/src/__snapshots__/run.test.ts.snap delete mode 100644 packages/kbn-pm/src/cli.ts delete mode 100644 packages/kbn-pm/src/commands/bootstrap.ts delete mode 100644 packages/kbn-pm/src/commands/build.ts delete mode 100644 packages/kbn-pm/src/commands/clean.ts delete mode 100644 packages/kbn-pm/src/commands/index.ts delete mode 100644 packages/kbn-pm/src/commands/reset.ts delete mode 100644 packages/kbn-pm/src/commands/run.ts delete mode 100644 packages/kbn-pm/src/commands/watch.ts delete mode 100644 packages/kbn-pm/src/config.ts delete mode 100644 packages/kbn-pm/src/index.ts delete mode 100644 packages/kbn-pm/src/run.test.ts delete mode 100644 packages/kbn-pm/src/run.ts delete mode 100644 packages/kbn-pm/src/test_helpers/absolute_path_snapshot_serializer.ts delete mode 100644 packages/kbn-pm/src/test_helpers/index.ts delete mode 100644 packages/kbn-pm/src/test_helpers/strip_ansi_snapshot_serializer.ts delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/packages/baz/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/plugins/quux/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/kibana/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/kibana/packages/bar/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/kibana/packages/foo/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/other-plugins/baz/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/plugins/baz/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/plugins/quux/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/plugins/zorge/package.json delete mode 100644 packages/kbn-pm/src/utils/__fixtures__/symlinked-plugins/corge/package.json delete mode 100644 packages/kbn-pm/src/utils/__snapshots__/link_project_executables.test.ts.snap delete mode 100644 packages/kbn-pm/src/utils/__snapshots__/project.test.ts.snap delete mode 100644 packages/kbn-pm/src/utils/__snapshots__/projects.test.ts.snap delete mode 100644 packages/kbn-pm/src/utils/__snapshots__/projects_tree.test.ts.snap delete mode 100644 packages/kbn-pm/src/utils/bazel/get_cache_folders.ts delete mode 100644 packages/kbn-pm/src/utils/bazel/install_tools.ts delete mode 100644 packages/kbn-pm/src/utils/bazel/yarn.ts delete mode 100644 packages/kbn-pm/src/utils/child_process.ts delete mode 100644 packages/kbn-pm/src/utils/convert_plugin_id_to_package_id.ts delete mode 100644 packages/kbn-pm/src/utils/errors.ts delete mode 100644 packages/kbn-pm/src/utils/fs.ts delete mode 100644 packages/kbn-pm/src/utils/kibana.ts delete mode 100644 packages/kbn-pm/src/utils/link_project_executables.test.ts delete mode 100644 packages/kbn-pm/src/utils/link_project_executables.ts delete mode 100644 packages/kbn-pm/src/utils/log.ts delete mode 100644 packages/kbn-pm/src/utils/package_json.ts delete mode 100644 packages/kbn-pm/src/utils/parallelize.test.ts delete mode 100644 packages/kbn-pm/src/utils/parallelize.ts delete mode 100644 packages/kbn-pm/src/utils/project.test.ts delete mode 100644 packages/kbn-pm/src/utils/project.ts delete mode 100644 packages/kbn-pm/src/utils/projects.test.ts delete mode 100644 packages/kbn-pm/src/utils/projects.ts delete mode 100644 packages/kbn-pm/src/utils/projects_tree.test.ts delete mode 100644 packages/kbn-pm/src/utils/projects_tree.ts delete mode 100644 packages/kbn-pm/src/utils/regenerate_synthetic_package_map.ts delete mode 100644 packages/kbn-pm/src/utils/scripts.ts delete mode 100644 packages/kbn-pm/src/utils/validate_dependencies.ts delete mode 100644 packages/kbn-pm/src/utils/watch.ts delete mode 100644 packages/kbn-pm/src/utils/yarn_lock.ts delete mode 100644 packages/kbn-pm/tsconfig.json delete mode 100644 packages/kbn-pm/webpack.config.js create mode 100644 packages/kbn-some-dev-log/BUILD.bazel create mode 100644 packages/kbn-some-dev-log/README.mdx rename packages/{kbn-pm => kbn-some-dev-log}/jest.config.js (82%) create mode 100644 packages/kbn-some-dev-log/package.json rename packages/{kbn-bazel-runner => kbn-some-dev-log}/src/index.ts (84%) create mode 100644 packages/kbn-some-dev-log/src/some_dev_log.ts create mode 100644 packages/kbn-some-dev-log/tsconfig.json create mode 100644 packages/kbn-yarn-lock-validator/BUILD.bazel create mode 100644 packages/kbn-yarn-lock-validator/README.mdx create mode 100644 packages/kbn-yarn-lock-validator/jest.config.js create mode 100644 packages/kbn-yarn-lock-validator/package.json create mode 100644 packages/kbn-yarn-lock-validator/src/find_production_dependencies.ts rename packages/{kbn-plugin-discovery => kbn-yarn-lock-validator}/src/index.ts (70%) create mode 100644 packages/kbn-yarn-lock-validator/src/validate_yarn_lock.ts create mode 100644 packages/kbn-yarn-lock-validator/src/yarn_lock.ts create mode 100644 packages/kbn-yarn-lock-validator/tsconfig.json delete mode 100644 test/scripts/checks/kbn_pm_dist.sh diff --git a/.buildkite/scripts/steps/checks.sh b/.buildkite/scripts/steps/checks.sh index 9937a25758e41..4af63d318c804 100755 --- a/.buildkite/scripts/steps/checks.sh +++ b/.buildkite/scripts/steps/checks.sh @@ -11,7 +11,6 @@ export DISABLE_BOOTSTRAP_VALIDATION=false .buildkite/scripts/steps/checks/telemetry.sh .buildkite/scripts/steps/checks/ts_projects.sh .buildkite/scripts/steps/checks/jest_configs.sh -.buildkite/scripts/steps/checks/kbn_pm_dist.sh .buildkite/scripts/steps/checks/plugin_list_docs.sh .buildkite/scripts/steps/checks/bundle_limits.sh .buildkite/scripts/steps/checks/i18n.sh diff --git a/.buildkite/scripts/steps/checks/kbn_pm_dist.sh b/.buildkite/scripts/steps/checks/kbn_pm_dist.sh deleted file mode 100755 index 6f75bd9ea4e29..0000000000000 --- a/.buildkite/scripts/steps/checks/kbn_pm_dist.sh +++ /dev/null @@ -1,10 +0,0 @@ -#!/usr/bin/env bash - -set -euo pipefail - -source .buildkite/scripts/common/util.sh - -echo "--- Building kbn-pm distributable" -yarn kbn run build -i @kbn/pm - -check_for_changed_files 'yarn kbn run build -i @kbn/pm' true diff --git a/.buildkite/scripts/steps/checks/test_projects.sh b/.buildkite/scripts/steps/checks/test_projects.sh index 4c7d9094cb0c3..76625b23ac335 100755 --- a/.buildkite/scripts/steps/checks/test_projects.sh +++ b/.buildkite/scripts/steps/checks/test_projects.sh @@ -6,4 +6,4 @@ source .buildkite/scripts/common/util.sh echo --- Test Projects checks-reporter-with-killswitch "Test Projects" \ - yarn kbn run test --exclude kibana --oss --skip-kibana-plugins --skip-missing + yarn kbn run-in-packages test diff --git a/docs/developer/getting-started/monorepo-packages.asciidoc b/docs/developer/getting-started/monorepo-packages.asciidoc index eed060d253a28..b6524c6007b2e 100644 --- a/docs/developer/getting-started/monorepo-packages.asciidoc +++ b/docs/developer/getting-started/monorepo-packages.asciidoc @@ -17,16 +17,6 @@ Remember that any time you need to make sure the monorepo is ready to be used ju yarn kbn bootstrap ---- -[discrete] -=== Building Non Bazel Packages - -Non Bazel packages can be built independently with - -[source,bash] ----- -yarn kbn run build -i PACKAGE_NAME ----- - [discrete] === Building Bazel Packages @@ -34,7 +24,7 @@ Bazel packages are built as a whole for now. You can use: [source,bash] ---- -yarn kbn build +yarn kbn bootstrap ---- [discrete] diff --git a/kbn_pm/README.mdx b/kbn_pm/README.mdx new file mode 100644 index 0000000000000..03568d5667a25 --- /dev/null +++ b/kbn_pm/README.mdx @@ -0,0 +1,44 @@ +--- +id: kibDevDocsOpsKbnPm +slug: /kibana-dev-docs/ops/kbn-pm +title: "@kbn/pm" +description: 'The tool which bootstraps the repo and helps work with packages' +date: 2022-07-14 +tags: ['kibana', 'dev', 'contributor', 'operations', 'packages', 'scripts'] +--- + +`@kbn/pm` is the tool that we use to bootstrap the Kibana repository, build packages with Bazel, and run scripts in packages. + +## commands + +### `yarn kbn bootstrap` + +Use this command to install dependencies, build packages, and prepare the repo for local development. + +### `yarn kbn watch` + +Use this command to build all packages and make sure that they are rebuilt as you make changes. + +### and more! + +There are several commands supported by `@kbn/pm`, but rather than documenting them here they are documented in the help text. Please run `yarn kbn --help` locally to see the most up-to-date info. + +## Why isn't this TypeScript? + +Since this tool is required for bootstrapping the repository it needs to work without any dependencies installed and without a build toolchain. We accomplish this by writing the tool in vanilla JS (shocker!) and using TypeScript to validate the code which is typed via heavy use of JSDoc comments. + +In order to use import/export syntax and enhance the developer experience a little we use the `.mjs` file extension. + +In some cases we actually do use TypeScript files, just for defining complicated types. These files are then imported only in special TS-compatible JSDoc comments, so Node.js will never try to import them but they can be used to define types which are too complicated to define inline or in a JSDoc comment. + +There are cases where `@kbn/pm` relies on code from packages, mostly to prevent reimplementing common functionality. This can only be done in one of two ways: + + 1. With a dynamic `await import(...)` statement that is always run after boostrap is complete, or is wrapped in a try/catch in case bootstrap didn't complete successfully. + 2. By pulling in the source code of the un-built package. + +Option 1 is used in several places, with contingencies in place in case bootstrap failed. Option 2 is used for two pieces of code which are needed in order to run bootstrap: + + 1. `@kbn/plugin-discovery` as we need to populate the `@kbn/synthetic-package-map` to run Bazel + 2. `@kbn/bazel-runner` as we want to have the logic for running bazel in a single location + +Because we load these two packages from source, without being built, before bootstrap is ever run, they can not depend on other packages and must be written in Vanilla JS as well. \ No newline at end of file diff --git a/kbn_pm/src/cli.mjs b/kbn_pm/src/cli.mjs new file mode 100644 index 0000000000000..99d8262f92aa9 --- /dev/null +++ b/kbn_pm/src/cli.mjs @@ -0,0 +1,130 @@ +/* + * 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. + */ + +/** + * This is the script that's run by `yarn kbn`. This script has as little logic + * as possible so that it can: + * - run without being built and without any dependencies + * - can bootstrap the repository, installing all deps and building all packages + * - load additional commands from packages which will extend the functionality + * beyond bootstrapping + */ + +import { Args } from './lib/args.mjs'; +import { getHelp } from './lib/help.mjs'; +import { createFlagError, isCliError } from './lib/cli_error.mjs'; +import { COMMANDS } from './commands/index.mjs'; +import { Log } from './lib/log.mjs'; + +const start = Date.now(); +const args = new Args(process.argv.slice(2), process.env.CI ? ['--quiet'] : []); +const log = new Log(args.getLoggingLevel()); +const cmdName = args.getCommandName(); + +/** + * @param {import('./lib/log.mjs').Log} log + */ +async function tryToGetCiStatsReporter(log) { + try { + const { CiStatsReporter } = await import('@kbn/ci-stats-reporter'); + return CiStatsReporter.fromEnv(log); + } catch { + return; + } +} + +try { + const cmd = cmdName ? COMMANDS.find((c) => c.name === cmdName) : undefined; + + if (cmdName && !cmd) { + throw createFlagError(`Invalid command name [${cmdName}]`); + } + + if (args.getBooleanValue('help')) { + log._write(await getHelp(cmdName)); + process.exit(0); + } + + if (!cmd) { + throw createFlagError('missing command name'); + } + + /** @type {import('@kbn/ci-stats-reporter').CiStatsTiming[]} */ + const timings = []; + + /** @type {import('./lib/command').CommandRunContext['time']} */ + const time = async (id, block) => { + if (!cmd.reportTimings) { + return await block(); + } + + const start = Date.now(); + log.verbose(`[${id}]`, 'start'); + const [result] = await Promise.allSettled([block()]); + const ms = Date.now() - start; + log.verbose(`[${id}]`, result.status === 'fulfilled' ? 'success' : 'failure', 'in', ms, 'ms'); + timings.push({ + group: cmd.reportTimings.group, + id, + ms, + meta: { + success: result.status === 'fulfilled', + }, + }); + + if (result.status === 'fulfilled') { + return result.value; + } else { + throw result.reason; + } + }; + + const [result] = await Promise.allSettled([ + (async () => + await cmd.run({ + args, + log, + time, + }))(), + ]); + + if (cmd.reportTimings) { + timings.push({ + group: cmd.reportTimings.group, + id: cmd.reportTimings.id, + ms: Date.now() - start, + meta: { + success: result.status === 'fulfilled', + }, + }); + } + + if (timings.length) { + const reporter = await tryToGetCiStatsReporter(log); + if (reporter) { + await reporter.timings({ timings }); + } + } + + if (result.status === 'rejected') { + throw result.reason; + } +} catch (error) { + if (!isCliError(error)) { + throw error; + } + + log.error(`[${cmdName}] failed: ${error.message}`); + + if (error.showHelp) { + log._write(''); + log._write(await getHelp(cmdName)); + } + + process.exit(error.exitCode ?? 1); +} diff --git a/kbn_pm/src/commands/bootstrap/bootstrap_command.mjs b/kbn_pm/src/commands/bootstrap/bootstrap_command.mjs new file mode 100644 index 0000000000000..65876b0799aeb --- /dev/null +++ b/kbn_pm/src/commands/bootstrap/bootstrap_command.mjs @@ -0,0 +1,127 @@ +/* + * 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 { spawnSync } from '../../lib/spawn.mjs'; +import * as Bazel from '../../lib/bazel.mjs'; +import { haveNodeModulesBeenManuallyDeleted, removeYarnIntegrityFileIfExists } from './yarn.mjs'; +import { setupRemoteCache } from './setup_remote_cache.mjs'; +import { regenerateSyntheticPackageMap } from './regenerate_synthetic_package_map.mjs'; +import { sortPackageJson } from './sort_package_json.mjs'; +import { pluginDiscovery } from './plugins.mjs'; +import { regenerateBaseTsconfig } from './regenerate_base_tsconfig.mjs'; + +/** @type {import('../../lib/command').Command} */ +export const command = { + name: 'bootstrap', + intro: 'Bootstrap the Kibana repository, installs all dependencies and builds all packages', + description: ` + This command should be run every time you checkout a new revision, or can be used to build all packages + once after making a change locally. Package builds are cached remotely so when you don't have local + changes build artifacts will be downloaded from the remote cache. + `, + flagsHelp: ` + --force-install Use this flag to force bootstrap to install yarn dependencies. By default the', + command will attempt to only run yarn installs when necessary, but if you manually', + delete the node modules directory or have an issue in your node_modules directory', + you might need to force the install manually.', + --offline Run the installation process without consulting online resources. This is useful and', + sometimes necessary for using bootstrap on an airplane for instance. The local caches', + will be used exclusively, including a yarn-registry local mirror which is created and', + maintained by successful online bootstrap executions.', + --no-validate By default bootstrap validates the yarn.lock file to check for a handfull of', + conditions. If you run into issues with this process locally you can disable it by', + passing this flag. + --no-vscode By default bootstrap updates the .vscode directory to include commonly useful vscode + settings for local development. Disable this process either pass this flag or set + the KBN_BOOTSTRAP_NO_VSCODE=true environment variable. + --quiet Prevent logging more than basic success/error messages + `, + reportTimings: { + group: 'scripts/kbn bootstrap', + id: 'total', + }, + async run({ args, log, time }) { + const offline = args.getBooleanValue('offline') ?? false; + const validate = args.getBooleanValue('validate') ?? true; + const quiet = args.getBooleanValue('quiet') ?? false; + const vscodeConfig = + args.getBooleanValue('vscode') ?? (process.env.KBN_BOOTSTRAP_NO_VSCODE ? false : true); + + // Force install is set in case a flag is passed into yarn kbn bootstrap or + // our custom logic have determined there is a chance node_modules have been manually deleted and as such bazel + // tracking mechanism is no longer valid + const forceInstall = + args.getBooleanValue('force-install') ?? haveNodeModulesBeenManuallyDeleted(); + + Bazel.tryRemovingBazeliskFromYarnGlobal(log); + + // Install bazel machinery tools if needed + Bazel.ensureInstalled(log); + + // Setup remote cache settings in .bazelrc.cache if needed + setupRemoteCache(log); + + // Bootstrap process for Bazel packages + // Bazel is now managing dependencies so yarn install + // will happen as part of this + // + // NOTE: Bazel projects will be introduced incrementally + // And should begin from the ones with none dependencies forward. + // That way non bazel projects could depend on bazel projects but not the other way around + // That is only intended during the migration process while non Bazel projects are not removed at all. + if (forceInstall) { + await time('force install dependencies', async () => { + removeYarnIntegrityFileIfExists(); + await Bazel.expungeCache(log, { quiet }); + await Bazel.installYarnDeps(log, { offline, quiet }); + }); + } + + const plugins = await time('plugin discovery', async () => { + return pluginDiscovery(); + }); + + // generate the synthetic package map which powers several other features, needed + // as an input to the package build + await time('regenerate synthetic package map', async () => { + regenerateSyntheticPackageMap(plugins); + }); + + // build packages + await time('build packages', async () => { + await Bazel.buildPackages(log, { offline, quiet }); + }); + + await time('sort package json', async () => { + await sortPackageJson(); + }); + await time('regenerate tsconfig.base.json', async () => { + regenerateBaseTsconfig(plugins); + }); + + if (validate) { + // now that packages are built we can import `@kbn/yarn-lock-validator` + const { readYarnLock, validateDependencies } = await import('@kbn/yarn-lock-validator'); + const yarnLock = await time('read yarn.lock', async () => { + return await readYarnLock(); + }); + await time('validate dependencies', async () => { + await validateDependencies(log, yarnLock); + }); + } + + if (vscodeConfig) { + await time('update vscode config', async () => { + // Update vscode settings + spawnSync('node', ['scripts/update_vscode_config']); + + log.success('vscode config updated'); + }); + } + }, +}; diff --git a/kbn_pm/src/commands/bootstrap/normalize_path.mjs b/kbn_pm/src/commands/bootstrap/normalize_path.mjs new file mode 100644 index 0000000000000..1ff4d286bff3a --- /dev/null +++ b/kbn_pm/src/commands/bootstrap/normalize_path.mjs @@ -0,0 +1,61 @@ +/* eslint-disable @kbn/eslint/require-license-header */ +/** + * @notice + * This code includes a copy of the `normalize-path` + * https://github.com/jonschlinkert/normalize-path/blob/52c3a95ebebc2d98c1ad7606cbafa7e658656899/index.js + * + * The MIT License (MIT) + * + * Copyright (c) 2014-2018, Jon Schlinkert. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +/** + * @param {string} path + * @returns {string} + */ +export function normalizePath(path) { + if (typeof path !== 'string') { + throw new TypeError('expected path to be a string'); + } + + if (path === '\\' || path === '/') return '/'; + + const len = path.length; + if (len <= 1) return path; + + // ensure that win32 namespaces has two leading slashes, so that the path is + // handled properly by the win32 version of path.parse() after being normalized + // https://msdn.microsoft.com/library/windows/desktop/aa365247(v=vs.85).aspx#namespaces + let prefix = ''; + if (len > 4 && path[3] === '\\') { + const ch = path[2]; + if ((ch === '?' || ch === '.') && path.slice(0, 2) === '\\\\') { + path = path.slice(2); + prefix = '//'; + } + } + + const segs = path.split(/[/\\]+/); + if (segs[segs.length - 1] === '') { + segs.pop(); + } + return prefix + segs.join('/'); +} diff --git a/kbn_pm/src/commands/bootstrap/plugins.mjs b/kbn_pm/src/commands/bootstrap/plugins.mjs new file mode 100644 index 0000000000000..70b7d98cee4da --- /dev/null +++ b/kbn_pm/src/commands/bootstrap/plugins.mjs @@ -0,0 +1,51 @@ +/* + * 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 { REPO_ROOT } from '../../lib/paths.mjs'; + +/** @type {string} */ +const PLUGIN_DISCOVERY_SRC = '../../../../packages/kbn-plugin-discovery/src/index.js'; + +/** + * @param {string} pluginId + * @returns {string} + */ +export function convertPluginIdToPackageId(pluginId) { + if (pluginId === 'core') { + // core is the only non-plugin + return `@kbn/core`; + } + + return `@kbn/${pluginId + .split('') + .flatMap((c) => (c.toUpperCase() === c ? `-${c.toLowerCase()}` : c)) + .join('')}-plugin` + .replace(/-\w(-\w)+-/g, (match) => `-${match.split('-').join('')}-`) + .replace(/-plugin-plugin$/, '-plugin'); +} + +/** + * @returns {Promise} + */ +export async function pluginDiscovery() { + /* eslint-disable no-unsanitized/method */ + /** @type {import('@kbn/plugin-discovery')} */ + const { getPluginSearchPaths, simpleKibanaPlatformPluginDiscovery } = await import( + PLUGIN_DISCOVERY_SRC + ); + /* eslint-enable no-unsanitized/method */ + + const searchPaths = getPluginSearchPaths({ + rootDir: REPO_ROOT, + examples: true, + oss: false, + testPlugins: true, + }); + + return simpleKibanaPlatformPluginDiscovery(searchPaths, []); +} diff --git a/packages/kbn-pm/src/utils/regenerate_base_tsconfig.ts b/kbn_pm/src/commands/bootstrap/regenerate_base_tsconfig.mjs similarity index 63% rename from packages/kbn-pm/src/utils/regenerate_base_tsconfig.ts rename to kbn_pm/src/commands/bootstrap/regenerate_base_tsconfig.mjs index 667dc97d9ee8e..69b288f7981bb 100644 --- a/packages/kbn-pm/src/utils/regenerate_base_tsconfig.ts +++ b/kbn_pm/src/commands/bootstrap/regenerate_base_tsconfig.mjs @@ -6,30 +6,33 @@ * Side Public License, v 1. */ -import Fs from 'fs/promises'; import Path from 'path'; +import Fs from 'fs'; -import normalizePath from 'normalize-path'; -import { KibanaPlatformPlugin } from '@kbn/plugin-discovery'; -import { convertPluginIdToPackageId } from './convert_plugin_id_to_package_id'; +import { REPO_ROOT } from '../../lib/paths.mjs'; +import { convertPluginIdToPackageId } from './plugins.mjs'; +import { normalizePath } from './normalize_path.mjs'; -export async function regenerateBaseTsconfig(plugins: KibanaPlatformPlugin[], repoRoot: string) { - const tsconfigPath = Path.resolve(repoRoot, 'tsconfig.base.json'); - const lines = (await Fs.readFile(tsconfigPath, 'utf-8')).split('\n'); +/** + * @param {import('@kbn/plugin-discovery').KibanaPlatformPlugin[]} plugins + */ +export function regenerateBaseTsconfig(plugins) { + const tsconfigPath = Path.resolve(REPO_ROOT, 'tsconfig.base.json'); + const lines = Fs.readFileSync(tsconfigPath, 'utf-8').split('\n'); const packageMap = plugins .slice() .sort((a, b) => a.manifestPath.localeCompare(b.manifestPath)) .flatMap((p) => { const id = convertPluginIdToPackageId(p.manifest.id); - const path = normalizePath(Path.relative(repoRoot, p.directory)); + const path = normalizePath(Path.relative(REPO_ROOT, p.directory)); return [` "${id}": ["${path}"],`, ` "${id}/*": ["${path}/*"],`]; }); const start = lines.findIndex((l) => l.trim() === '// START AUTOMATED PACKAGE LISTING'); const end = lines.findIndex((l) => l.trim() === '// END AUTOMATED PACKAGE LISTING'); - await Fs.writeFile( + Fs.writeFileSync( tsconfigPath, [...lines.slice(0, start + 1), ...packageMap, ...lines.slice(end)].join('\n') ); diff --git a/kbn_pm/src/commands/bootstrap/regenerate_synthetic_package_map.mjs b/kbn_pm/src/commands/bootstrap/regenerate_synthetic_package_map.mjs new file mode 100644 index 0000000000000..22898daa92b21 --- /dev/null +++ b/kbn_pm/src/commands/bootstrap/regenerate_synthetic_package_map.mjs @@ -0,0 +1,34 @@ +/* + * 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 Path from 'path'; +import Fs from 'fs'; + +import { normalizePath } from './normalize_path.mjs'; +import { REPO_ROOT } from '../../lib/paths.mjs'; +import { convertPluginIdToPackageId } from './plugins.mjs'; + +/** + * @param {import('@kbn/plugin-discovery').KibanaPlatformPlugin[]} plugins + */ +export function regenerateSyntheticPackageMap(plugins) { + /** @type {Array<[string, string]>} */ + const entries = [['@kbn/core', 'src/core']]; + + for (const plugin of plugins) { + entries.push([ + convertPluginIdToPackageId(plugin.manifest.id), + normalizePath(Path.relative(REPO_ROOT, plugin.directory)), + ]); + } + + Fs.writeFileSync( + Path.resolve(REPO_ROOT, 'packages/kbn-synthetic-package-map/synthetic-packages.json'), + JSON.stringify(entries, null, 2) + ); +} diff --git a/packages/kbn-pm/src/utils/bazel/setup_remote_cache.ts b/kbn_pm/src/commands/bootstrap/setup_remote_cache.mjs similarity index 52% rename from packages/kbn-pm/src/utils/bazel/setup_remote_cache.ts rename to kbn_pm/src/commands/bootstrap/setup_remote_cache.mjs index 9ec7f36821d3d..6961e644a0989 100644 --- a/packages/kbn-pm/src/utils/bazel/setup_remote_cache.ts +++ b/kbn_pm/src/commands/bootstrap/setup_remote_cache.mjs @@ -5,17 +5,19 @@ * in compliance with, at your election, the Elastic License 2.0 or the Server * Side Public License, v 1. */ -import dedent from 'dedent'; -import { writeFileSync } from 'fs'; -import { resolve } from 'path'; -import { spawn } from '../child_process'; -import { log } from '../log'; -import { isFile, readFile } from '../fs'; -async function isElasticCommitter() { +import Path from 'path'; +import Fs from 'fs'; +import { spawnSync } from 'child_process'; + +import { isFile } from '../../lib/fs.mjs'; +import { dedent } from '../../lib/indent.mjs'; +import { REPO_ROOT } from '../../lib/paths.mjs'; + +function isElasticCommitter() { try { - const { stdout: email } = await spawn('git', ['config', 'user.email'], { - stdio: 'pipe', + const { stdout: email } = spawnSync('git', ['config', 'user.email'], { + encoding: 'utf8', }); return email.trim().endsWith('@elastic.co'); @@ -24,31 +26,39 @@ async function isElasticCommitter() { } } -async function upToDate(settingsPath: string) { - if (!(await isFile(settingsPath))) { +/** + * + * @param {string} settingsPath + * @returns + */ +function upToDate(settingsPath) { + if (!isFile(settingsPath)) { return false; } - const readSettingsFile = await readFile(settingsPath, 'utf8'); + const readSettingsFile = Fs.readFileSync(settingsPath, 'utf8'); return readSettingsFile.startsWith('# V2 '); } -export async function setupRemoteCache(repoRootPath: string) { +/** + * @param {import('@kbn/some-dev-log').SomeDevLog} log + */ +export function setupRemoteCache(log) { // The remote cache is only for Elastic employees working locally (CI cache settings are handled elsewhere) if ( process.env.FORCE_BOOTSTRAP_REMOTE_CACHE !== 'true' && - (process.env.CI || !(await isElasticCommitter())) + (process.env.CI || !isElasticCommitter()) ) { return; } - log.debug(`[bazel_tools] setting up remote cache settings if necessary`); + log.debug(`setting up remote cache settings if necessary`); - const settingsPath = resolve(repoRootPath, '.bazelrc.cache'); + const settingsPath = Path.resolve(REPO_ROOT, '.bazelrc.cache'); // Checks if we should upgrade or install the config file - if (await upToDate(settingsPath)) { - log.debug(`[bazel_tools] remote cache config already exists and is up-to-date, skipping`); + if (upToDate(settingsPath)) { + log.debug(`remote cache config already exists and is up-to-date, skipping`); return; } @@ -60,6 +70,6 @@ export async function setupRemoteCache(repoRootPath: string) { build --incompatible_remote_results_ignore_disk `; - writeFileSync(settingsPath, contents); - log.info(`[bazel_tools] remote cache settings written to ${settingsPath}`); + Fs.writeFileSync(settingsPath, contents); + log.info(`remote cache settings written to ${settingsPath}`); } diff --git a/packages/kbn-pm/src/utils/regenerate_package_json.ts b/kbn_pm/src/commands/bootstrap/sort_package_json.mjs similarity index 53% rename from packages/kbn-pm/src/utils/regenerate_package_json.ts rename to kbn_pm/src/commands/bootstrap/sort_package_json.mjs index 6124aebc38879..f78401c257e40 100644 --- a/packages/kbn-pm/src/utils/regenerate_package_json.ts +++ b/kbn_pm/src/commands/bootstrap/sort_package_json.mjs @@ -6,13 +6,15 @@ * Side Public License, v 1. */ -import Fsp from 'fs/promises'; import Path from 'path'; +import Fs from 'fs'; -import { sortPackageJson } from '@kbn/sort-package-json'; +import { REPO_ROOT } from '../../lib/paths.mjs'; -export async function regeneratePackageJson(rootPath: string) { - const path = Path.resolve(rootPath, 'package.json'); - const json = await Fsp.readFile(path, 'utf8'); - await Fsp.writeFile(path, sortPackageJson(json)); +export async function sortPackageJson() { + const { sortPackageJson } = await import('@kbn/sort-package-json'); + + const path = Path.resolve(REPO_ROOT, 'package.json'); + const json = Fs.readFileSync(path, 'utf8'); + Fs.writeFileSync(path, sortPackageJson(json)); } diff --git a/kbn_pm/src/commands/bootstrap/yarn.mjs b/kbn_pm/src/commands/bootstrap/yarn.mjs new file mode 100644 index 0000000000000..db11c3b12930e --- /dev/null +++ b/kbn_pm/src/commands/bootstrap/yarn.mjs @@ -0,0 +1,53 @@ +/* + * 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 Path from 'path'; +import Fs from 'fs'; + +import { REPO_ROOT } from '../../lib/paths.mjs'; +import { maybeRealpath, isFile, isDirectory } from '../../lib/fs.mjs'; + +// yarn integrity file checker +export function removeYarnIntegrityFileIfExists() { + try { + const nodeModulesRealPath = maybeRealpath(Path.resolve(REPO_ROOT, 'node_modules')); + const yarnIntegrityFilePath = Path.resolve(nodeModulesRealPath, '.yarn-integrity'); + + // check if the file exists and delete it in that case + if (isFile(yarnIntegrityFilePath)) { + Fs.unlinkSync(yarnIntegrityFilePath); + } + } catch { + // no-op + } +} + +// yarn and bazel integration checkers +function areNodeModulesPresent() { + try { + return isDirectory(Path.resolve(REPO_ROOT, 'node_modules')); + } catch { + return false; + } +} + +function haveBazelFoldersBeenCreatedBefore() { + try { + return ( + isDirectory(Path.resolve(REPO_ROOT, 'bazel-bin/packages')) || + isDirectory(Path.resolve(REPO_ROOT, 'bazel-kibana/packages')) || + isDirectory(Path.resolve(REPO_ROOT, 'bazel-out/host')) + ); + } catch { + return false; + } +} + +export function haveNodeModulesBeenManuallyDeleted() { + return !areNodeModulesPresent() && haveBazelFoldersBeenCreatedBefore(); +} diff --git a/kbn_pm/src/commands/clean_command.mjs b/kbn_pm/src/commands/clean_command.mjs new file mode 100644 index 0000000000000..a112431eeda57 --- /dev/null +++ b/kbn_pm/src/commands/clean_command.mjs @@ -0,0 +1,44 @@ +/* + * 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 { dedent } from '../lib/indent.mjs'; +import { cleanPaths } from '../lib/clean.mjs'; +import * as Bazel from '../lib/bazel.mjs'; +import { findPluginCleanPaths } from '../lib/find_clean_paths.mjs'; + +/** @type {import('../lib/command').Command} */ +export const command = { + name: 'clean', + description: 'Deletes output directories and resets internal caches', + reportTimings: { + group: 'scripts/kbn clean', + id: 'total', + }, + flagsHelp: ` + --quiet Prevent logging more than basic success/error messages + `, + async run({ args, log }) { + log.warning(dedent` + This command is only necessary for the circumstance where you need to recover a consistent + state when problems arise. If you need to run this command often, please let us know by + filling out this form: https://ela.st/yarn-kbn-clean. + + Please note it might not solve problems with node_modules. To solve problems around node_modules + you might need to run 'yarn kbn reset'. + `); + + await cleanPaths(log, await findPluginCleanPaths(log)); + + // Runs Bazel soft clean + if (Bazel.isInstalled(log)) { + await Bazel.clean(log, { + quiet: args.getBooleanValue('quiet'), + }); + } + }, +}; diff --git a/kbn_pm/src/commands/index.mjs b/kbn_pm/src/commands/index.mjs new file mode 100644 index 0000000000000..8d4638310d329 --- /dev/null +++ b/kbn_pm/src/commands/index.mjs @@ -0,0 +1,15 @@ +/* + * 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. + */ + +export const COMMANDS = [ + (await import('./bootstrap/bootstrap_command.mjs')).command, + (await import('./watch_command.mjs')).command, + (await import('./run_in_packages_command.mjs')).command, + (await import('./clean_command.mjs')).command, + (await import('./reset_command.mjs')).command, +]; diff --git a/kbn_pm/src/commands/reset_command.mjs b/kbn_pm/src/commands/reset_command.mjs new file mode 100644 index 0000000000000..1b218087bd33d --- /dev/null +++ b/kbn_pm/src/commands/reset_command.mjs @@ -0,0 +1,47 @@ +/* + * 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 Path from 'path'; + +import { REPO_ROOT } from '../lib/paths.mjs'; +import { dedent } from '../lib/indent.mjs'; +import { cleanPaths } from '../lib/clean.mjs'; +import * as Bazel from '../lib/bazel.mjs'; +import { findPluginCleanPaths, readCleanPatterns } from '../lib/find_clean_paths.mjs'; + +/** @type {import('../lib/command').Command} */ +export const command = { + name: 'reset', + description: + 'Deletes node_modules and output directories, resets internal and disk caches, and stops Bazel server', + reportTimings: { + group: 'scripts/kbn reset', + id: 'total', + }, + flagsHelp: ` + --quiet Prevent logging more than basic success/error messages + `, + async run({ args, log }) { + log.warning(dedent` + In most cases, 'yarn kbn clean' is all that should be needed to recover a consistent state when + problems arise. However for the rare cases where something get corrupt on node_modules you might need this command. + If you think you need to use this command very often (which is not normal), please let us know. + `); + + await cleanPaths(log, [ + Path.resolve(REPO_ROOT, 'node_modules'), + Path.resolve(REPO_ROOT, 'x-pack/node_modules'), + ...readCleanPatterns(REPO_ROOT), + ...(await findPluginCleanPaths(log)), + ]); + + const quiet = args.getBooleanValue('quiet'); + Bazel.expungeCache(log, { quiet }); + Bazel.cleanDiskCache(log); + }, +}; diff --git a/kbn_pm/src/commands/run_in_packages_command.mjs b/kbn_pm/src/commands/run_in_packages_command.mjs new file mode 100644 index 0000000000000..78a168463e6db --- /dev/null +++ b/kbn_pm/src/commands/run_in_packages_command.mjs @@ -0,0 +1,76 @@ +/* + * 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 Path from 'path'; + +import { REPO_ROOT } from '../lib/paths.mjs'; +import { spawnSync, spawnStreaming } from '../lib/spawn.mjs'; + +/** @type {import('../lib/command').Command} */ +export const command = { + name: 'run-in-packages', + usage: '[...flags] [...subFlags]', + description: ` + Run script defined in package.json in each package that contains that script. Any flags passed + after the script name will be passed directly to the script. + `, + flagsHelp: ` + --filter package name to be filter packages by, can be specified multiple times + and only packages matching this filter will be matched + --exclude package name to be excluded, can be specified multiple times + --quiet only log the output of commands if they fail + `, + reportTimings: { + group: 'scripts/kbn run', + id: 'total', + }, + async run({ log, args }) { + const scriptName = args.getPositionalArgs()[0]; + + const rawArgs = args.getRawArgs(); + const i = rawArgs.indexOf(scriptName); + const scriptArgs = i !== -1 ? rawArgs.slice(i + 1) : []; + + const exclude = args.getStringValues('exclude') ?? []; + const include = args.getStringValues('include') ?? []; + + const { discoverBazelPackages } = await import('@kbn/bazel-packages'); + const packages = await discoverBazelPackages(REPO_ROOT); + for (const { pkg, normalizedRepoRelativeDir } of packages) { + if ( + exclude.includes(pkg.name) || + (include.length && !include.includes(pkg.name)) || + !pkg.scripts || + !Object.hasOwn(pkg.scripts, scriptName) + ) { + continue; + } + + log.debug( + `running [${scriptName}] script in [${pkg.name}]`, + scriptArgs.length ? `with args [${scriptArgs.join(' ')}]` : '' + ); + + const cwd = Path.resolve(REPO_ROOT, normalizedRepoRelativeDir); + + if (args.getBooleanValue('quiet')) { + spawnSync('yarn', ['run', scriptName, ...scriptArgs], { + cwd, + description: `${scriptName} in ${pkg.name}`, + }); + } else { + await spawnStreaming('yarn', ['run', scriptName, ...scriptArgs], { + cwd: cwd, + logPrefix: ' ', + }); + } + + log.success(`Ran [${scriptName}] in [${pkg.name}]`); + } + }, +}; diff --git a/kbn_pm/src/commands/watch_command.mjs b/kbn_pm/src/commands/watch_command.mjs new file mode 100644 index 0000000000000..537721d58aae5 --- /dev/null +++ b/kbn_pm/src/commands/watch_command.mjs @@ -0,0 +1,31 @@ +/* + * 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 * as Bazel from '../lib/bazel.mjs'; + +/** @type {import('../lib/command').Command} */ +export const command = { + name: 'watch', + description: 'Runs a build in the Bazel built packages and keeps watching them for changes', + flagsHelp: ` + --offline Run the installation process without consulting online resources. This is useful and', + sometimes necessary for using bootstrap on an airplane for instance. The local caches', + will be used exclusively, including a yarn-registry local mirror which is created and', + maintained by successful online bootstrap executions.', + `, + reportTimings: { + group: 'scripts/kbn watch', + id: 'total', + }, + + async run({ args, log }) { + await Bazel.watch(log, { + offline: args.getBooleanValue('offline') ?? true, + }); + }, +}; diff --git a/kbn_pm/src/lib/args.mjs b/kbn_pm/src/lib/args.mjs new file mode 100644 index 0000000000000..034f4b7d9becf --- /dev/null +++ b/kbn_pm/src/lib/args.mjs @@ -0,0 +1,182 @@ +/* + * 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 { createFlagError } from './cli_error.mjs'; + +/** + * @param {string[]} argv + */ +function parseArgv(argv) { + /** @type {string[]} */ + const raw = []; + /** @type {string[]} */ + const positional = []; + /** @type {Map} */ + const flags = new Map(); + + for (const arg of argv) { + raw.push(arg); + + if (!arg.startsWith('--')) { + // positional arguments are anything that doesn't start with "--" + positional.push(arg); + continue; + } + + // flags always start with "--" and might have an =value attached. + // - If the flag name starts with "no-", like `--no-flag`, it will set `flag` to `false` + // - If the flag has multiple string values they will be turned into an array of values + const [name, ...value] = arg.slice(2).split('='); + if (value.length === 0) { + // boolean flag + if (name.startsWith('no-')) { + flags.set(name.slice(3), false); + } else { + flags.set(name, true); + } + } else { + flags.set(name, value.join('=')); + } + } + + return { raw, positional, flags }; +} + +export class Args { + #flags; + #positional; + #raw; + #defaults; + + /** + * @param {string[]} argv + * @param {string[]} defaultArgv + */ + constructor(argv, defaultArgv) { + const { flags, positional, raw } = parseArgv(argv); + this.#flags = flags; + this.#positional = positional; + this.#raw = raw; + this.#defaults = parseArgv(defaultArgv).flags; + } + + /** + * @returns {import('@kbn/some-dev-log').SomeLogLevel} + */ + getLoggingLevel() { + if (this.getBooleanValue('quiet')) { + return 'quiet'; + } + + if (this.getBooleanValue('verbose')) { + return 'verbose'; + } + + if (this.getBooleanValue('debug')) { + return 'debug'; + } + + return 'info'; + } + + /** + * Get the command name from the args + */ + getCommandName() { + return this.#positional[0]; + } + + /** + * Get the positional arguments, excludes the command name + */ + getPositionalArgs() { + return this.#positional.slice(1); + } + + /** + * Get all of the passed args + */ + getRawArgs() { + return this.#raw.slice(); + } + + /** + * Get the value of a specific flag as a string, if the argument is specified multiple + * times then only the last value specified will be returned. If the flag was specified + * as a boolean then an error will be thrown. If the flag wasn't specified then + * undefined will be returned. + * @param {string} name + */ + getStringValue(name) { + const value = this.#flags.get(name) ?? this.#defaults.get(name); + if (Array.isArray(value)) { + return value.at(-1); + } + + if (typeof value === 'boolean') { + throw createFlagError(`Expected [--${name}] to have a value, not be a boolean flag`); + } + + return value; + } + + /** + * Get the string values of a flag as an array of values. This will return all values for a + * given flag and any boolean values will cause an error to be thrown. + * @param {string} name + */ + getStringValues(name) { + const value = this.#flags.get(name) ?? this.#defaults.get(name); + if (typeof value === 'string') { + return [value]; + } + + if (value === undefined || Array.isArray(value)) { + return value; + } + + throw createFlagError(`Expected [--${name}] to have a string value`); + } + + /** + * Get the boolean value of a specific flag. If the flag wasn't defined then undefined will + * be returned. If the flag was specified with a string value then an error will be thrown. + * @param {string} name + */ + getBooleanValue(name) { + const value = this.#flags.get(name) ?? this.#defaults.get(name); + if (typeof value === 'boolean' || value === undefined) { + return value; + } + + throw createFlagError( + `Unexpected value for [--${name}], this is a boolean flag and should be specified as just [--${name}] or [--no-${name}]` + ); + } + + /** + * Get the value of a specific flag parsed as a number. If the flag wasn't specified then + * undefined will be returned. If the flag was specified multiple times then the last value + * specified will be used. If the flag's value can't be parsed as a number then an error + * will be returned. + * @param {string} name + */ + getNumberValue(name) { + const value = this.getStringValue(name); + if (value === undefined) { + return value; + } + + const parsed = parseFloat(value); + if (Number.isNaN(parsed)) { + throw createFlagError(`Expected value of [--${name}] to be parsable as a valid number`); + } + + return parsed; + } +} diff --git a/kbn_pm/src/lib/bazel.mjs b/kbn_pm/src/lib/bazel.mjs new file mode 100644 index 0000000000000..3fb27a18e5557 --- /dev/null +++ b/kbn_pm/src/lib/bazel.mjs @@ -0,0 +1,260 @@ +/* + * 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 Path from 'path'; +import Fs from 'fs'; + +import { spawnSync } from './spawn.mjs'; +import * as Color from './colors.mjs'; +import { createCliError } from './cli_error.mjs'; +import { REPO_ROOT } from './paths.mjs'; +import { cleanPaths } from './clean.mjs'; +import { indent } from './indent.mjs'; + +const BAZEL_RUNNER_SRC = '../../../packages/kbn-bazel-runner/src/index.js'; + +async function getBazelRunner() { + /* eslint-disable no-unsanitized/method */ + /** @type {import('@kbn/bazel-runner')} */ + const { runBazel, runIBazel } = await import(BAZEL_RUNNER_SRC); + /* eslint-enable no-unsanitized/method */ + return { runBazel, runIBazel }; +} + +/** + * @param {import('./log.mjs').Log} log + * @param {string} name + * @param {number} code + * @param {string} output + */ +function throwBazelError(log, name, code, output) { + const tag = Color.title('HINT'); + log._write( + [ + tag, + tag + + 'If experiencing problems with node_modules try `yarn kbn bootstrap --force-install` or as last resort `yarn kbn reset && yarn kbn bootstrap`', + tag, + ].join('\n') + ); + + throw createCliError( + `[${name}] exited with code [${code}]${output ? `\n output:\n${indent(4, output)}}` : ''}` + ); +} + +/** + * @param {import('./log.mjs').Log} log + * @param {string[]} inputArgs + * @param {{ quiet?: boolean; offline?: boolean, env?: Record } | undefined} opts + */ +async function runBazel(log, inputArgs, opts = undefined) { + const bazel = (await getBazelRunner()).runBazel; + + const args = [...(opts?.offline ? ['--config=offline'] : []), ...inputArgs]; + log.debug(`> bazel ${args.join(' ')}`); + await bazel(args, { + env: opts?.env, + cwd: REPO_ROOT, + quiet: opts?.quiet, + logPrefix: Color.info('[bazel]'), + onErrorExit(code, output) { + throwBazelError(log, 'bazel', code, output); + }, + }); +} + +/** + * + * @param {import('./log.mjs').Log} log + * @param {{ offline: boolean } | undefined} opts + */ +export async function watch(log, opts = undefined) { + const ibazel = (await getBazelRunner()).runIBazel; + + const args = [ + // --run_output=false arg will disable the iBazel notifications about gazelle + // and buildozer when running it. Could also be solved by adding a root + // `.bazel_fix_commands.json` but its not needed at the moment + '--run_output=false', + 'build', + '//packages:build', + '--show_result=1', + ...(opts?.offline ? ['--config=offline'] : []), + ]; + log.debug(`> ibazel ${args.join(' ')}`); + await ibazel(args, { + cwd: REPO_ROOT, + logPrefix: Color.info('[ibazel]'), + onErrorExit(code, output) { + throwBazelError(log, 'ibazel', code, output); + }, + }); +} + +/** + * @param {import('./log.mjs').Log} log + * @param {{ quiet?: boolean } | undefined} opts + */ +export async function clean(log, opts = undefined) { + await runBazel(log, ['clean'], { + quiet: opts?.quiet, + }); + log.success('soft cleaned bazel'); +} + +/** + * @param {import('./log.mjs').Log} log + * @param {{ quiet?: boolean } | undefined} opts + */ +export async function expungeCache(log, opts = undefined) { + await runBazel(log, ['clean', '--expunge'], { + quiet: opts?.quiet, + }); + log.success('hard cleaned bazel'); +} + +/** + * @param {import('./log.mjs').Log} log + */ +export async function cleanDiskCache(log) { + const args = ['info', 'repository_cache']; + log.debug(`> bazel ${args.join(' ')}`); + const repositoryCachePath = spawnSync('bazel', args); + + await cleanPaths(log, [ + Path.resolve(Path.dirname(repositoryCachePath), 'disk-cache'), + Path.resolve(repositoryCachePath), + ]); + + log.success('removed disk caches'); +} + +/** + * @param {import('./log.mjs').Log} log + * @param {{ offline?: boolean, quiet?: boolean } | undefined} opts + */ +export async function installYarnDeps(log, opts = undefined) { + await runBazel(log, ['run', '@nodejs//:yarn'], { + offline: opts?.offline, + quiet: opts?.quiet, + env: { + SASS_BINARY_SITE: + 'https://us-central1-elastic-kibana-184716.cloudfunctions.net/kibana-ci-proxy-cache/node-sass', + RE2_DOWNLOAD_MIRROR: + 'https://us-central1-elastic-kibana-184716.cloudfunctions.net/kibana-ci-proxy-cache/node-re2', + }, + }); + + log.success('yarn deps installed'); +} + +/** + * @param {import('./log.mjs').Log} log + * @param {{ offline?: boolean, quiet?: boolean } | undefined} opts + */ +export async function buildPackages(log, opts = undefined) { + await runBazel(log, ['build', '//packages:build', '--show_result=1'], { + offline: opts?.offline, + quiet: opts?.quiet, + }); + + log.success('packages built'); +} + +/** + * @param {string} versionFilename + * @returns + */ +function readBazelToolsVersionFile(versionFilename) { + const version = Fs.readFileSync(Path.resolve(REPO_ROOT, versionFilename), 'utf8').trim(); + + if (!version) { + throw new Error( + `Failed on reading bazel tools versions\n ${versionFilename} file do not contain any version set` + ); + } + + return version; +} + +/** + * @param {import('./log.mjs').Log} log + */ +export function tryRemovingBazeliskFromYarnGlobal(log) { + try { + log.debug('Checking if Bazelisk is installed on the yarn global scope'); + const stdout = spawnSync('yarn', ['global', 'list']); + + if (stdout.includes(`@bazel/bazelisk@`)) { + log.debug('Bazelisk was found on yarn global scope, removing it'); + spawnSync('yarn', ['global', 'remove', `@bazel/bazelisk`]); + + log.info(`bazelisk was installed on Yarn global packages and is now removed`); + return true; + } + + return false; + } catch { + return false; + } +} + +/** + * @param {import('./log.mjs').Log} log + */ +export function isInstalled(log) { + try { + log.debug('getting bazel version'); + const stdout = spawnSync('bazel', ['--version']).trim(); + const bazelVersion = readBazelToolsVersionFile('.bazelversion'); + + if (stdout === `bazel ${bazelVersion}`) { + return true; + } else { + log.info(`Bazel is installed (${stdout}), but was expecting ${bazelVersion}`); + return false; + } + } catch { + return false; + } +} + +/** + * @param {import('./log.mjs').Log} log + */ +export function ensureInstalled(log) { + if (isInstalled(log)) { + return; + } + + // Install bazelisk if not installed + log.debug(`reading bazel tools versions from version files`); + const bazeliskVersion = readBazelToolsVersionFile('.bazeliskversion'); + const bazelVersion = readBazelToolsVersionFile('.bazelversion'); + + log.info(`installing Bazel tools`); + + log.debug( + `bazelisk is not installed. Installing @bazel/bazelisk@${bazeliskVersion} and bazel@${bazelVersion}` + ); + spawnSync('npm', ['install', '--global', `@bazel/bazelisk@${bazeliskVersion}`], { + env: { + USE_BAZEL_VERSION: bazelVersion, + }, + }); + + const isBazelBinAvailableAfterInstall = isInstalled(log); + if (!isBazelBinAvailableAfterInstall) { + throw new Error( + `an error occurred when installing the Bazel tools. Please make sure you have access to npm globally installed modules on your $PATH` + ); + } + + log.success(`bazel tools installed`); +} diff --git a/kbn_pm/src/lib/clean.mjs b/kbn_pm/src/lib/clean.mjs new file mode 100644 index 0000000000000..0c44e972b26bb --- /dev/null +++ b/kbn_pm/src/lib/clean.mjs @@ -0,0 +1,30 @@ +/* + * 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 Fs from 'fs'; +import Fsp from 'fs/promises'; +import Path from 'path'; + +/** + * + * @param {import('@kbn/some-dev-log').SomeDevLog} log + * @param {string[]} paths + */ +export async function cleanPaths(log, paths) { + for (const path of paths) { + if (!Fs.existsSync(path)) { + continue; + } + + log.info('deleting', Path.relative(process.cwd(), path)); + await Fsp.rm(path, { + recursive: true, + force: true, + }); + } +} diff --git a/kbn_pm/src/lib/cli_error.mjs b/kbn_pm/src/lib/cli_error.mjs new file mode 100644 index 0000000000000..54936f49b6769 --- /dev/null +++ b/kbn_pm/src/lib/cli_error.mjs @@ -0,0 +1,48 @@ +/* + * 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 { isObj } from './obj_helpers.mjs'; + +/** @typedef {Error & { showHelp: boolean, exitCode?: number }} CliError */ + +/** + * Create a CliError instance + * @param {string} message + * @param {{ showHelp?: boolean, exitCode?: number } | undefined} options + * @returns {CliError} + */ +export function createCliError(message, options = undefined) { + /** @type {true} */ + const __isCliError = true; + + return Object.assign(new Error(message), { + __isCliError, + showHelp: options?.showHelp || false, + exitCode: options?.exitCode, + }); +} + +/** + * @param {string} message + */ +export function createFlagError(message) { + return createCliError(message, { + showHelp: true, + exitCode: 1, + }); +} + +/** + * Determine if the passed value is a CliError + * + * @param {unknown} error + * @returns {error is CliError} + */ +export function isCliError(error) { + return isObj(error) && !!error.__isCliError; +} diff --git a/kbn_pm/src/lib/colors.mjs b/kbn_pm/src/lib/colors.mjs new file mode 100644 index 0000000000000..edea708c7f99d --- /dev/null +++ b/kbn_pm/src/lib/colors.mjs @@ -0,0 +1,49 @@ +/* + * 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. + */ + +/** + * Print an error title, prints on a red background with white text + * @param {string} txt + */ +export const err = (txt) => `\x1b[41m\x1b[37m${txt}\x1b[39m\x1b[49m`; + +/** + * Print some text with some spacing, with very high contrast and bold text + * @param {string} txt + */ +export const title = (txt) => `\x1b[100m\x1b[37m\x1b[1m ${txt} \x1b[22m\x1b[39m\x1b[49m`; + +/** + * Print the yellow warning label + * @param {string} txt + */ +export const warning = (txt) => `\x1b[33m${txt}\x1b[39m`; + +/** + * Print the simple blue info label + * @param {string} txt + */ +export const info = (txt) => `\x1b[94m${txt}\x1b[39m`; + +/** + * Print a green success label + * @param {string} txt + */ +export const success = (txt) => `\x1b[32m${txt}\x1b[39m`; + +/** + * Print the simple dim debug label + * @param {string} txt + */ +export const debug = (txt) => `\x1b[2m${txt}\x1b[22m`; + +/** + * Print the bright verbose label + * @param {string} txt + */ +export const verbose = (txt) => `\x1b[35m${txt}\x1b[39m`; diff --git a/kbn_pm/src/lib/command.ts b/kbn_pm/src/lib/command.ts new file mode 100644 index 0000000000000..03568a9ba241f --- /dev/null +++ b/kbn_pm/src/lib/command.ts @@ -0,0 +1,71 @@ +/* + * 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 type { Log } from './log.mjs'; +import type { Args } from './args.mjs'; + +/** + * Helper function to easily time specific parts of a kbn command. Does not produce + * timings unless the reportTimings config is also defined + */ +export type SubCommandTimeFn = (id: string, block: () => Promise) => Promise; + +/** + * Argument passed to the command run function + */ +export interface CommandRunContext { + args: Args; + log: Log; + time: SubCommandTimeFn; +} + +/** + * Description of a command that can be run by kbn/pm + */ +export interface Command { + /** + * The name of the command + */ + name: string; + + /** + * Additionall usage details which should be added after the command name + */ + usage?: string; + + /** + * Text to follow the name of the command in the help output + */ + intro?: string; + + /** + * Summary of the functionality for this command, printed + * between the usage and flags help in the help output + */ + description?: string; + + /** + * Description of the flags this command accepts + */ + flagsHelp?: string; + + /** + * Function which executes the command. + */ + run(ctx: CommandRunContext): Promise; + + /** + * Configuration to send timing data to ci-stats for this command. If the + * time() fn is used those timing records will use the group from this config. + * If this config is not used then the time() fn won't report any data. + */ + reportTimings?: { + group: string; + id: string; + }; +} diff --git a/kbn_pm/src/lib/find_clean_paths.mjs b/kbn_pm/src/lib/find_clean_paths.mjs new file mode 100644 index 0000000000000..e98a949971487 --- /dev/null +++ b/kbn_pm/src/lib/find_clean_paths.mjs @@ -0,0 +1,75 @@ +/* + * 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 Path from 'path'; +import Fs from 'fs'; + +import { REPO_ROOT } from './paths.mjs'; + +/** + * Attempt to load the synthetic package map, if bootstrap hasn't run successfully + * this might fail. + * @param {import('@kbn/some-dev-log').SomeDevLog} log + * @returns {Promise} + */ +async function tryToGetSyntheticPackageMap(log) { + try { + const { readPackageMap } = await import('@kbn/synthetic-package-map'); + return readPackageMap(); + } catch (error) { + log.warning( + 'unable to load synthetic package map, unable to clean target directories in synthetic packages' + ); + return new Map(); + } +} + +/** + * @param {*} packageDir + * @returns {string[]} + */ +export function readCleanPatterns(packageDir) { + let json; + try { + const path = Path.resolve(packageDir, 'package.json'); + json = JSON.parse(Fs.readFileSync(path, 'utf8')); + } catch (error) { + if (error.code === 'ENOENT') { + return []; + } + throw error; + } + + /** @type {string[]} */ + const patterns = json.kibana?.clean?.extraPatterns ?? []; + + return patterns.flatMap((pattern) => { + const absolute = Path.resolve(packageDir, pattern); + + // sanity check to make sure that resolved patterns are "relative" to + // the package dir, if they start with a . then they traverse out of + // the package dir so we drop them + if (Path.relative(packageDir, absolute).startsWith('.')) { + return []; + } + + return absolute; + }); +} + +/** + * @param {import('@kbn/some-dev-log').SomeDevLog} log + * @returns {Promise} + */ +export async function findPluginCleanPaths(log) { + const packageMap = await tryToGetSyntheticPackageMap(log); + return [...packageMap.values()].flatMap((repoRelativePath) => { + const pkgDir = Path.resolve(REPO_ROOT, repoRelativePath); + return [Path.resolve(pkgDir, 'target'), ...readCleanPatterns(pkgDir)]; + }); +} diff --git a/kbn_pm/src/lib/fs.mjs b/kbn_pm/src/lib/fs.mjs new file mode 100644 index 0000000000000..4a1cc9f406aa3 --- /dev/null +++ b/kbn_pm/src/lib/fs.mjs @@ -0,0 +1,51 @@ +/* + * 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 Fs from 'fs'; + +/** + * @param {string} path + * @returns {string} + */ +export function maybeRealpath(path) { + try { + return Fs.realpathSync.native(path); + } catch (error) { + if (error.code !== 'ENOENT') { + throw error; + } + } + + return path; +} + +/** + * @param {string} path + * @returns {boolean} + */ +export function isDirectory(path) { + try { + const stat = Fs.statSync(path); + return stat.isDirectory(); + } catch (error) { + return false; + } +} + +/** + * @param {string} path + * @returns {boolean} + */ +export function isFile(path) { + try { + const stat = Fs.statSync(path); + return stat.isFile(); + } catch (error) { + return false; + } +} diff --git a/kbn_pm/src/lib/help.mjs b/kbn_pm/src/lib/help.mjs new file mode 100644 index 0000000000000..08a5467d92fc3 --- /dev/null +++ b/kbn_pm/src/lib/help.mjs @@ -0,0 +1,56 @@ +/* + * 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 { COMMANDS } from '../commands/index.mjs'; +import { dedent, indent } from './indent.mjs'; +import { title } from './colors.mjs'; + +/** + * @param {string | undefined} cmdName + * @returns {Promise} + */ +export async function getHelp(cmdName = undefined) { + const cmd = cmdName && COMMANDS.find((c) => c.name === cmdName); + + /** + * @param {number} depth + * @param {import('./command').Command} cmd + * @returns {string[]} + */ + const cmdLines = (depth, cmd) => { + const intro = cmd.intro ? dedent(cmd.intro) : ''; + const desc = cmd.description ? dedent(cmd.description) : ''; + const flags = cmd.flagsHelp ? dedent(cmd.flagsHelp) : ''; + + return [ + indent( + depth, + `${title(`yarn kbn ${cmd.name}${cmd.usage ? ` ${cmd.usage}` : ''}`)}${ + intro ? ` ${intro}` : '' + }` + ), + '', + ...(desc ? [indent(depth + 2, desc), ''] : []), + ...(flags ? [indent(depth + 2, 'Flags:'), indent(depth + 4, flags), ''] : []), + ]; + }; + + if (cmd) { + return ['', ...cmdLines(0, cmd)].join('\n'); + } + + const lines = [ + 'Usage:', + ' yarn kbn [...flags]', + '', + 'Commands:', + ...COMMANDS.map((cmd) => cmdLines(2, cmd)).flat(), + ]; + + return lines.join('\n'); +} diff --git a/kbn_pm/src/lib/indent.mjs b/kbn_pm/src/lib/indent.mjs new file mode 100644 index 0000000000000..c1efe6a24a845 --- /dev/null +++ b/kbn_pm/src/lib/indent.mjs @@ -0,0 +1,55 @@ +/* + * 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. + */ + +const NON_WS_RE = /\S/; + +/** + * @param {string} line + */ +const nonWsStart = (line) => line.match(NON_WS_RE)?.index ?? line.length; + +/** + * Dedent the string, trimming all empty lines from the beggining of + * `txt` and finding the first line with non-whitespace characters, then + * subtracting the indent from that line from all subsequent lines + * @param {TemplateStringsArray | string} txts + * @param {...any} vars + */ +export function dedent(txts, ...vars) { + /** @type {string[]} */ + const lines = ( + Array.isArray(txts) ? txts.reduce((acc, txt, i) => `${acc}${vars[i - 1]}${txt}`) : txts + ).split('\n'); + + while (lines.length && lines[0].trim() === '') { + lines.shift(); + } + + /** @type {number | undefined} */ + let depth; + return lines + .map((l) => { + if (depth === undefined) { + depth = nonWsStart(l); + } + + return l.slice(Math.min(nonWsStart(l), depth)); + }) + .join('\n'); +} + +/** + * @param {number} width + * @param {string} txt + * @returns {string} + */ +export const indent = (width, txt) => + txt + .split('\n') + .map((l) => `${' '.repeat(width)}${l}`) + .join('\n'); diff --git a/kbn_pm/src/lib/log.mjs b/kbn_pm/src/lib/log.mjs new file mode 100644 index 0000000000000..d05ff0eaf03c3 --- /dev/null +++ b/kbn_pm/src/lib/log.mjs @@ -0,0 +1,120 @@ +/* + * 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 { format } from 'util'; + +import * as Colors from './colors.mjs'; + +/** @typedef {import('@kbn/some-dev-log').SomeDevLog} SomeDevLog */ + +/** + * @implements {SomeDevLog} + */ +export class Log { + #flags; + + /** + * + * @param {import('@kbn/some-dev-log').SomeLogLevel} level + */ + constructor(level) { + this.#flags = { + error: true, + success: true, + info: level !== 'quiet', + warning: level !== 'quiet', + debug: level === 'debug' || level === 'verbose', + verbose: level === 'verbose', + }; + } + + /** + * Log an error message + * @param {string} msg + * @param {...any} rest + */ + error(msg, ...rest) { + if (this.#flags.error) { + this._fmt(' ERROR ', Colors.err, msg, rest); + } + } + + /** + * Log a verbose message, only shown when using --verbose + * @param {string} msg + * @param {...any} rest + */ + warning(msg, ...rest) { + if (this.#flags.warning) { + this._fmt('warn', Colors.warning, msg, rest); + } + } + + /** + * Log a standard message to the log + * @param {string} msg + * @param {...any} rest + */ + info(msg, ...rest) { + if (this.#flags.info) { + this._fmt('info', Colors.info, msg, rest); + } + } + + /** + * Log a verbose message, only shown when using --verbose + * @param {string} msg + * @param {...any} rest + */ + success(msg, ...rest) { + if (this.#flags.success) { + this._fmt('success', Colors.success, msg, rest); + } + } + + /** + * Log a debug message, only shown when using --debug or --verbose + * @param {string} msg + * @param {...any} rest + */ + debug(msg, ...rest) { + if (this.#flags.debug) { + this._fmt('debg', Colors.debug, msg, rest); + } + } + + /** + * Log a verbose message, only shown when using --verbose + * @param {string} msg + * @param {...any} rest + */ + verbose(msg, ...rest) { + if (this.#flags.verbose) { + this._fmt('verb', Colors.verbose, msg, rest); + } + } + + /** + * @param {string} tag + * @param {(txt: string) => string} color + * @param {string} msg + * @param {...any} rest + */ + _fmt(tag, color, msg, rest) { + const lines = format(msg, ...rest).split('\n'); + const padding = ' '.repeat(tag.length + 1); + this._write(`${color(tag)} ${lines.map((l, i) => (i > 0 ? `${padding}${l}` : l)).join('\n')}`); + } + + /** + * @param {string} txt + */ + _write(txt) { + console.log(txt); + } +} diff --git a/kbn_pm/src/lib/obj_helpers.mjs b/kbn_pm/src/lib/obj_helpers.mjs new file mode 100644 index 0000000000000..b54f332ce37f6 --- /dev/null +++ b/kbn_pm/src/lib/obj_helpers.mjs @@ -0,0 +1,13 @@ +/* + * 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. + */ + +/** + * @param {unknown} v + * @returns {v is Record} + */ +export const isObj = (v) => typeof v === 'object' && v !== null; diff --git a/packages/kbn-pm/index.d.ts b/kbn_pm/src/lib/paths.mjs similarity index 73% rename from packages/kbn-pm/index.d.ts rename to kbn_pm/src/lib/paths.mjs index de0577ee3ed83..f133642792681 100644 --- a/packages/kbn-pm/index.d.ts +++ b/kbn_pm/src/lib/paths.mjs @@ -6,4 +6,6 @@ * Side Public License, v 1. */ -export * from './src'; +import Path from 'path'; + +export const REPO_ROOT = Path.resolve(Path.dirname(new URL(import.meta.url).pathname), '../../..'); diff --git a/kbn_pm/src/lib/spawn.mjs b/kbn_pm/src/lib/spawn.mjs new file mode 100644 index 0000000000000..68a25289184c1 --- /dev/null +++ b/kbn_pm/src/lib/spawn.mjs @@ -0,0 +1,113 @@ +/* + * 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 ChildProcess from 'child_process'; +import Readline from 'readline'; + +import { createCliError } from './cli_error.mjs'; +import { REPO_ROOT } from './paths.mjs'; +import { indent } from './indent.mjs'; + +/** @typedef {{ cwd?: string, env?: Record }} SpawnOpts */ + +/** + * Run a child process and return it's stdout + * @param {string} cmd + * @param {string[]} args + * @param {undefined | (SpawnOpts & { description?: string })} opts + */ +export function spawnSync(cmd, args, opts = undefined) { + const result = ChildProcess.spawnSync(cmd === 'node' ? process.execPath : cmd, args, { + cwd: opts?.cwd ?? REPO_ROOT, + encoding: 'utf8', + env: { + ...process.env, + ...opts?.env, + }, + }); + + if (result.status !== null && result.status > 0) { + throw createCliError( + `[${opts?.description ?? cmd}] exitted with ${result.status}:\n${ + result.stdout.trim() + ? ` stdout:\n${indent(4, result.stdout.trim())}\n\n` + : ' stdout: no output\n' + }${ + result.stderr.trim() + ? ` stderr:\n${indent(4, result.stderr.trim())}\n\n` + : ' stderr: no output\n' + }` + ); + } + + return result.stdout; +} + +/** + * Print each line of output to the console + * @param {import('stream').Readable} stream + * @param {string | undefined} prefix + */ +async function printLines(stream, prefix) { + const int = Readline.createInterface({ + input: stream, + crlfDelay: Infinity, + }); + + for await (const line of int) { + console.log(prefix ? `${prefix} ${line}` : line); + } +} + +/** + * @param {import('events').EventEmitter} emitter + * @param {string} event + * @returns {Promise} + */ +function once(emitter, event) { + return new Promise((resolve) => { + emitter.once(event, resolve); + }); +} + +/** + * Run a child process and print the output to the log + * @param {string} cmd + * @param {string[]} args + * @param {undefined | (SpawnOpts & { logPrefix?: string })} options + */ +export async function spawnStreaming(cmd, args, options = undefined) { + const proc = ChildProcess.spawn(cmd, args, { + env: { + ...process.env, + ...options?.env, + }, + cwd: options?.cwd, + stdio: ['ignore', 'pipe', 'pipe'], + }); + + await Promise.all([ + printLines(proc.stdout, options?.logPrefix), + printLines(proc.stderr, options?.logPrefix), + + // Wait for process to exit, or error + Promise.race([ + once(proc, 'exit').then((code) => { + if (typeof code !== 'number' || code === 0) { + return; + } + + throw new Error(`[${cmd}] exitted with code [${code}]`); + }), + + once(proc, 'error').then((error) => { + throw error; + }), + ]), + ]); +} diff --git a/kbn_pm/tsconfig.json b/kbn_pm/tsconfig.json new file mode 100644 index 0000000000000..06582d6dbd655 --- /dev/null +++ b/kbn_pm/tsconfig.json @@ -0,0 +1,16 @@ +{ + "extends": "../tsconfig.base.json", + "compilerOptions": { + "outDir": "target", + "allowJs": true, + "checkJs": true, + "composite": false, + "target": "ES2022", + "module": "ESNext" + }, + "include": [ + "src/**/*.mjs", + "src/**/*.ts", + ], + "exclude": [] +} diff --git a/nav-kibana-dev.docnav.json b/nav-kibana-dev.docnav.json index f31483fa76849..ada91f9e5f5db 100644 --- a/nav-kibana-dev.docnav.json +++ b/nav-kibana-dev.docnav.json @@ -229,9 +229,6 @@ { "id": "kibCoreChromePluginApi" }, - { - "id": "kibCoreHttpPluginApi" - }, { "id": "kibCoreSavedObjectsPluginApi" }, @@ -450,6 +447,9 @@ { "label": "Build tooling", "items": [ + { + "id": "kibDevDocsOpsKbnPm" + }, { "id": "kibDevDocsOpsOptimizer" }, @@ -487,6 +487,9 @@ }, { "id": "kibDevDocsOpsEslintPluginImports" + }, + { + "id": "kibDevDocsOpsKbnYarnLockValidator" } ] }, @@ -519,6 +522,12 @@ }, { "id": "kibDevDocsOpsEs" + }, + { + "id": "kibDevDocsOpsSomeDevLog" + }, + { + "id": "kibDevDocsOpsDevCliRunner" } ] } diff --git a/package.json b/package.json index 93912b9cf2cf7..2ec9bb79fd254 100644 --- a/package.json +++ b/package.json @@ -597,8 +597,8 @@ "@kbn/performance-testing-dataset-extractor": "link:bazel-bin/packages/kbn-performance-testing-dataset-extractor", "@kbn/plugin-generator": "link:bazel-bin/packages/kbn-plugin-generator", "@kbn/plugin-helpers": "link:bazel-bin/packages/kbn-plugin-helpers", - "@kbn/pm": "link:packages/kbn-pm", "@kbn/scalability-simulation-generator": "link:bazel-bin/packages/kbn-scalability-simulation-generator", + "@kbn/some-dev-log": "link:bazel-bin/packages/kbn-some-dev-log", "@kbn/sort-package-json": "link:bazel-bin/packages/kbn-sort-package-json", "@kbn/spec-to-console": "link:bazel-bin/packages/kbn-spec-to-console", "@kbn/stdio-dev-helpers": "link:bazel-bin/packages/kbn-stdio-dev-helpers", @@ -612,6 +612,7 @@ "@kbn/type-summarizer": "link:bazel-bin/packages/kbn-type-summarizer", "@kbn/type-summarizer-cli": "link:bazel-bin/packages/kbn-type-summarizer-cli", "@kbn/type-summarizer-core": "link:bazel-bin/packages/kbn-type-summarizer-core", + "@kbn/yarn-lock-validator": "link:bazel-bin/packages/kbn-yarn-lock-validator", "@loaders.gl/polyfills": "^2.3.5", "@mapbox/vector-tile": "1.3.1", "@octokit/rest": "^16.35.0", @@ -648,7 +649,6 @@ "@types/chroma-js": "^1.4.2", "@types/chromedriver": "^81.0.1", "@types/classnames": "^2.2.9", - "@types/cmd-shim": "^2.0.0", "@types/color": "^3.0.3", "@types/compression-webpack-plugin": "^2.0.2", "@types/cytoscape": "^3.14.0", @@ -876,6 +876,7 @@ "@types/kbn__shared-ux-services": "link:bazel-bin/packages/kbn-shared-ux-services/npm_module_types", "@types/kbn__shared-ux-storybook": "link:bazel-bin/packages/kbn-shared-ux-storybook/npm_module_types", "@types/kbn__shared-ux-utility": "link:bazel-bin/packages/kbn-shared-ux-utility/npm_module_types", + "@types/kbn__some-dev-log": "link:bazel-bin/packages/kbn-some-dev-log/npm_module_types", "@types/kbn__sort-package-json": "link:bazel-bin/packages/kbn-sort-package-json/npm_module_types", "@types/kbn__std": "link:bazel-bin/packages/kbn-std/npm_module_types", "@types/kbn__stdio-dev-helpers": "link:bazel-bin/packages/kbn-stdio-dev-helpers/npm_module_types", @@ -894,6 +895,7 @@ "@types/kbn__utility-types": "link:bazel-bin/packages/kbn-utility-types/npm_module_types", "@types/kbn__utility-types-jest": "link:bazel-bin/packages/kbn-utility-types-jest/npm_module_types", "@types/kbn__utils": "link:bazel-bin/packages/kbn-utils/npm_module_types", + "@types/kbn__yarn-lock-validator": "link:bazel-bin/packages/kbn-yarn-lock-validator/npm_module_types", "@types/license-checker": "15.0.0", "@types/listr": "^0.14.0", "@types/loader-utils": "^1.1.3", @@ -913,7 +915,6 @@ "@types/moment-duration-format": "^2.2.3", "@types/moment-timezone": "^0.5.30", "@types/mustache": "^0.8.31", - "@types/ncp": "^2.0.1", "@types/nock": "^10.0.3", "@types/node": "16.11.41", "@types/node-fetch": "^2.6.0", @@ -946,7 +947,6 @@ "@types/react-test-renderer": "^16.9.1", "@types/react-virtualized": "^9.18.7", "@types/react-vis": "^1.11.9", - "@types/read-pkg": "^4.0.0", "@types/recompose": "^0.30.6", "@types/reduce-reducers": "^1.0.0", "@types/redux-actions": "^2.6.1", @@ -961,7 +961,6 @@ "@types/source-map-support": "^0.5.3", "@types/stats-lite": "^2.2.0", "@types/strip-ansi": "^5.2.1", - "@types/strong-log-transformer": "^1.0.0", "@types/styled-components": "^5.1.0", "@types/supertest": "^2.0.5", "@types/tapable": "^1.0.6", @@ -980,7 +979,6 @@ "@types/webpack-env": "^1.15.3", "@types/webpack-merge": "^4.1.5", "@types/webpack-sources": "^0.1.4", - "@types/write-pkg": "^3.1.0", "@types/xml-crypto": "^1.4.2", "@types/xml2js": "^0.4.5", "@types/yargs": "^15.0.0", @@ -1011,7 +1009,6 @@ "chokidar": "^3.4.3", "chromedriver": "^103.0.0", "clean-webpack-plugin": "^3.0.0", - "cmd-shim": "^2.1.0", "compression-webpack-plugin": "^4.0.0", "copy-webpack-plugin": "^6.0.2", "cpy": "^8.1.1", @@ -1111,9 +1108,7 @@ "mochawesome-merge": "^4.2.1", "mock-fs": "^5.1.2", "ms-chromium-edge-driver": "^0.5.1", - "multimatch": "^4.0.0", "mutation-observer": "^1.0.3", - "ncp": "^2.0.0", "nock": "12.0.3", "node-sass": "7.0.1", "null-loader": "^3.0.0", @@ -1133,7 +1128,6 @@ "q": "^1.5.1", "raw-loader": "^3.1.0", "react-test-renderer": "^16.14.0", - "read-pkg": "^5.2.0", "regenerate": "^1.4.0", "resolve": "^1.22.0", "rxjs-marbles": "^5.0.6", @@ -1144,7 +1138,6 @@ "sort-package-json": "^1.53.1", "source-map": "^0.7.3", "string-replace-loader": "^2.2.0", - "strong-log-transformer": "^2.1.0", "style-loader": "^1.1.3", "stylelint": "13.8.0", "stylelint-scss": "^3.18.0", @@ -1161,7 +1154,6 @@ "ts-morph": "^13.0.2", "tsd": "^0.20.0", "typescript": "4.6.3", - "unlazy-loader": "^0.1.3", "url-loader": "^2.2.0", "val-loader": "^1.1.1", "vinyl-fs": "^3.0.3", @@ -1172,7 +1164,6 @@ "webpack-dev-server": "^3.11.0", "webpack-merge": "^4.2.2", "webpack-sources": "^1.4.1", - "write-pkg": "^4.0.0", "xml-crypto": "^2.1.3", "xmlbuilder": "13.0.2", "yargs": "^15.4.1" diff --git a/packages/BUILD.bazel b/packages/BUILD.bazel index fb1f7a6bdb146..8941724c39751 100644 --- a/packages/BUILD.bazel +++ b/packages/BUILD.bazel @@ -170,6 +170,7 @@ filegroup( "//packages/kbn-shared-ux-services:build", "//packages/kbn-shared-ux-storybook:build", "//packages/kbn-shared-ux-utility:build", + "//packages/kbn-some-dev-log:build", "//packages/kbn-sort-package-json:build", "//packages/kbn-spec-to-console:build", "//packages/kbn-std:build", @@ -194,6 +195,7 @@ filegroup( "//packages/kbn-utility-types-jest:build", "//packages/kbn-utility-types:build", "//packages/kbn-utils:build", + "//packages/kbn-yarn-lock-validator:build", "//packages/shared-ux/avatar/solution:build", "//packages/shared-ux/button_toolbar:build", "//packages/shared-ux/button/exit_full_screen:build", @@ -367,6 +369,7 @@ filegroup( "//packages/kbn-shared-ux-services:build_types", "//packages/kbn-shared-ux-storybook:build_types", "//packages/kbn-shared-ux-utility:build_types", + "//packages/kbn-some-dev-log:build_types", "//packages/kbn-sort-package-json:build_types", "//packages/kbn-std:build_types", "//packages/kbn-stdio-dev-helpers:build_types", @@ -385,6 +388,7 @@ filegroup( "//packages/kbn-utility-types-jest:build_types", "//packages/kbn-utility-types:build_types", "//packages/kbn-utils:build_types", + "//packages/kbn-yarn-lock-validator:build_types", "//packages/shared-ux/avatar/solution:build_types", "//packages/shared-ux/button_toolbar:build_types", "//packages/shared-ux/button/exit_full_screen:build_types", diff --git a/packages/README.md b/packages/README.md index 57c865aedf649..2dbbc7220221e 100644 --- a/packages/README.md +++ b/packages/README.md @@ -30,9 +30,6 @@ instead be: "@kbn/i18n": "link:../../kibana/packages/kbn-i18n" ``` -How all of this works is described in more detail in the -[`@kbn/pm` docs](./kbn-pm#how-it-works). - ## Creating a new package Create a new sub-folder. The name of the folder should mirror the `name` in the diff --git a/packages/kbn-bazel-packages/src/bazel_package.ts b/packages/kbn-bazel-packages/src/bazel_package.ts index 930eed591a853..91e411770175b 100644 --- a/packages/kbn-bazel-packages/src/bazel_package.ts +++ b/packages/kbn-bazel-packages/src/bazel_package.ts @@ -30,12 +30,10 @@ export class BazelPackage { const pkg = readPackageJson(Path.resolve(dir, 'package.json')); let buildBazelContent; - if (pkg.name !== '@kbn/pm') { - try { - buildBazelContent = await Fsp.readFile(Path.resolve(dir, 'BUILD.bazel'), 'utf8'); - } catch (error) { - throw new Error(`unable to read BUILD.bazel file in [${dir}]: ${error.message}`); - } + try { + buildBazelContent = await Fsp.readFile(Path.resolve(dir, 'BUILD.bazel'), 'utf8'); + } catch (error) { + throw new Error(`unable to read BUILD.bazel file in [${dir}]: ${error.message}`); } return new BazelPackage(normalizePath(Path.relative(REPO_ROOT, dir)), pkg, buildBazelContent); diff --git a/packages/kbn-bazel-packages/src/parse_package_json.ts b/packages/kbn-bazel-packages/src/parse_package_json.ts index c3ad446b66823..b060656c0c512 100644 --- a/packages/kbn-bazel-packages/src/parse_package_json.ts +++ b/packages/kbn-bazel-packages/src/parse_package_json.ts @@ -24,6 +24,10 @@ export interface ParsedPackageJson { /** Is this package only intended for dev? */ devOnly?: boolean; }; + /** Scripts defined in the package.json file */ + scripts?: { + [key: string]: string | undefined; + }; /** All other fields in the package.json are typed as unknown as we don't care what they are */ [key: string]: unknown; } diff --git a/packages/kbn-bazel-runner/BUILD.bazel b/packages/kbn-bazel-runner/BUILD.bazel index 1f7c95fc9d2b4..2620e6b1ef783 100644 --- a/packages/kbn-bazel-runner/BUILD.bazel +++ b/packages/kbn-bazel-runner/BUILD.bazel @@ -7,6 +7,7 @@ PKG_REQUIRE_NAME = "@kbn/bazel-runner" SOURCE_FILES = glob( [ + "src/**/*.js", "src/**/*.ts", ], exclude = [ @@ -81,6 +82,7 @@ ts_project( args = ['--pretty'], srcs = SRCS, deps = TYPES_DEPS, + allow_js = True, declaration = True, declaration_map = True, emit_declaration_only = True, diff --git a/packages/kbn-bazel-runner/README.mdx b/packages/kbn-bazel-runner/README.mdx index 23459e6a5ba70..2e7e288bb198a 100644 --- a/packages/kbn-bazel-runner/README.mdx +++ b/packages/kbn-bazel-runner/README.mdx @@ -9,29 +9,38 @@ tags: ['kibana', 'dev', 'contributor', 'operations', 'bazel', 'runner'] This is a package with helpers for invoking bazel and iBazel commands, used everywhere we programmatically run bazel. -## async runBazel(options: BazelRunOptions) +## API + +### async runBazel(args: string[], options: BazelRunOptions) It runs bazel on the background with the given options -## async runIBazel(options: BazelRunOptions) +### async runIBazel(args: string[], options: BazelRunOptions) It runs a IBazel on the background with the given options -### BazelRunOptions +#### BazelRunOptions ``` { // a logger to print the command output - log: ToolingLog; - // the arguments to run the bazel or ibazel with - bazelArgs: string[]; + log: SomeDevLog; // run bazel with the no connection compatible config or not offline?: boolean; - // additional options to pass into execa process - execaOpts?: execa.Options; + // environment variables to set in process running Bazel + env?: Record; + // directory to run bazel in + cwd?: string; + // text to include at the beginning on each line of log output produced by bazel + logPrefix?: string; + // handler to implement custom error handling + onErrorExit?: (code: number) => void; } ``` -### execa.Options -Info around available execa options can be found [here](https://github.com/sindresorhus/execa/blob/9a157b3bc247b19d55cc6fbec77800a5ac348d19/readme.md#options) \ No newline at end of file +## NOTE: + +This code is needed in order to properly bootstrap the repository. As such, it can't have any NPM dependencies or require being built. This code is loaded directly into the node.js process that boostraps the repository from source while also being built into a package and exposed to the rest of the package system. Please consider this when making any changes to the source. + +The code is still type-checked as JS with JSDoc comments, and a single .ts file which provides interfaces to the JS validation and are publically available to package consumers. \ No newline at end of file diff --git a/packages/kbn-bazel-runner/src/bazel_runner.js b/packages/kbn-bazel-runner/src/bazel_runner.js new file mode 100644 index 0000000000000..257c7e695b312 --- /dev/null +++ b/packages/kbn-bazel-runner/src/bazel_runner.js @@ -0,0 +1,128 @@ +/* + * 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. + */ + +const ChildProcess = require('child_process'); +const Readline = require('readline'); + +/** + * Print each line of output to the console + * @param {import('stream').Readable} stream + * @param {string | undefined} prefix + */ +async function printLines(stream, prefix) { + const int = Readline.createInterface({ + input: stream, + crlfDelay: Infinity, + }); + + for await (const line of int) { + console.log(prefix ? `${prefix} ${line}` : line); + } +} + +/** + * Buffer each line of output to an array so that it can be printed if necessary + * @param {import('stream').Readable} stream + * @param {string[]} buffer + */ +async function bufferLines(stream, buffer) { + const int = Readline.createInterface({ + input: stream, + crlfDelay: Infinity, + }); + + for await (const line of int) { + buffer.push(line); + } +} + +/** + * @param {import('events').EventEmitter} emitter + * @param {string} event + * @returns {Promise} + */ +function once(emitter, event) { + return new Promise((resolve) => { + emitter.once(event, resolve); + }); +} + +/** + * @param {'bazel' | 'ibazel'} runner + * @param {string[]} args + * @param {import('./types').BazelRunOptions | undefined} options + */ +async function runBazelRunner(runner, args, options = undefined) { + const proc = ChildProcess.spawn(runner, args, { + env: { + ...process.env, + ...options?.env, + }, + cwd: options?.cwd, + stdio: ['ignore', 'pipe', 'pipe'], + }); + + /** @type {string[]} */ + const buffer = []; + + await Promise.all([ + options?.quiet + ? Promise.all([bufferLines(proc.stdout, buffer), bufferLines(proc.stderr, buffer)]) + : Promise.all([ + printLines(proc.stdout, options?.logPrefix), + printLines(proc.stderr, options?.logPrefix), + ]), + + // Wait for process to exit, or error + Promise.race([ + once(proc, 'exit').then((code) => { + if (typeof code !== 'number' || code === 0) { + return; + } + + if (options?.onErrorExit) { + options.onErrorExit(code, buffer.join('\n')); + } else { + throw new Error( + `The bazel command that was running exitted with code [${code}]${ + buffer.length ? `\n output:\n${buffer.map((l) => ` ${l}`).join('\n')}` : '' + }` + ); + } + }), + + once(proc, 'error').then((error) => { + throw error; + }), + ]), + ]); +} + +/** + * @param {string[]} args + * @param {import('./types').BazelRunOptions | undefined} options + */ +async function runBazel(args, options = undefined) { + return await runBazelRunner('bazel', args, options); +} + +/** + * @param {string[]} args + * @param {import('./types').BazelRunOptions | undefined} options + */ +async function runIBazel(args, options = undefined) { + return await runBazelRunner('ibazel', args, { + ...options, + env: { + IBAZEL_USE_LEGACY_WATCHER: '0', + ...options?.env, + }, + }); +} + +module.exports = { runBazel, runIBazel }; diff --git a/packages/kbn-bazel-runner/src/bazel_runner.ts b/packages/kbn-bazel-runner/src/bazel_runner.ts deleted file mode 100644 index a07ec35285872..0000000000000 --- a/packages/kbn-bazel-runner/src/bazel_runner.ts +++ /dev/null @@ -1,76 +0,0 @@ -/* - * 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 chalk from 'chalk'; -import execa from 'execa'; -import * as Rx from 'rxjs'; -import { tap } from 'rxjs/operators'; -import { ToolingLog } from '@kbn/tooling-log'; -import { observeLines } from '@kbn/stdio-dev-helpers'; - -type BazelCommandRunner = 'bazel' | 'ibazel'; - -interface BazelRunOptions { - log: ToolingLog; - bazelArgs: string[]; - offline?: boolean; - execaOpts?: execa.Options; -} - -async function runBazelCommandWithRunner(runner: BazelCommandRunner, options: BazelRunOptions) { - const bazelProc = execa( - runner, - options.offline ? [...options.bazelArgs, '--config=offline'] : options.bazelArgs, - { - ...options.execaOpts, - stdio: 'pipe', - preferLocal: true, - } - ); - - await Promise.all([ - // Bazel outputs machine readable output into stdout and human readable output goes to stderr. - // Therefore we need to get both. In order to get errors we need to parse the actual text line - Rx.lastValueFrom( - Rx.merge( - observeLines(bazelProc.stdout!).pipe( - tap((line) => options.log.info(`${chalk.cyan(`[${runner}]`)} ${line}`)) - ), - observeLines(bazelProc.stderr!).pipe( - tap((line) => options.log.info(`${chalk.cyan(`[${runner}]`)} ${line}`)) - ) - ).pipe(Rx.defaultIfEmpty(undefined)) - ), - - // Wait for process and logs to finish, unsubscribing in the end - bazelProc.catch(() => { - options.log.error( - 'HINT: If experiencing problems with node_modules try `yarn kbn bootstrap --force-install` or as last resort `yarn kbn reset && yarn kbn bootstrap`' - ); - - throw new Error(`The bazel command that was running failed to complete.`); - }), - ]); -} - -export async function runBazel(options: BazelRunOptions) { - await runBazelCommandWithRunner('bazel', options); -} - -export async function runIBazel(options: BazelRunOptions) { - await runBazelCommandWithRunner('ibazel', { - ...options, - execaOpts: { - ...options.execaOpts, - env: { - ...options.execaOpts?.env, - IBAZEL_USE_LEGACY_WATCHER: '0', - }, - }, - }); -} diff --git a/packages/kbn-pm/src/utils/bazel/index.ts b/packages/kbn-bazel-runner/src/index.js similarity index 77% rename from packages/kbn-pm/src/utils/bazel/index.ts rename to packages/kbn-bazel-runner/src/index.js index d1460d5598f55..cc7af490e8fd0 100644 --- a/packages/kbn-pm/src/utils/bazel/index.ts +++ b/packages/kbn-bazel-runner/src/index.js @@ -6,6 +6,6 @@ * Side Public License, v 1. */ -export * from './get_cache_folders'; -export * from './install_tools'; -export * from './yarn'; +const { runBazel, runIBazel } = require('./bazel_runner'); + +module.exports = { runBazel, runIBazel }; diff --git a/packages/kbn-bazel-runner/src/types.ts b/packages/kbn-bazel-runner/src/types.ts new file mode 100644 index 0000000000000..23d9ed3473fbe --- /dev/null +++ b/packages/kbn-bazel-runner/src/types.ts @@ -0,0 +1,34 @@ +/* + * 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. + */ + +/** + * Options that can be used to customize how Bazel is run + */ +export interface BazelRunOptions { + /** + * Current working directory to run bazel in + */ + cwd?: string; + /** + * Custom environment variables to define for the bazel process + */ + env?: Record; + /** + * Prevent logging bazel output unless there is something wrong + */ + quiet?: boolean; + /** + * Prefix to write before each line of output, does nothing if `quiet` is true. + */ + logPrefix?: string; + /** + * Error handler which can be used to throw custom error types when bazel failes. Output will + * be empty unless `quiet` is true + */ + onErrorExit?: (core: number, output: string) => void; +} diff --git a/packages/kbn-bazel-runner/tsconfig.json b/packages/kbn-bazel-runner/tsconfig.json index 789c6b3111115..9f78bc243ac66 100644 --- a/packages/kbn-bazel-runner/tsconfig.json +++ b/packages/kbn-bazel-runner/tsconfig.json @@ -4,6 +4,8 @@ "declaration": true, "declarationMap": true, "emitDeclarationOnly": true, + "allowJs": true, + "checkJs": true, "outDir": "target_types", "rootDir": "src", "stripInternal": false, diff --git a/packages/kbn-ci-stats-core/BUILD.bazel b/packages/kbn-ci-stats-core/BUILD.bazel index 0ffe582109949..c9320c4f3b20a 100644 --- a/packages/kbn-ci-stats-core/BUILD.bazel +++ b/packages/kbn-ci-stats-core/BUILD.bazel @@ -52,6 +52,7 @@ TYPES_DEPS = [ "@npm//@types/node", "@npm//@types/jest", "//packages/kbn-tooling-log:npm_module_types", + "//packages/kbn-some-dev-log:npm_module_types", ] jsts_transpiler( diff --git a/packages/kbn-ci-stats-core/src/ci_stats_config.ts b/packages/kbn-ci-stats-core/src/ci_stats_config.ts index c97d99c53bf6a..8bef950324d87 100644 --- a/packages/kbn-ci-stats-core/src/ci_stats_config.ts +++ b/packages/kbn-ci-stats-core/src/ci_stats_config.ts @@ -6,7 +6,7 @@ * Side Public License, v 1. */ -import type { ToolingLog } from '@kbn/tooling-log'; +import { SomeDevLog } from '@kbn/some-dev-log'; /** * Information about how CiStatsReporter should talk to the ci-stats service. Normally @@ -23,7 +23,7 @@ export interface Config { buildId: string; } -function validateConfig(log: ToolingLog, config: { [k in keyof Config]: unknown }) { +function validateConfig(log: SomeDevLog, config: { [k in keyof Config]: unknown }) { const validApiToken = typeof config.apiToken === 'string' && config.apiToken.length !== 0; if (!validApiToken) { log.warning('KIBANA_CI_STATS_CONFIG is missing a valid api token, stats will not be reported'); @@ -39,7 +39,7 @@ function validateConfig(log: ToolingLog, config: { [k in keyof Config]: unknown return config as Config; } -export function parseConfig(log: ToolingLog) { +export function parseConfig(log: SomeDevLog) { const configJson = process.env.KIBANA_CI_STATS_CONFIG; if (!configJson) { log.debug('KIBANA_CI_STATS_CONFIG environment variable not found, disabling CiStatsReporter'); diff --git a/packages/kbn-ci-stats-reporter/BUILD.bazel b/packages/kbn-ci-stats-reporter/BUILD.bazel index d3fd4780dc2ab..2e6e85c6a7c26 100644 --- a/packages/kbn-ci-stats-reporter/BUILD.bazel +++ b/packages/kbn-ci-stats-reporter/BUILD.bazel @@ -58,6 +58,7 @@ TYPES_DEPS = [ "@npm//@types/jest", "//packages/kbn-tooling-log:npm_module_types", "//packages/kbn-ci-stats-core:npm_module_types", + "//packages/kbn-some-dev-log:npm_module_types", ] jsts_transpiler( diff --git a/packages/kbn-ci-stats-reporter/src/ci_stats_reporter.ts b/packages/kbn-ci-stats-reporter/src/ci_stats_reporter.ts index 7a23f20143d94..ecc6221250bec 100644 --- a/packages/kbn-ci-stats-reporter/src/ci_stats_reporter.ts +++ b/packages/kbn-ci-stats-reporter/src/ci_stats_reporter.ts @@ -14,11 +14,13 @@ import crypto from 'crypto'; import execa from 'execa'; import Axios, { AxiosRequestConfig } from 'axios'; +import { REPO_ROOT, kibanaPackageJson } from '@kbn/utils'; +import { parseConfig, Config, CiStatsMetadata } from '@kbn/ci-stats-core'; +import type { SomeDevLog } from '@kbn/some-dev-log'; + // @ts-expect-error not "public", but necessary to prevent Jest shimming from breaking things import httpAdapter from 'axios/lib/adapters/http'; -import { ToolingLog } from '@kbn/tooling-log'; -import { parseConfig, Config, CiStatsMetadata } from '@kbn/ci-stats-core'; import type { CiStatsTestGroupInfo, CiStatsTestRun } from './ci_stats_test_group_types'; const BASE_URL = 'https://ci-stats.kibana.dev'; @@ -119,11 +121,11 @@ export class CiStatsReporter { /** * Create a CiStatsReporter by inspecting the ENV for the necessary config */ - static fromEnv(log: ToolingLog) { + static fromEnv(log: SomeDevLog) { return new CiStatsReporter(parseConfig(log), log); } - constructor(private readonly config: Config | undefined, private readonly log: ToolingLog) {} + constructor(private readonly config: Config | undefined, private readonly log: SomeDevLog) {} /** * Determine if CI_STATS is explicitly disabled by the environment. To determine @@ -327,28 +329,16 @@ export class CiStatsReporter { } /** - * In order to allow this code to run before @kbn/utils is built, @kbn/pm will pass - * in the upstreamBranch when calling the timings() method. Outside of @kbn/pm - * we rely on @kbn/utils to find the package.json file. + * In order to allow this code to run before @kbn/utils is built */ private getUpstreamBranch() { - // specify the module id in a way that will keep webpack from bundling extra code into @kbn/pm - const hideFromWebpack = ['@', 'kbn/utils']; - // eslint-disable-next-line @typescript-eslint/no-var-requires - const { kibanaPackageJson } = require(hideFromWebpack.join('')); return kibanaPackageJson.branch; } /** - * In order to allow this code to run before @kbn/utils is built, @kbn/pm will pass - * in the kibanaUuid when calling the timings() method. Outside of @kbn/pm - * we rely on @kbn/utils to find the repo root. + * In order to allow this code to run before @kbn/utils is built */ private getKibanaUuid() { - // specify the module id in a way that will keep webpack from bundling extra code into @kbn/pm - const hideFromWebpack = ['@', 'kbn/utils']; - // eslint-disable-next-line @typescript-eslint/no-var-requires - const { REPO_ROOT } = require(hideFromWebpack.join('')); try { return Fs.readFileSync(Path.resolve(REPO_ROOT, 'data/uuid'), 'utf-8').trim(); } catch (error) { diff --git a/packages/kbn-dev-cli-runner/README.md b/packages/kbn-dev-cli-runner/README.mdx similarity index 93% rename from packages/kbn-dev-cli-runner/README.md rename to packages/kbn-dev-cli-runner/README.mdx index 0ef87f0e8e078..cb4582cc9e735 100644 --- a/packages/kbn-dev-cli-runner/README.md +++ b/packages/kbn-dev-cli-runner/README.mdx @@ -1,8 +1,17 @@ -# @kbn/dev-cli-runner +--- +id: kibDevDocsOpsDevCliRunner +slug: /kibana-dev-docs/ops/kbn-dev-cli-runner +title: "@kbn/dev-cli-runner" +description: 'Helper functions for writing little scripts for random build/ci/dev tasks' +date: 2022-07-14 +tags: ['kibana', 'dev', 'contributor', 'operations', 'packages', 'scripts', 'cli'] +--- + +## @kbn/dev-cli-runner Helper functions for writing little scripts for random build/ci/dev tasks. -## Usage +### Usage Define the function that should validate the CLI arguments and call your task fn: @@ -63,7 +72,7 @@ $ node scripts/my_task # ``` -## API +### API - ***`run(fn: async ({ flags: Flags, log: ToolingLog, addCleanupTask }) => Promise, options: Options)`*** diff --git a/packages/kbn-eslint-config/javascript.js b/packages/kbn-eslint-config/javascript.js index 3e59731caa314..d048d9a93bdda 100644 --- a/packages/kbn-eslint-config/javascript.js +++ b/packages/kbn-eslint-config/javascript.js @@ -7,7 +7,7 @@ module.exports = { * Main JS configuration */ { - files: ['**/*.js'], + files: ['**/*.js', '**/*.mjs'], parser: require.resolve('@babel/eslint-parser'), plugins: [ diff --git a/packages/kbn-plugin-discovery/BUILD.bazel b/packages/kbn-plugin-discovery/BUILD.bazel index b2e5ecde9c426..a051005a61ef2 100644 --- a/packages/kbn-plugin-discovery/BUILD.bazel +++ b/packages/kbn-plugin-discovery/BUILD.bazel @@ -7,6 +7,7 @@ PKG_REQUIRE_NAME = "@kbn/plugin-discovery" SOURCE_FILES = glob( [ + "src/**/*.js", "src/**/*.ts", ], exclude = [ @@ -36,10 +37,6 @@ NPM_MODULE_EXTRA_FILES = [ # "@npm//name-of-package" # eg. "@npm//lodash" RUNTIME_DEPS = [ - "@npm//globby", - "@npm//load-json-file", - "@npm//normalize-path", - "@npm//tslib", ] # In this array place dependencies necessary to build the types, which will include the @@ -54,11 +51,6 @@ RUNTIME_DEPS = [ TYPES_DEPS = [ "@npm//@types/jest", "@npm//@types/node", - "@npm//@types/normalize-path", - "@npm//globby", - "@npm//load-json-file", - "@npm//normalize-path", - "@npm//tslib", ] jsts_transpiler( @@ -83,6 +75,7 @@ ts_project( deps = TYPES_DEPS, declaration = True, declaration_map = True, + allow_js = True, emit_declaration_only = True, out_dir = "target_types", root_dir = "src", diff --git a/packages/kbn-plugin-discovery/README.mdx b/packages/kbn-plugin-discovery/README.mdx index 973db3fb2a1e1..97689cd9458d4 100644 --- a/packages/kbn-plugin-discovery/README.mdx +++ b/packages/kbn-plugin-discovery/README.mdx @@ -11,14 +11,22 @@ At the moment plugins can live in a couple of different places and in the future to live anywhere in the repository. This is a package that holds custom logic useful to find and parse those. -## parseKibanaPlatformPlugin +## API + +### parseKibanaPlatformPlugin It returns a platform plugin for a given manifest path -## getPluginSearchPaths +### getPluginSearchPaths It returns the paths where plugins will be searched for -## simpleKibanaPlatformPluginDiscovery +### simpleKibanaPlatformPluginDiscovery It finds and returns the new platform plugins + +## NOTE: + +This code is needed in order to properly bootstrap the repository. As such, it can't have any NPM dependencies or require being built. This code is loaded directly into the node.js process that boostraps the repository from source while also being built into a package and exposed to the rest of the package system. Please consider this when making any changes to the source. + +The code is still type-checked as JS with JSDoc comments, and a single .ts file which provides interfaces to the JS validation and are publically available to package consumers. \ No newline at end of file diff --git a/packages/kbn-plugin-discovery/src/find_kibana_json_files.js b/packages/kbn-plugin-discovery/src/find_kibana_json_files.js new file mode 100644 index 0000000000000..f1687859627a8 --- /dev/null +++ b/packages/kbn-plugin-discovery/src/find_kibana_json_files.js @@ -0,0 +1,65 @@ +/* + * 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. + */ + +const Path = require('path'); +const Fs = require('fs'); + +/** + * @param {string} path + */ +function safeReadDir(path) { + try { + return Fs.readdirSync(path, { + withFileTypes: true, + }); + } catch (error) { + if (error.code === 'ENOENT' || error.code === 'ENOTDIR') { + return []; + } + + throw error; + } +} + +/** + * Given an iterable of paths with optoinal "*" segments, expand the path to the + * list of actual absolute paths, removing all "*" segments, and then return the + * set of paths which end up pointing to actual files. + * + * @param {string} dir + * @param {number} depth + * @returns {string[]} + */ +function findKibanaJsonFiles(dir, depth) { + // if depth = 0 then we just need to determine if there is a kibana.json file in this directory + // and return either that path or an empty array + if (depth === 0) { + const path = Path.resolve(dir, 'kibana.json'); + return Fs.existsSync(path) ? [path] : []; + } + + // if depth > 0 read the files in this directory, if we find a kibana.json file then we can stop + // otherwise we will iterate through the child directories and try to find kibana.json files there. + const files = safeReadDir(dir); + + /** @type {string[]} */ + const childDirs = []; + for (const ent of files) { + if (ent.isFile()) { + if (ent.name === 'kibana.json') { + return [Path.resolve(dir, ent.name)]; + } + } else if (ent.isDirectory()) { + childDirs.push(Path.resolve(dir, ent.name)); + } + } + + return childDirs.flatMap((dir) => findKibanaJsonFiles(dir, depth - 1)); +} + +module.exports = { findKibanaJsonFiles }; diff --git a/packages/kbn-plugin-discovery/src/index.js b/packages/kbn-plugin-discovery/src/index.js new file mode 100644 index 0000000000000..4d2f0bbffaa50 --- /dev/null +++ b/packages/kbn-plugin-discovery/src/index.js @@ -0,0 +1,19 @@ +/* + * 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. + */ + +const { parseKibanaPlatformPlugin } = require('./parse_kibana_platform_plugin'); +const { getPluginSearchPaths } = require('./plugin_search_paths'); +const { + simpleKibanaPlatformPluginDiscovery, +} = require('./simple_kibana_platform_plugin_discovery'); + +module.exports = { + parseKibanaPlatformPlugin, + getPluginSearchPaths, + simpleKibanaPlatformPluginDiscovery, +}; diff --git a/packages/kbn-plugin-discovery/src/load_json_file.js b/packages/kbn-plugin-discovery/src/load_json_file.js new file mode 100644 index 0000000000000..2e35a503ccf4c --- /dev/null +++ b/packages/kbn-plugin-discovery/src/load_json_file.js @@ -0,0 +1,30 @@ +/* + * 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. + */ + +const Fs = require('fs'); +const Path = require('path'); + +/** + * @param {string} path + * @returns {any} + */ +function loadJsonFile(path) { + try { + return JSON.parse(Fs.readFileSync(path, 'utf8')); + } catch (error) { + if (error.code === 'ENOENT') { + throw new Error(`Missing file: ${path}`); + } + + throw new Error( + `Unable to read JSON at [${Path.relative(process.cwd(), path)}]: ${error.message}` + ); + } +} + +module.exports = { loadJsonFile }; diff --git a/packages/kbn-plugin-discovery/src/parse_kibana_platform_plugin.ts b/packages/kbn-plugin-discovery/src/parse_kibana_platform_plugin.js similarity index 65% rename from packages/kbn-plugin-discovery/src/parse_kibana_platform_plugin.ts rename to packages/kbn-plugin-discovery/src/parse_kibana_platform_plugin.js index e9fd2a285f09d..6137d5ad40187 100644 --- a/packages/kbn-plugin-discovery/src/parse_kibana_platform_plugin.ts +++ b/packages/kbn-plugin-discovery/src/parse_kibana_platform_plugin.js @@ -6,16 +6,16 @@ * Side Public License, v 1. */ -import Path from 'path'; -import loadJsonFile from 'load-json-file'; +const Path = require('path'); -export interface KibanaPlatformPlugin { - readonly directory: string; - readonly manifestPath: string; - readonly manifest: KibanaPlatformPluginManifest; -} +const { loadJsonFile } = require('./load_json_file'); -function isValidDepsDeclaration(input: unknown, type: string): string[] { +/** + * @param {unknown} input + * @param {string} type + * @returns {string[]} + */ +function isValidDepsDeclaration(input, type) { if (typeof input === 'undefined') return []; if (Array.isArray(input) && input.every((i) => typeof i === 'string')) { return input; @@ -23,35 +23,17 @@ function isValidDepsDeclaration(input: unknown, type: string): string[] { throw new TypeError(`The "${type}" in plugin manifest should be an array of strings.`); } -export interface KibanaPlatformPluginManifest { - id: string; - ui: boolean; - server: boolean; - kibanaVersion: string; - version: string; - owner: { - // Internally, this should be a team name. - name: string; - // All internally owned plugins should have a github team specified that can be pinged in issues, or used to look up - // members who can be asked questions regarding the plugin. - githubTeam?: string; - }; - // TODO: make required. - description?: string; - enabledOnAnonymousPages?: boolean; - serviceFolders: readonly string[]; - requiredPlugins: readonly string[]; - optionalPlugins: readonly string[]; - requiredBundles: readonly string[]; - extraPublicDirs: readonly string[]; -} - -export function parseKibanaPlatformPlugin(manifestPath: string): KibanaPlatformPlugin { +/** + * @param {string} manifestPath + * @returns {import('./types').KibanaPlatformPlugin} + */ +function parseKibanaPlatformPlugin(manifestPath) { if (!Path.isAbsolute(manifestPath)) { throw new TypeError('expected new platform manifest path to be absolute'); } - const manifest: Partial = loadJsonFile.sync(manifestPath); + /** @type {Partial} */ + const manifest = loadJsonFile(manifestPath); if (!manifest || typeof manifest !== 'object' || Array.isArray(manifest)) { throw new TypeError('expected new platform plugin manifest to be a JSON encoded object'); } @@ -92,3 +74,5 @@ export function parseKibanaPlatformPlugin(manifestPath: string): KibanaPlatformP }, }; } + +module.exports = { parseKibanaPlatformPlugin }; diff --git a/packages/kbn-plugin-discovery/src/plugin_search_paths.ts b/packages/kbn-plugin-discovery/src/plugin_search_paths.js similarity index 85% rename from packages/kbn-plugin-discovery/src/plugin_search_paths.ts rename to packages/kbn-plugin-discovery/src/plugin_search_paths.js index dce55698e88ee..6012f42a38ee1 100644 --- a/packages/kbn-plugin-discovery/src/plugin_search_paths.ts +++ b/packages/kbn-plugin-discovery/src/plugin_search_paths.js @@ -6,16 +6,13 @@ * Side Public License, v 1. */ -import { resolve } from 'path'; +const { resolve } = require('path'); -export interface SearchOptions { - rootDir: string; - oss: boolean; - examples: boolean; - testPlugins?: boolean; -} - -export function getPluginSearchPaths({ rootDir, oss, examples, testPlugins }: SearchOptions) { +/** + * @param {{ rootDir: string; oss: boolean; examples: boolean; testPlugins?: boolean; }} options + * @returns {string[]} + */ +function getPluginSearchPaths({ rootDir, oss, examples, testPlugins }) { return [ resolve(rootDir, 'src', 'plugins'), ...(oss ? [] : [resolve(rootDir, 'x-pack', 'plugins')]), @@ -45,3 +42,5 @@ export function getPluginSearchPaths({ rootDir, oss, examples, testPlugins }: Se : []), ]; } + +module.exports = { getPluginSearchPaths }; diff --git a/packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.js b/packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.js new file mode 100644 index 0000000000000..8ea7bb6d563ab --- /dev/null +++ b/packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.js @@ -0,0 +1,29 @@ +/* + * 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. + */ + +const { parseKibanaPlatformPlugin } = require('./parse_kibana_platform_plugin'); +const { findKibanaJsonFiles } = require('./find_kibana_json_files'); + +/** + * Helper to find the new platform plugins. + * @param {string[]} scanDirs + * @param {string[]} pluginPaths + * @returns {Array} + */ +function simpleKibanaPlatformPluginDiscovery(scanDirs, pluginPaths) { + return Array.from( + new Set([ + // find kibana.json files up to 5 levels within each scan dir + ...scanDirs.flatMap((dir) => findKibanaJsonFiles(dir, 5)), + // find kibana.json files at the root of each plugin path + ...pluginPaths.flatMap((path) => findKibanaJsonFiles(path, 0)), + ]) + ).map(parseKibanaPlatformPlugin); +} + +module.exports = { simpleKibanaPlatformPluginDiscovery }; diff --git a/packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.ts b/packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.ts deleted file mode 100644 index ebf476a668851..0000000000000 --- a/packages/kbn-plugin-discovery/src/simple_kibana_platform_plugin_discovery.ts +++ /dev/null @@ -1,49 +0,0 @@ -/* - * 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 Path from 'path'; - -import globby from 'globby'; -import normalize from 'normalize-path'; - -import { parseKibanaPlatformPlugin, KibanaPlatformPlugin } from './parse_kibana_platform_plugin'; - -/** - * Helper to find the new platform plugins. - */ -export function simpleKibanaPlatformPluginDiscovery( - scanDirs: string[], - pluginPaths: string[] -): KibanaPlatformPlugin[] { - const patterns = Array.from( - new Set([ - // find kibana.json files up to 5 levels within the scan dir - ...scanDirs.reduce( - (acc: string[], dir) => [ - ...acc, - Path.resolve(dir, '*/kibana.json'), - Path.resolve(dir, '*/*/kibana.json'), - Path.resolve(dir, '*/*/*/kibana.json'), - Path.resolve(dir, '*/*/*/*/kibana.json'), - Path.resolve(dir, '*/*/*/*/*/kibana.json'), - ], - [] - ), - ...pluginPaths.map((path) => Path.resolve(path, `kibana.json`)), - ]) - ).map((path) => normalize(path)); - - const manifestPaths = globby.sync(patterns, { absolute: true }).map((path) => - // absolute paths returned from globby are using normalize or - // something so the path separators are `/` even on windows, - // Path.resolve solves this - Path.resolve(path) - ); - - return manifestPaths.map(parseKibanaPlatformPlugin); -} diff --git a/packages/kbn-plugin-discovery/src/types.ts b/packages/kbn-plugin-discovery/src/types.ts new file mode 100644 index 0000000000000..ebf3f68074c7b --- /dev/null +++ b/packages/kbn-plugin-discovery/src/types.ts @@ -0,0 +1,44 @@ +/* + * 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. + */ + +export type JsonValue = + | { [key: string]: JsonValue } + | JsonValue[] + | string + | number + | boolean + | null; + +export interface KibanaPlatformPlugin { + readonly directory: string; + readonly manifestPath: string; + readonly manifest: KibanaPlatformPluginManifest; +} + +export interface KibanaPlatformPluginManifest { + id: string; + ui: boolean; + server: boolean; + kibanaVersion: string; + version: string; + owner: { + // Internally, this should be a team name. + name: string; + // All internally owned plugins should have a github team specified that can be pinged in issues, or used to look up + // members who can be asked questions regarding the plugin. + githubTeam?: string; + }; + // TODO: make required. + description?: string; + enabledOnAnonymousPages?: boolean; + serviceFolders: readonly string[]; + requiredPlugins: readonly string[]; + optionalPlugins: readonly string[]; + requiredBundles: readonly string[]; + extraPublicDirs: readonly string[]; +} diff --git a/packages/kbn-plugin-discovery/tsconfig.json b/packages/kbn-plugin-discovery/tsconfig.json index 789c6b3111115..88aeef31ff2da 100644 --- a/packages/kbn-plugin-discovery/tsconfig.json +++ b/packages/kbn-plugin-discovery/tsconfig.json @@ -3,7 +3,8 @@ "compilerOptions": { "declaration": true, "declarationMap": true, - "emitDeclarationOnly": true, + "allowJs": true, + "checkJs": true, "outDir": "target_types", "rootDir": "src", "stripInternal": false, @@ -13,6 +14,6 @@ ] }, "include": [ - "src/**/*" + "src/**/*", ] } diff --git a/packages/kbn-pm/.babelrc b/packages/kbn-pm/.babelrc deleted file mode 100644 index 9ea6ecafe7287..0000000000000 --- a/packages/kbn-pm/.babelrc +++ /dev/null @@ -1,15 +0,0 @@ -{ - "presets": [ - "@babel/typescript", - ["@babel/preset-env", { - "targets": { - "node": "current" - } - }] - ], - "plugins": [ - "@babel/proposal-class-properties", - "@babel/proposal-object-rest-spread", - "@babel/proposal-optional-chaining" - ] -} diff --git a/packages/kbn-pm/README.md b/packages/kbn-pm/README.md deleted file mode 100644 index 33d1fe6590f4b..0000000000000 --- a/packages/kbn-pm/README.md +++ /dev/null @@ -1,266 +0,0 @@ -# `@kbn/pm` — The Kibana project management tool - -`@kbn/pm` is a project management tool inspired by Lerna, which enables sharing -code between Kibana and Kibana plugins. - -To run `@kbn/pm`, go to Kibana root and run `yarn kbn`. - -## Why `@kbn/pm`? - -Long-term we want to get rid of Webpack from production (basically, it's causing -a lot of problems, using a lot of memory and adding a lot of complexity). -Ideally we want each plugin to build its own separate production bundles for -both server and UI. To get there all Kibana plugins (including x-pack) need to -be able to build their production bundles separately from Kibana, which means -they need to be able to depend on code from Kibana without `import`-ing random -files directly from the Kibana source code. - -From a plugin perspective there are two different types of Kibana dependencies: -runtime and static dependencies. Runtime dependencies are things that are -instantiated at runtime and that are injected into the plugin, for example -config and elasticsearch clients. Static dependencies are those dependencies -that we want to `import`. `kbn-eslint-config` is one example of this, and -it's actually needed because eslint requires it to be a separate package. But we -also have dependencies like `datemath`, `flot`, `eui` and others that we -control, but where we want to `import` them in plugins instead of injecting them -(because injecting them would be painful to work with). (Btw, these examples -aren't necessarily a part of the Kibana repo today, they are just meant as -examples of code that we might at some point want to include in the repo while -having them be `import`able in Kibana plugins like any other npm package) - -Another reason we need static dependencies is that we're starting to introduce -TypeScript into Kibana, and to work nicely with TypeScript across plugins we -need to be able to statically import dependencies. We have for example built an -observable library for Kibana in TypeScript and we need to expose both the -functionality and the TypeScript types to plugins (so other plugins built with -TypeScript can depend on the types for the lib). - -However, even though we have multiple packages we don't necessarily want to -`npm publish` them. The ideal solution for us is being able to work on code -locally in the Kibana repo and have a nice workflow that doesn't require -publishing, but where we still get the value of having "packages" that are -available to plugins, without these plugins having to import files directly from -the Kibana folder. - -Basically, we just want to be able to share "static code" (aka being able to -`import`) between Kibana and Kibana plugins. To get there we need tooling. - -`@kbn/pm` is a tool that helps us manage these static dependencies, and it -enables us to share these packages between Kibana and Kibana plugins. It also -enables these packages to have their own dependencies and their own build -scripts, while still having a nice developer experience. - -## How it works - -### Internal usage - -For packages that are referenced within the Kibana repo itself (for example, -using the `@kbn/i18n` package from an `x-pack` plugin), we are leveraging -Yarn's workspaces feature. This allows yarn to optimize node_modules within -the entire repo to avoid duplicate modules by hoisting common packages as high -in the dependency tree as possible. - -To reference a package from within the Kibana repo, simply use the current -version number from that package's package.json file. Then, running `yarn kbn -bootstrap` will symlink that package into your dependency tree. That means -you can make changes to `@kbn/i18n` and immediately have them available -in Kibana itself. No `npm publish` needed anymore — Kibana will always rely -directly on the code that's in the local packages. - -### External Plugins - -For external plugins, referencing packages in Kibana relies on -`link:` style dependencies in Yarn. With `link:` dependencies you specify the -relative location to a package instead of a version when adding it to -`package.json`. For example: - -``` -"@kbn/i18n": "link:packages/kbn-i18n" -``` - -Now when you run `yarn` it will set up a symlink to this folder instead of -downloading code from the npm registry. This allows external plugins to always -use the versions of the package that is bundled with the Kibana version they -are running inside of. - -``` -"@kbn/i18n": "link:../../kibana/packages/kbn-date-math" -``` - -This works because we moved to a strict location of Kibana plugins, -`./plugins/{pluginName}` inside of Kibana, or `../kibana-extra/{pluginName}` -relative to Kibana. This is one of the reasons we wanted to move towards a setup -that looks like this: - -``` -elastic -└── kibana - └── plugins - ├── kibana-canvas - └── x-pack-kibana -``` - -Relying on `link:` style dependencies means we no longer need to `npm publish` -our Kibana specific packages. It also means that plugin authors no longer need -to worry about the versions of the Kibana packages, as they will always use the -packages from their local Kibana. - -## The `kbn` use-cases - -### Bootstrapping - -Now, instead of installing all the dependencies with just running `yarn` you use -the `@kbn/pm` tool, which can install dependencies (and set up symlinks) in -all the packages using one command (aka "bootstrap" the setup). - -To bootstrap Kibana: - -``` -yarn kbn bootstrap -``` - -By default, `@kbn/pm` will bootstrap all packages within Kibana, plus all -Kibana plugins located in `./plugins` or `../kibana-extra`. There are several -options for skipping parts of this, e.g. to skip bootstrapping of Kibana -plugins: - -``` -yarn kbn bootstrap --skip-kibana-plugins -``` - -Or just skip few selected packages: - -``` -yarn kbn bootstrap --exclude @kbn/pm --exclude @kbn/i18n -``` - -For more details, run: - -``` -yarn kbn -``` - -Bootstrapping also calls the `kbn:bootstrap` script for every included project. -This is intended for packages that need to be built/transpiled to be usable. - -### Running scripts - -Some times you want to run the same script across multiple packages and plugins, -e.g. `build` or `test`. Instead of jumping into each package and running -`yarn build` you can run: - -``` -yarn kbn run build --skip-missing -``` - -And if needed, you can skip packages in the same way as for bootstrapping, e.g. -with `--exclude` and `--skip-kibana-plugins`: - -``` -yarn kbn run build --exclude kibana --skip-missing -``` - -### Watching - -During development you can also use `kbn` to watch for changes. For this to work -package should define `kbn:watch` script in the `package.json`: - -``` -yarn kbn watch -``` - -By default `kbn watch` will sort all packages within Kibana into batches based on -their mutual dependencies and run watch script for all packages in the correct order. - -As with any other `kbn` command, you can use `--include` and `--exclude` filters to watch -only for a selected packages: - -``` -yarn kbn watch --include @kbn/pm --include kibana -``` - -## Building packages for production - -The production build process relies on both the Grunt setup at the root of the -Kibana project and code in `@kbn/pm`. The full process is described in -`tasks/build/packages.js`. - -## Development - -This package is run from Kibana root, using `yarn kbn`. This will run the -"pre-built" (aka built and committed to git) version of this tool, which is -located in the `dist/` folder. This will also use the included version of Yarn -instead of using your local install of Yarn. - -If you need to build a new version of this package, run `yarn build` in this -folder. - -Even though this file is generated we commit it to Kibana, because it's used -_before_ dependencies are fetched (as this is the tool actually responsible for -fetching dependencies). - -## Technical decisions - -### Why our own tool? - -While exploring the approach to static dependencies we built PoCs using npm 5 -(which symlinks packages using [`file:` dependencies][npm5-file]), [Yarn -workspaces][yarn-workspaces], Yarn (using `link:` dependencies), and -[Lerna][lerna]. - -In the end we decided to build our own tool, based on Yarn, and `link:` -dependencies, and workspaces. This gave us the control we wanted, and it fits -nicely into our context (e.g. where publishing to npm isn't necessarily -something we want to do). - -### Some notes from this exploration - -#### `file:` dependencies in npm<5 and in yarn - -When you add a dependency like `"foo": "file:../../kibana/packages/foo"`, both -npm<5 and yarn copies the files into the `node_modules` folder. This means you -can't easily make changes to the plugin while developing. Therefore this is a -no-go. - -#### `file:` dependencies in npm5 - -In npm5 `file:` dependencies changed to symlink instead of copy the files. This -means you can have a nicer workflow while developing packages locally. However, -we hit several bugs when using this feature, and we often had to re-run -`npm install` in packages. This is likely because we used an early version of -the new `file:` dependencies in npm5. - -#### `link:` dependencies in Yarn - -This is the same feature as `file:` dependencies in npm5. However, we did not -hit any problems with them during our exploration. - -#### Yarn workspaces - -Enables specifying multiple "workspaces" (aka packages/projects) in -`package.json`. When running `yarn` from the root, Yarn will install all the -dependencies for these workspaces and hoist the dependencies to the root (to -"deduplicate" packages). However: - -> Workspaces must be children of the workspace root in term of folder hierarchy. -> You cannot and must not reference a workspace that is located outside of this -> filesystem hierarchy. - -So Yarn workspaces requires a shared root, which (at least currently) doesn't -fit Kibana, and it's therefore a no-go for now. - -#### Lerna - -Lerna is based on symlinking packages (similarly to the [`link`][npm-link] -feature which exists in both npm and Yarn, but it's not directly using that -feature). It's a tool built specifically for managing JavaScript projects with -multiple packages. However, it's primarily built (i.e. optimized) for monorepo -_libraries_, so it's focused on publishing packages and other use-cases that are -not necessarily optimized for our use-cases. It's also not ideal for the setup -we currently have, with one app that "owns everything" and the rest being -packages for that app. - -[npm-link]: https://docs.npmjs.com/cli/link -[npm5-file]: https://github.com/npm/npm/pull/15900 -[yarn-workspaces]: https://yarnpkg.com/lang/en/docs/workspaces/ -[lerna]: https://github.com/lerna/lerna diff --git a/packages/kbn-pm/dist/index.js b/packages/kbn-pm/dist/index.js deleted file mode 100644 index 647e8a8d4bbbe..0000000000000 --- a/packages/kbn-pm/dist/index.js +++ /dev/null @@ -1,63187 +0,0 @@ -module.exports = -/******/ (function(modules) { // webpackBootstrap -/******/ // The module cache -/******/ var installedModules = {}; -/******/ -/******/ // The require function -/******/ function __webpack_require__(moduleId) { -/******/ -/******/ // Check if module is in cache -/******/ if(installedModules[moduleId]) { -/******/ return installedModules[moduleId].exports; -/******/ } -/******/ // Create a new module (and put it into the cache) -/******/ var module = installedModules[moduleId] = { -/******/ i: moduleId, -/******/ l: false, -/******/ exports: {} -/******/ }; -/******/ -/******/ // Execute the module function -/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__); -/******/ -/******/ // Flag the module as loaded -/******/ module.l = true; -/******/ -/******/ // Return the exports of the module -/******/ return module.exports; -/******/ } -/******/ -/******/ -/******/ // expose the modules object (__webpack_modules__) -/******/ __webpack_require__.m = modules; -/******/ -/******/ // expose the module cache -/******/ __webpack_require__.c = installedModules; -/******/ -/******/ // define getter function for harmony exports -/******/ __webpack_require__.d = function(exports, name, getter) { -/******/ if(!__webpack_require__.o(exports, name)) { -/******/ Object.defineProperty(exports, name, { enumerable: true, get: getter }); -/******/ } -/******/ }; -/******/ -/******/ // define __esModule on exports -/******/ __webpack_require__.r = function(exports) { -/******/ if(typeof Symbol !== 'undefined' && Symbol.toStringTag) { -/******/ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' }); -/******/ } -/******/ Object.defineProperty(exports, '__esModule', { value: true }); -/******/ }; -/******/ -/******/ // create a fake namespace object -/******/ // mode & 1: value is a module id, require it -/******/ // mode & 2: merge all properties of value into the ns -/******/ // mode & 4: return value when already ns object -/******/ // mode & 8|1: behave like require -/******/ __webpack_require__.t = function(value, mode) { -/******/ if(mode & 1) value = __webpack_require__(value); -/******/ if(mode & 8) return value; -/******/ if((mode & 4) && typeof value === 'object' && value && value.__esModule) return value; -/******/ var ns = Object.create(null); -/******/ __webpack_require__.r(ns); -/******/ Object.defineProperty(ns, 'default', { enumerable: true, value: value }); -/******/ if(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key)); -/******/ return ns; -/******/ }; -/******/ -/******/ // getDefaultExport function for compatibility with non-harmony modules -/******/ __webpack_require__.n = function(module) { -/******/ var getter = module && module.__esModule ? -/******/ function getDefault() { return module['default']; } : -/******/ function getModuleExports() { return module; }; -/******/ __webpack_require__.d(getter, 'a', getter); -/******/ return getter; -/******/ }; -/******/ -/******/ // Object.prototype.hasOwnProperty.call -/******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); }; -/******/ -/******/ // __webpack_public_path__ -/******/ __webpack_require__.p = ""; -/******/ -/******/ -/******/ // Load entry module and return exports -/******/ return __webpack_require__(__webpack_require__.s = "./src/index.ts"); -/******/ }) -/************************************************************************/ -/******/ ({ - -/***/ "../../node_modules/@babel/code-frame/lib/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.codeFrameColumns = codeFrameColumns; -exports.default = _default; - -var _highlight = __webpack_require__("../../node_modules/@babel/highlight/lib/index.js"); - -let deprecationWarningShown = false; - -function getDefs(chalk) { - return { - gutter: chalk.grey, - marker: chalk.red.bold, - message: chalk.red.bold - }; -} - -const NEWLINE = /\r\n|[\n\r\u2028\u2029]/; - -function getMarkerLines(loc, source, opts) { - const startLoc = Object.assign({ - column: 0, - line: -1 - }, loc.start); - const endLoc = Object.assign({}, startLoc, loc.end); - const { - linesAbove = 2, - linesBelow = 3 - } = opts || {}; - const startLine = startLoc.line; - const startColumn = startLoc.column; - const endLine = endLoc.line; - const endColumn = endLoc.column; - let start = Math.max(startLine - (linesAbove + 1), 0); - let end = Math.min(source.length, endLine + linesBelow); - - if (startLine === -1) { - start = 0; - } - - if (endLine === -1) { - end = source.length; - } - - const lineDiff = endLine - startLine; - const markerLines = {}; - - if (lineDiff) { - for (let i = 0; i <= lineDiff; i++) { - const lineNumber = i + startLine; - - if (!startColumn) { - markerLines[lineNumber] = true; - } else if (i === 0) { - const sourceLength = source[lineNumber - 1].length; - markerLines[lineNumber] = [startColumn, sourceLength - startColumn + 1]; - } else if (i === lineDiff) { - markerLines[lineNumber] = [0, endColumn]; - } else { - const sourceLength = source[lineNumber - i].length; - markerLines[lineNumber] = [0, sourceLength]; - } - } - } else { - if (startColumn === endColumn) { - if (startColumn) { - markerLines[startLine] = [startColumn, 0]; - } else { - markerLines[startLine] = true; - } - } else { - markerLines[startLine] = [startColumn, endColumn - startColumn]; - } - } - - return { - start, - end, - markerLines - }; -} - -function codeFrameColumns(rawLines, loc, opts = {}) { - const highlighted = (opts.highlightCode || opts.forceColor) && (0, _highlight.shouldHighlight)(opts); - const chalk = (0, _highlight.getChalk)(opts); - const defs = getDefs(chalk); - - const maybeHighlight = (chalkFn, string) => { - return highlighted ? chalkFn(string) : string; - }; - - const lines = rawLines.split(NEWLINE); - const { - start, - end, - markerLines - } = getMarkerLines(loc, lines, opts); - const hasColumns = loc.start && typeof loc.start.column === "number"; - const numberMaxWidth = String(end).length; - const highlightedLines = highlighted ? (0, _highlight.default)(rawLines, opts) : rawLines; - let frame = highlightedLines.split(NEWLINE, end).slice(start, end).map((line, index) => { - const number = start + 1 + index; - const paddedNumber = ` ${number}`.slice(-numberMaxWidth); - const gutter = ` ${paddedNumber} |`; - const hasMarker = markerLines[number]; - const lastMarkerLine = !markerLines[number + 1]; - - if (hasMarker) { - let markerLine = ""; - - if (Array.isArray(hasMarker)) { - const markerSpacing = line.slice(0, Math.max(hasMarker[0] - 1, 0)).replace(/[^\t]/g, " "); - const numberOfMarkers = hasMarker[1] || 1; - markerLine = ["\n ", maybeHighlight(defs.gutter, gutter.replace(/\d/g, " ")), " ", markerSpacing, maybeHighlight(defs.marker, "^").repeat(numberOfMarkers)].join(""); - - if (lastMarkerLine && opts.message) { - markerLine += " " + maybeHighlight(defs.message, opts.message); - } - } - - return [maybeHighlight(defs.marker, ">"), maybeHighlight(defs.gutter, gutter), line.length > 0 ? ` ${line}` : "", markerLine].join(""); - } else { - return ` ${maybeHighlight(defs.gutter, gutter)}${line.length > 0 ? ` ${line}` : ""}`; - } - }).join("\n"); - - if (opts.message && !hasColumns) { - frame = `${" ".repeat(numberMaxWidth + 1)}${opts.message}\n${frame}`; - } - - if (highlighted) { - return chalk.reset(frame); - } else { - return frame; - } -} - -function _default(rawLines, lineNumber, colNumber, opts = {}) { - if (!deprecationWarningShown) { - deprecationWarningShown = true; - const message = "Passing lineNumber and colNumber is deprecated to @babel/code-frame. Please use `codeFrameColumns`."; - - if (process.emitWarning) { - process.emitWarning(message, "DeprecationWarning"); - } else { - const deprecationError = new Error(message); - deprecationError.name = "DeprecationWarning"; - console.warn(new Error(message)); - } - } - - colNumber = Math.max(colNumber, 0); - const location = { - start: { - column: colNumber, - line: lineNumber - } - }; - return codeFrameColumns(rawLines, location, opts); -} - -/***/ }), - -/***/ "../../node_modules/@babel/helper-validator-identifier/lib/identifier.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.isIdentifierChar = isIdentifierChar; -exports.isIdentifierName = isIdentifierName; -exports.isIdentifierStart = isIdentifierStart; -let nonASCIIidentifierStartChars = "\xaa\xb5\xba\xc0-\xd6\xd8-\xf6\xf8-\u02c1\u02c6-\u02d1\u02e0-\u02e4\u02ec\u02ee\u0370-\u0374\u0376\u0377\u037a-\u037d\u037f\u0386\u0388-\u038a\u038c\u038e-\u03a1\u03a3-\u03f5\u03f7-\u0481\u048a-\u052f\u0531-\u0556\u0559\u0560-\u0588\u05d0-\u05ea\u05ef-\u05f2\u0620-\u064a\u066e\u066f\u0671-\u06d3\u06d5\u06e5\u06e6\u06ee\u06ef\u06fa-\u06fc\u06ff\u0710\u0712-\u072f\u074d-\u07a5\u07b1\u07ca-\u07ea\u07f4\u07f5\u07fa\u0800-\u0815\u081a\u0824\u0828\u0840-\u0858\u0860-\u086a\u0870-\u0887\u0889-\u088e\u08a0-\u08c9\u0904-\u0939\u093d\u0950\u0958-\u0961\u0971-\u0980\u0985-\u098c\u098f\u0990\u0993-\u09a8\u09aa-\u09b0\u09b2\u09b6-\u09b9\u09bd\u09ce\u09dc\u09dd\u09df-\u09e1\u09f0\u09f1\u09fc\u0a05-\u0a0a\u0a0f\u0a10\u0a13-\u0a28\u0a2a-\u0a30\u0a32\u0a33\u0a35\u0a36\u0a38\u0a39\u0a59-\u0a5c\u0a5e\u0a72-\u0a74\u0a85-\u0a8d\u0a8f-\u0a91\u0a93-\u0aa8\u0aaa-\u0ab0\u0ab2\u0ab3\u0ab5-\u0ab9\u0abd\u0ad0\u0ae0\u0ae1\u0af9\u0b05-\u0b0c\u0b0f\u0b10\u0b13-\u0b28\u0b2a-\u0b30\u0b32\u0b33\u0b35-\u0b39\u0b3d\u0b5c\u0b5d\u0b5f-\u0b61\u0b71\u0b83\u0b85-\u0b8a\u0b8e-\u0b90\u0b92-\u0b95\u0b99\u0b9a\u0b9c\u0b9e\u0b9f\u0ba3\u0ba4\u0ba8-\u0baa\u0bae-\u0bb9\u0bd0\u0c05-\u0c0c\u0c0e-\u0c10\u0c12-\u0c28\u0c2a-\u0c39\u0c3d\u0c58-\u0c5a\u0c5d\u0c60\u0c61\u0c80\u0c85-\u0c8c\u0c8e-\u0c90\u0c92-\u0ca8\u0caa-\u0cb3\u0cb5-\u0cb9\u0cbd\u0cdd\u0cde\u0ce0\u0ce1\u0cf1\u0cf2\u0d04-\u0d0c\u0d0e-\u0d10\u0d12-\u0d3a\u0d3d\u0d4e\u0d54-\u0d56\u0d5f-\u0d61\u0d7a-\u0d7f\u0d85-\u0d96\u0d9a-\u0db1\u0db3-\u0dbb\u0dbd\u0dc0-\u0dc6\u0e01-\u0e30\u0e32\u0e33\u0e40-\u0e46\u0e81\u0e82\u0e84\u0e86-\u0e8a\u0e8c-\u0ea3\u0ea5\u0ea7-\u0eb0\u0eb2\u0eb3\u0ebd\u0ec0-\u0ec4\u0ec6\u0edc-\u0edf\u0f00\u0f40-\u0f47\u0f49-\u0f6c\u0f88-\u0f8c\u1000-\u102a\u103f\u1050-\u1055\u105a-\u105d\u1061\u1065\u1066\u106e-\u1070\u1075-\u1081\u108e\u10a0-\u10c5\u10c7\u10cd\u10d0-\u10fa\u10fc-\u1248\u124a-\u124d\u1250-\u1256\u1258\u125a-\u125d\u1260-\u1288\u128a-\u128d\u1290-\u12b0\u12b2-\u12b5\u12b8-\u12be\u12c0\u12c2-\u12c5\u12c8-\u12d6\u12d8-\u1310\u1312-\u1315\u1318-\u135a\u1380-\u138f\u13a0-\u13f5\u13f8-\u13fd\u1401-\u166c\u166f-\u167f\u1681-\u169a\u16a0-\u16ea\u16ee-\u16f8\u1700-\u1711\u171f-\u1731\u1740-\u1751\u1760-\u176c\u176e-\u1770\u1780-\u17b3\u17d7\u17dc\u1820-\u1878\u1880-\u18a8\u18aa\u18b0-\u18f5\u1900-\u191e\u1950-\u196d\u1970-\u1974\u1980-\u19ab\u19b0-\u19c9\u1a00-\u1a16\u1a20-\u1a54\u1aa7\u1b05-\u1b33\u1b45-\u1b4c\u1b83-\u1ba0\u1bae\u1baf\u1bba-\u1be5\u1c00-\u1c23\u1c4d-\u1c4f\u1c5a-\u1c7d\u1c80-\u1c88\u1c90-\u1cba\u1cbd-\u1cbf\u1ce9-\u1cec\u1cee-\u1cf3\u1cf5\u1cf6\u1cfa\u1d00-\u1dbf\u1e00-\u1f15\u1f18-\u1f1d\u1f20-\u1f45\u1f48-\u1f4d\u1f50-\u1f57\u1f59\u1f5b\u1f5d\u1f5f-\u1f7d\u1f80-\u1fb4\u1fb6-\u1fbc\u1fbe\u1fc2-\u1fc4\u1fc6-\u1fcc\u1fd0-\u1fd3\u1fd6-\u1fdb\u1fe0-\u1fec\u1ff2-\u1ff4\u1ff6-\u1ffc\u2071\u207f\u2090-\u209c\u2102\u2107\u210a-\u2113\u2115\u2118-\u211d\u2124\u2126\u2128\u212a-\u2139\u213c-\u213f\u2145-\u2149\u214e\u2160-\u2188\u2c00-\u2ce4\u2ceb-\u2cee\u2cf2\u2cf3\u2d00-\u2d25\u2d27\u2d2d\u2d30-\u2d67\u2d6f\u2d80-\u2d96\u2da0-\u2da6\u2da8-\u2dae\u2db0-\u2db6\u2db8-\u2dbe\u2dc0-\u2dc6\u2dc8-\u2dce\u2dd0-\u2dd6\u2dd8-\u2dde\u3005-\u3007\u3021-\u3029\u3031-\u3035\u3038-\u303c\u3041-\u3096\u309b-\u309f\u30a1-\u30fa\u30fc-\u30ff\u3105-\u312f\u3131-\u318e\u31a0-\u31bf\u31f0-\u31ff\u3400-\u4dbf\u4e00-\ua48c\ua4d0-\ua4fd\ua500-\ua60c\ua610-\ua61f\ua62a\ua62b\ua640-\ua66e\ua67f-\ua69d\ua6a0-\ua6ef\ua717-\ua71f\ua722-\ua788\ua78b-\ua7ca\ua7d0\ua7d1\ua7d3\ua7d5-\ua7d9\ua7f2-\ua801\ua803-\ua805\ua807-\ua80a\ua80c-\ua822\ua840-\ua873\ua882-\ua8b3\ua8f2-\ua8f7\ua8fb\ua8fd\ua8fe\ua90a-\ua925\ua930-\ua946\ua960-\ua97c\ua984-\ua9b2\ua9cf\ua9e0-\ua9e4\ua9e6-\ua9ef\ua9fa-\ua9fe\uaa00-\uaa28\uaa40-\uaa42\uaa44-\uaa4b\uaa60-\uaa76\uaa7a\uaa7e-\uaaaf\uaab1\uaab5\uaab6\uaab9-\uaabd\uaac0\uaac2\uaadb-\uaadd\uaae0-\uaaea\uaaf2-\uaaf4\uab01-\uab06\uab09-\uab0e\uab11-\uab16\uab20-\uab26\uab28-\uab2e\uab30-\uab5a\uab5c-\uab69\uab70-\uabe2\uac00-\ud7a3\ud7b0-\ud7c6\ud7cb-\ud7fb\uf900-\ufa6d\ufa70-\ufad9\ufb00-\ufb06\ufb13-\ufb17\ufb1d\ufb1f-\ufb28\ufb2a-\ufb36\ufb38-\ufb3c\ufb3e\ufb40\ufb41\ufb43\ufb44\ufb46-\ufbb1\ufbd3-\ufd3d\ufd50-\ufd8f\ufd92-\ufdc7\ufdf0-\ufdfb\ufe70-\ufe74\ufe76-\ufefc\uff21-\uff3a\uff41-\uff5a\uff66-\uffbe\uffc2-\uffc7\uffca-\uffcf\uffd2-\uffd7\uffda-\uffdc"; -let nonASCIIidentifierChars = "\u200c\u200d\xb7\u0300-\u036f\u0387\u0483-\u0487\u0591-\u05bd\u05bf\u05c1\u05c2\u05c4\u05c5\u05c7\u0610-\u061a\u064b-\u0669\u0670\u06d6-\u06dc\u06df-\u06e4\u06e7\u06e8\u06ea-\u06ed\u06f0-\u06f9\u0711\u0730-\u074a\u07a6-\u07b0\u07c0-\u07c9\u07eb-\u07f3\u07fd\u0816-\u0819\u081b-\u0823\u0825-\u0827\u0829-\u082d\u0859-\u085b\u0898-\u089f\u08ca-\u08e1\u08e3-\u0903\u093a-\u093c\u093e-\u094f\u0951-\u0957\u0962\u0963\u0966-\u096f\u0981-\u0983\u09bc\u09be-\u09c4\u09c7\u09c8\u09cb-\u09cd\u09d7\u09e2\u09e3\u09e6-\u09ef\u09fe\u0a01-\u0a03\u0a3c\u0a3e-\u0a42\u0a47\u0a48\u0a4b-\u0a4d\u0a51\u0a66-\u0a71\u0a75\u0a81-\u0a83\u0abc\u0abe-\u0ac5\u0ac7-\u0ac9\u0acb-\u0acd\u0ae2\u0ae3\u0ae6-\u0aef\u0afa-\u0aff\u0b01-\u0b03\u0b3c\u0b3e-\u0b44\u0b47\u0b48\u0b4b-\u0b4d\u0b55-\u0b57\u0b62\u0b63\u0b66-\u0b6f\u0b82\u0bbe-\u0bc2\u0bc6-\u0bc8\u0bca-\u0bcd\u0bd7\u0be6-\u0bef\u0c00-\u0c04\u0c3c\u0c3e-\u0c44\u0c46-\u0c48\u0c4a-\u0c4d\u0c55\u0c56\u0c62\u0c63\u0c66-\u0c6f\u0c81-\u0c83\u0cbc\u0cbe-\u0cc4\u0cc6-\u0cc8\u0cca-\u0ccd\u0cd5\u0cd6\u0ce2\u0ce3\u0ce6-\u0cef\u0d00-\u0d03\u0d3b\u0d3c\u0d3e-\u0d44\u0d46-\u0d48\u0d4a-\u0d4d\u0d57\u0d62\u0d63\u0d66-\u0d6f\u0d81-\u0d83\u0dca\u0dcf-\u0dd4\u0dd6\u0dd8-\u0ddf\u0de6-\u0def\u0df2\u0df3\u0e31\u0e34-\u0e3a\u0e47-\u0e4e\u0e50-\u0e59\u0eb1\u0eb4-\u0ebc\u0ec8-\u0ecd\u0ed0-\u0ed9\u0f18\u0f19\u0f20-\u0f29\u0f35\u0f37\u0f39\u0f3e\u0f3f\u0f71-\u0f84\u0f86\u0f87\u0f8d-\u0f97\u0f99-\u0fbc\u0fc6\u102b-\u103e\u1040-\u1049\u1056-\u1059\u105e-\u1060\u1062-\u1064\u1067-\u106d\u1071-\u1074\u1082-\u108d\u108f-\u109d\u135d-\u135f\u1369-\u1371\u1712-\u1715\u1732-\u1734\u1752\u1753\u1772\u1773\u17b4-\u17d3\u17dd\u17e0-\u17e9\u180b-\u180d\u180f-\u1819\u18a9\u1920-\u192b\u1930-\u193b\u1946-\u194f\u19d0-\u19da\u1a17-\u1a1b\u1a55-\u1a5e\u1a60-\u1a7c\u1a7f-\u1a89\u1a90-\u1a99\u1ab0-\u1abd\u1abf-\u1ace\u1b00-\u1b04\u1b34-\u1b44\u1b50-\u1b59\u1b6b-\u1b73\u1b80-\u1b82\u1ba1-\u1bad\u1bb0-\u1bb9\u1be6-\u1bf3\u1c24-\u1c37\u1c40-\u1c49\u1c50-\u1c59\u1cd0-\u1cd2\u1cd4-\u1ce8\u1ced\u1cf4\u1cf7-\u1cf9\u1dc0-\u1dff\u203f\u2040\u2054\u20d0-\u20dc\u20e1\u20e5-\u20f0\u2cef-\u2cf1\u2d7f\u2de0-\u2dff\u302a-\u302f\u3099\u309a\ua620-\ua629\ua66f\ua674-\ua67d\ua69e\ua69f\ua6f0\ua6f1\ua802\ua806\ua80b\ua823-\ua827\ua82c\ua880\ua881\ua8b4-\ua8c5\ua8d0-\ua8d9\ua8e0-\ua8f1\ua8ff-\ua909\ua926-\ua92d\ua947-\ua953\ua980-\ua983\ua9b3-\ua9c0\ua9d0-\ua9d9\ua9e5\ua9f0-\ua9f9\uaa29-\uaa36\uaa43\uaa4c\uaa4d\uaa50-\uaa59\uaa7b-\uaa7d\uaab0\uaab2-\uaab4\uaab7\uaab8\uaabe\uaabf\uaac1\uaaeb-\uaaef\uaaf5\uaaf6\uabe3-\uabea\uabec\uabed\uabf0-\uabf9\ufb1e\ufe00-\ufe0f\ufe20-\ufe2f\ufe33\ufe34\ufe4d-\ufe4f\uff10-\uff19\uff3f"; -const nonASCIIidentifierStart = new RegExp("[" + nonASCIIidentifierStartChars + "]"); -const nonASCIIidentifier = new RegExp("[" + nonASCIIidentifierStartChars + nonASCIIidentifierChars + "]"); -nonASCIIidentifierStartChars = nonASCIIidentifierChars = null; -const astralIdentifierStartCodes = [0, 11, 2, 25, 2, 18, 2, 1, 2, 14, 3, 13, 35, 122, 70, 52, 268, 28, 4, 48, 48, 31, 14, 29, 6, 37, 11, 29, 3, 35, 5, 7, 2, 4, 43, 157, 19, 35, 5, 35, 5, 39, 9, 51, 13, 10, 2, 14, 2, 6, 2, 1, 2, 10, 2, 14, 2, 6, 2, 1, 68, 310, 10, 21, 11, 7, 25, 5, 2, 41, 2, 8, 70, 5, 3, 0, 2, 43, 2, 1, 4, 0, 3, 22, 11, 22, 10, 30, 66, 18, 2, 1, 11, 21, 11, 25, 71, 55, 7, 1, 65, 0, 16, 3, 2, 2, 2, 28, 43, 28, 4, 28, 36, 7, 2, 27, 28, 53, 11, 21, 11, 18, 14, 17, 111, 72, 56, 50, 14, 50, 14, 35, 349, 41, 7, 1, 79, 28, 11, 0, 9, 21, 43, 17, 47, 20, 28, 22, 13, 52, 58, 1, 3, 0, 14, 44, 33, 24, 27, 35, 30, 0, 3, 0, 9, 34, 4, 0, 13, 47, 15, 3, 22, 0, 2, 0, 36, 17, 2, 24, 85, 6, 2, 0, 2, 3, 2, 14, 2, 9, 8, 46, 39, 7, 3, 1, 3, 21, 2, 6, 2, 1, 2, 4, 4, 0, 19, 0, 13, 4, 159, 52, 19, 3, 21, 2, 31, 47, 21, 1, 2, 0, 185, 46, 42, 3, 37, 47, 21, 0, 60, 42, 14, 0, 72, 26, 38, 6, 186, 43, 117, 63, 32, 7, 3, 0, 3, 7, 2, 1, 2, 23, 16, 0, 2, 0, 95, 7, 3, 38, 17, 0, 2, 0, 29, 0, 11, 39, 8, 0, 22, 0, 12, 45, 20, 0, 19, 72, 264, 8, 2, 36, 18, 0, 50, 29, 113, 6, 2, 1, 2, 37, 22, 0, 26, 5, 2, 1, 2, 31, 15, 0, 328, 18, 190, 0, 80, 921, 103, 110, 18, 195, 2637, 96, 16, 1070, 4050, 582, 8634, 568, 8, 30, 18, 78, 18, 29, 19, 47, 17, 3, 32, 20, 6, 18, 689, 63, 129, 74, 6, 0, 67, 12, 65, 1, 2, 0, 29, 6135, 9, 1237, 43, 8, 8936, 3, 2, 6, 2, 1, 2, 290, 46, 2, 18, 3, 9, 395, 2309, 106, 6, 12, 4, 8, 8, 9, 5991, 84, 2, 70, 2, 1, 3, 0, 3, 1, 3, 3, 2, 11, 2, 0, 2, 6, 2, 64, 2, 3, 3, 7, 2, 6, 2, 27, 2, 3, 2, 4, 2, 0, 4, 6, 2, 339, 3, 24, 2, 24, 2, 30, 2, 24, 2, 30, 2, 24, 2, 30, 2, 24, 2, 30, 2, 24, 2, 7, 1845, 30, 482, 44, 11, 6, 17, 0, 322, 29, 19, 43, 1269, 6, 2, 3, 2, 1, 2, 14, 2, 196, 60, 67, 8, 0, 1205, 3, 2, 26, 2, 1, 2, 0, 3, 0, 2, 9, 2, 3, 2, 0, 2, 0, 7, 0, 5, 0, 2, 0, 2, 0, 2, 2, 2, 1, 2, 0, 3, 0, 2, 0, 2, 0, 2, 0, 2, 0, 2, 1, 2, 0, 3, 3, 2, 6, 2, 3, 2, 3, 2, 0, 2, 9, 2, 16, 6, 2, 2, 4, 2, 16, 4421, 42719, 33, 4152, 8, 221, 3, 5761, 15, 7472, 3104, 541, 1507, 4938]; -const astralIdentifierCodes = [509, 0, 227, 0, 150, 4, 294, 9, 1368, 2, 2, 1, 6, 3, 41, 2, 5, 0, 166, 1, 574, 3, 9, 9, 370, 1, 154, 10, 50, 3, 123, 2, 54, 14, 32, 10, 3, 1, 11, 3, 46, 10, 8, 0, 46, 9, 7, 2, 37, 13, 2, 9, 6, 1, 45, 0, 13, 2, 49, 13, 9, 3, 2, 11, 83, 11, 7, 0, 161, 11, 6, 9, 7, 3, 56, 1, 2, 6, 3, 1, 3, 2, 10, 0, 11, 1, 3, 6, 4, 4, 193, 17, 10, 9, 5, 0, 82, 19, 13, 9, 214, 6, 3, 8, 28, 1, 83, 16, 16, 9, 82, 12, 9, 9, 84, 14, 5, 9, 243, 14, 166, 9, 71, 5, 2, 1, 3, 3, 2, 0, 2, 1, 13, 9, 120, 6, 3, 6, 4, 0, 29, 9, 41, 6, 2, 3, 9, 0, 10, 10, 47, 15, 406, 7, 2, 7, 17, 9, 57, 21, 2, 13, 123, 5, 4, 0, 2, 1, 2, 6, 2, 0, 9, 9, 49, 4, 2, 1, 2, 4, 9, 9, 330, 3, 19306, 9, 87, 9, 39, 4, 60, 6, 26, 9, 1014, 0, 2, 54, 8, 3, 82, 0, 12, 1, 19628, 1, 4706, 45, 3, 22, 543, 4, 4, 5, 9, 7, 3, 6, 31, 3, 149, 2, 1418, 49, 513, 54, 5, 49, 9, 0, 15, 0, 23, 4, 2, 14, 1361, 6, 2, 16, 3, 6, 2, 1, 2, 4, 262, 6, 10, 9, 357, 0, 62, 13, 1495, 6, 110, 6, 6, 9, 4759, 9, 787719, 239]; - -function isInAstralSet(code, set) { - let pos = 0x10000; - - for (let i = 0, length = set.length; i < length; i += 2) { - pos += set[i]; - if (pos > code) return false; - pos += set[i + 1]; - if (pos >= code) return true; - } - - return false; -} - -function isIdentifierStart(code) { - if (code < 65) return code === 36; - if (code <= 90) return true; - if (code < 97) return code === 95; - if (code <= 122) return true; - - if (code <= 0xffff) { - return code >= 0xaa && nonASCIIidentifierStart.test(String.fromCharCode(code)); - } - - return isInAstralSet(code, astralIdentifierStartCodes); -} - -function isIdentifierChar(code) { - if (code < 48) return code === 36; - if (code < 58) return true; - if (code < 65) return false; - if (code <= 90) return true; - if (code < 97) return code === 95; - if (code <= 122) return true; - - if (code <= 0xffff) { - return code >= 0xaa && nonASCIIidentifier.test(String.fromCharCode(code)); - } - - return isInAstralSet(code, astralIdentifierStartCodes) || isInAstralSet(code, astralIdentifierCodes); -} - -function isIdentifierName(name) { - let isFirst = true; - - for (let i = 0; i < name.length; i++) { - let cp = name.charCodeAt(i); - - if ((cp & 0xfc00) === 0xd800 && i + 1 < name.length) { - const trail = name.charCodeAt(++i); - - if ((trail & 0xfc00) === 0xdc00) { - cp = 0x10000 + ((cp & 0x3ff) << 10) + (trail & 0x3ff); - } - } - - if (isFirst) { - isFirst = false; - - if (!isIdentifierStart(cp)) { - return false; - } - } else if (!isIdentifierChar(cp)) { - return false; - } - } - - return !isFirst; -} - -/***/ }), - -/***/ "../../node_modules/@babel/helper-validator-identifier/lib/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -Object.defineProperty(exports, "isIdentifierChar", { - enumerable: true, - get: function () { - return _identifier.isIdentifierChar; - } -}); -Object.defineProperty(exports, "isIdentifierName", { - enumerable: true, - get: function () { - return _identifier.isIdentifierName; - } -}); -Object.defineProperty(exports, "isIdentifierStart", { - enumerable: true, - get: function () { - return _identifier.isIdentifierStart; - } -}); -Object.defineProperty(exports, "isKeyword", { - enumerable: true, - get: function () { - return _keyword.isKeyword; - } -}); -Object.defineProperty(exports, "isReservedWord", { - enumerable: true, - get: function () { - return _keyword.isReservedWord; - } -}); -Object.defineProperty(exports, "isStrictBindOnlyReservedWord", { - enumerable: true, - get: function () { - return _keyword.isStrictBindOnlyReservedWord; - } -}); -Object.defineProperty(exports, "isStrictBindReservedWord", { - enumerable: true, - get: function () { - return _keyword.isStrictBindReservedWord; - } -}); -Object.defineProperty(exports, "isStrictReservedWord", { - enumerable: true, - get: function () { - return _keyword.isStrictReservedWord; - } -}); - -var _identifier = __webpack_require__("../../node_modules/@babel/helper-validator-identifier/lib/identifier.js"); - -var _keyword = __webpack_require__("../../node_modules/@babel/helper-validator-identifier/lib/keyword.js"); - -/***/ }), - -/***/ "../../node_modules/@babel/helper-validator-identifier/lib/keyword.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.isKeyword = isKeyword; -exports.isReservedWord = isReservedWord; -exports.isStrictBindOnlyReservedWord = isStrictBindOnlyReservedWord; -exports.isStrictBindReservedWord = isStrictBindReservedWord; -exports.isStrictReservedWord = isStrictReservedWord; -const reservedWords = { - keyword: ["break", "case", "catch", "continue", "debugger", "default", "do", "else", "finally", "for", "function", "if", "return", "switch", "throw", "try", "var", "const", "while", "with", "new", "this", "super", "class", "extends", "export", "import", "null", "true", "false", "in", "instanceof", "typeof", "void", "delete"], - strict: ["implements", "interface", "let", "package", "private", "protected", "public", "static", "yield"], - strictBind: ["eval", "arguments"] -}; -const keywords = new Set(reservedWords.keyword); -const reservedWordsStrictSet = new Set(reservedWords.strict); -const reservedWordsStrictBindSet = new Set(reservedWords.strictBind); - -function isReservedWord(word, inModule) { - return inModule && word === "await" || word === "enum"; -} - -function isStrictReservedWord(word, inModule) { - return isReservedWord(word, inModule) || reservedWordsStrictSet.has(word); -} - -function isStrictBindOnlyReservedWord(word) { - return reservedWordsStrictBindSet.has(word); -} - -function isStrictBindReservedWord(word, inModule) { - return isStrictReservedWord(word, inModule) || isStrictBindOnlyReservedWord(word); -} - -function isKeyword(word) { - return keywords.has(word); -} - -/***/ }), - -/***/ "../../node_modules/@babel/highlight/lib/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.default = highlight; -exports.getChalk = getChalk; -exports.shouldHighlight = shouldHighlight; - -var _jsTokens = __webpack_require__("../../node_modules/@babel/highlight/node_modules/js-tokens/index.js"); - -var _helperValidatorIdentifier = __webpack_require__("../../node_modules/@babel/helper-validator-identifier/lib/index.js"); - -var _chalk = __webpack_require__("../../node_modules/@babel/highlight/node_modules/chalk/index.js"); - -const sometimesKeywords = new Set(["as", "async", "from", "get", "of", "set"]); - -function getDefs(chalk) { - return { - keyword: chalk.cyan, - capitalized: chalk.yellow, - jsxIdentifier: chalk.yellow, - punctuator: chalk.yellow, - number: chalk.magenta, - string: chalk.green, - regex: chalk.magenta, - comment: chalk.grey, - invalid: chalk.white.bgRed.bold - }; -} - -const NEWLINE = /\r\n|[\n\r\u2028\u2029]/; -const BRACKET = /^[()[\]{}]$/; -let tokenize; -{ - const JSX_TAG = /^[a-z][\w-]*$/i; - - const getTokenType = function (token, offset, text) { - if (token.type === "name") { - if ((0, _helperValidatorIdentifier.isKeyword)(token.value) || (0, _helperValidatorIdentifier.isStrictReservedWord)(token.value, true) || sometimesKeywords.has(token.value)) { - return "keyword"; - } - - if (JSX_TAG.test(token.value) && (text[offset - 1] === "<" || text.substr(offset - 2, 2) == " colorize(str)).join("\n"); - } else { - highlighted += value; - } - } - - return highlighted; -} - -function shouldHighlight(options) { - return !!_chalk.supportsColor || options.forceColor; -} - -function getChalk(options) { - return options.forceColor ? new _chalk.constructor({ - enabled: true, - level: 1 - }) : _chalk; -} - -function highlight(code, options = {}) { - if (code !== "" && shouldHighlight(options)) { - const chalk = getChalk(options); - const defs = getDefs(chalk); - return highlightTokens(defs, code); - } else { - return code; - } -} - -/***/ }), - -/***/ "../../node_modules/@babel/highlight/node_modules/ansi-styles/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/* WEBPACK VAR INJECTION */(function(module) { -const colorConvert = __webpack_require__("../../node_modules/color-convert/index.js"); - -const wrapAnsi16 = (fn, offset) => function () { - const code = fn.apply(colorConvert, arguments); - return `\u001B[${code + offset}m`; -}; - -const wrapAnsi256 = (fn, offset) => function () { - const code = fn.apply(colorConvert, arguments); - return `\u001B[${38 + offset};5;${code}m`; -}; - -const wrapAnsi16m = (fn, offset) => function () { - const rgb = fn.apply(colorConvert, arguments); - return `\u001B[${38 + offset};2;${rgb[0]};${rgb[1]};${rgb[2]}m`; -}; - -function assembleStyles() { - const codes = new Map(); - const styles = { - modifier: { - reset: [0, 0], - // 21 isn't widely supported and 22 does the same thing - bold: [1, 22], - dim: [2, 22], - italic: [3, 23], - underline: [4, 24], - inverse: [7, 27], - hidden: [8, 28], - strikethrough: [9, 29] - }, - color: { - black: [30, 39], - red: [31, 39], - green: [32, 39], - yellow: [33, 39], - blue: [34, 39], - magenta: [35, 39], - cyan: [36, 39], - white: [37, 39], - gray: [90, 39], - - // Bright color - redBright: [91, 39], - greenBright: [92, 39], - yellowBright: [93, 39], - blueBright: [94, 39], - magentaBright: [95, 39], - cyanBright: [96, 39], - whiteBright: [97, 39] - }, - bgColor: { - bgBlack: [40, 49], - bgRed: [41, 49], - bgGreen: [42, 49], - bgYellow: [43, 49], - bgBlue: [44, 49], - bgMagenta: [45, 49], - bgCyan: [46, 49], - bgWhite: [47, 49], - - // Bright color - bgBlackBright: [100, 49], - bgRedBright: [101, 49], - bgGreenBright: [102, 49], - bgYellowBright: [103, 49], - bgBlueBright: [104, 49], - bgMagentaBright: [105, 49], - bgCyanBright: [106, 49], - bgWhiteBright: [107, 49] - } - }; - - // Fix humans - styles.color.grey = styles.color.gray; - - for (const groupName of Object.keys(styles)) { - const group = styles[groupName]; - - for (const styleName of Object.keys(group)) { - const style = group[styleName]; - - styles[styleName] = { - open: `\u001B[${style[0]}m`, - close: `\u001B[${style[1]}m` - }; - - group[styleName] = styles[styleName]; - - codes.set(style[0], style[1]); - } - - Object.defineProperty(styles, groupName, { - value: group, - enumerable: false - }); - - Object.defineProperty(styles, 'codes', { - value: codes, - enumerable: false - }); - } - - const ansi2ansi = n => n; - const rgb2rgb = (r, g, b) => [r, g, b]; - - styles.color.close = '\u001B[39m'; - styles.bgColor.close = '\u001B[49m'; - - styles.color.ansi = { - ansi: wrapAnsi16(ansi2ansi, 0) - }; - styles.color.ansi256 = { - ansi256: wrapAnsi256(ansi2ansi, 0) - }; - styles.color.ansi16m = { - rgb: wrapAnsi16m(rgb2rgb, 0) - }; - - styles.bgColor.ansi = { - ansi: wrapAnsi16(ansi2ansi, 10) - }; - styles.bgColor.ansi256 = { - ansi256: wrapAnsi256(ansi2ansi, 10) - }; - styles.bgColor.ansi16m = { - rgb: wrapAnsi16m(rgb2rgb, 10) - }; - - for (let key of Object.keys(colorConvert)) { - if (typeof colorConvert[key] !== 'object') { - continue; - } - - const suite = colorConvert[key]; - - if (key === 'ansi16') { - key = 'ansi'; - } - - if ('ansi16' in suite) { - styles.color.ansi[key] = wrapAnsi16(suite.ansi16, 0); - styles.bgColor.ansi[key] = wrapAnsi16(suite.ansi16, 10); - } - - if ('ansi256' in suite) { - styles.color.ansi256[key] = wrapAnsi256(suite.ansi256, 0); - styles.bgColor.ansi256[key] = wrapAnsi256(suite.ansi256, 10); - } - - if ('rgb' in suite) { - styles.color.ansi16m[key] = wrapAnsi16m(suite.rgb, 0); - styles.bgColor.ansi16m[key] = wrapAnsi16m(suite.rgb, 10); - } - } - - return styles; -} - -// Make the export immutable -Object.defineProperty(module, 'exports', { - enumerable: true, - get: assembleStyles -}); - -/* WEBPACK VAR INJECTION */}.call(this, __webpack_require__("../../node_modules/webpack/buildin/module.js")(module))) - -/***/ }), - -/***/ "../../node_modules/@babel/highlight/node_modules/chalk/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const escapeStringRegexp = __webpack_require__("../../node_modules/escape-string-regexp/index.js"); -const ansiStyles = __webpack_require__("../../node_modules/@babel/highlight/node_modules/ansi-styles/index.js"); -const stdoutColor = __webpack_require__("../../node_modules/@babel/highlight/node_modules/supports-color/index.js").stdout; - -const template = __webpack_require__("../../node_modules/@babel/highlight/node_modules/chalk/templates.js"); - -const isSimpleWindowsTerm = process.platform === 'win32' && !(process.env.TERM || '').toLowerCase().startsWith('xterm'); - -// `supportsColor.level` → `ansiStyles.color[name]` mapping -const levelMapping = ['ansi', 'ansi', 'ansi256', 'ansi16m']; - -// `color-convert` models to exclude from the Chalk API due to conflicts and such -const skipModels = new Set(['gray']); - -const styles = Object.create(null); - -function applyOptions(obj, options) { - options = options || {}; - - // Detect level if not set manually - const scLevel = stdoutColor ? stdoutColor.level : 0; - obj.level = options.level === undefined ? scLevel : options.level; - obj.enabled = 'enabled' in options ? options.enabled : obj.level > 0; -} - -function Chalk(options) { - // We check for this.template here since calling `chalk.constructor()` - // by itself will have a `this` of a previously constructed chalk object - if (!this || !(this instanceof Chalk) || this.template) { - const chalk = {}; - applyOptions(chalk, options); - - chalk.template = function () { - const args = [].slice.call(arguments); - return chalkTag.apply(null, [chalk.template].concat(args)); - }; - - Object.setPrototypeOf(chalk, Chalk.prototype); - Object.setPrototypeOf(chalk.template, chalk); - - chalk.template.constructor = Chalk; - - return chalk.template; - } - - applyOptions(this, options); -} - -// Use bright blue on Windows as the normal blue color is illegible -if (isSimpleWindowsTerm) { - ansiStyles.blue.open = '\u001B[94m'; -} - -for (const key of Object.keys(ansiStyles)) { - ansiStyles[key].closeRe = new RegExp(escapeStringRegexp(ansiStyles[key].close), 'g'); - - styles[key] = { - get() { - const codes = ansiStyles[key]; - return build.call(this, this._styles ? this._styles.concat(codes) : [codes], this._empty, key); - } - }; -} - -styles.visible = { - get() { - return build.call(this, this._styles || [], true, 'visible'); - } -}; - -ansiStyles.color.closeRe = new RegExp(escapeStringRegexp(ansiStyles.color.close), 'g'); -for (const model of Object.keys(ansiStyles.color.ansi)) { - if (skipModels.has(model)) { - continue; - } - - styles[model] = { - get() { - const level = this.level; - return function () { - const open = ansiStyles.color[levelMapping[level]][model].apply(null, arguments); - const codes = { - open, - close: ansiStyles.color.close, - closeRe: ansiStyles.color.closeRe - }; - return build.call(this, this._styles ? this._styles.concat(codes) : [codes], this._empty, model); - }; - } - }; -} - -ansiStyles.bgColor.closeRe = new RegExp(escapeStringRegexp(ansiStyles.bgColor.close), 'g'); -for (const model of Object.keys(ansiStyles.bgColor.ansi)) { - if (skipModels.has(model)) { - continue; - } - - const bgModel = 'bg' + model[0].toUpperCase() + model.slice(1); - styles[bgModel] = { - get() { - const level = this.level; - return function () { - const open = ansiStyles.bgColor[levelMapping[level]][model].apply(null, arguments); - const codes = { - open, - close: ansiStyles.bgColor.close, - closeRe: ansiStyles.bgColor.closeRe - }; - return build.call(this, this._styles ? this._styles.concat(codes) : [codes], this._empty, model); - }; - } - }; -} - -const proto = Object.defineProperties(() => {}, styles); - -function build(_styles, _empty, key) { - const builder = function () { - return applyStyle.apply(builder, arguments); - }; - - builder._styles = _styles; - builder._empty = _empty; - - const self = this; - - Object.defineProperty(builder, 'level', { - enumerable: true, - get() { - return self.level; - }, - set(level) { - self.level = level; - } - }); - - Object.defineProperty(builder, 'enabled', { - enumerable: true, - get() { - return self.enabled; - }, - set(enabled) { - self.enabled = enabled; - } - }); - - // See below for fix regarding invisible grey/dim combination on Windows - builder.hasGrey = this.hasGrey || key === 'gray' || key === 'grey'; - - // `__proto__` is used because we must return a function, but there is - // no way to create a function with a different prototype - builder.__proto__ = proto; // eslint-disable-line no-proto - - return builder; -} - -function applyStyle() { - // Support varags, but simply cast to string in case there's only one arg - const args = arguments; - const argsLen = args.length; - let str = String(arguments[0]); - - if (argsLen === 0) { - return ''; - } - - if (argsLen > 1) { - // Don't slice `arguments`, it prevents V8 optimizations - for (let a = 1; a < argsLen; a++) { - str += ' ' + args[a]; - } - } - - if (!this.enabled || this.level <= 0 || !str) { - return this._empty ? '' : str; - } - - // Turns out that on Windows dimmed gray text becomes invisible in cmd.exe, - // see https://github.com/chalk/chalk/issues/58 - // If we're on Windows and we're dealing with a gray color, temporarily make 'dim' a noop. - const originalDim = ansiStyles.dim.open; - if (isSimpleWindowsTerm && this.hasGrey) { - ansiStyles.dim.open = ''; - } - - for (const code of this._styles.slice().reverse()) { - // Replace any instances already present with a re-opening code - // otherwise only the part of the string until said closing code - // will be colored, and the rest will simply be 'plain'. - str = code.open + str.replace(code.closeRe, code.open) + code.close; - - // Close the styling before a linebreak and reopen - // after next line to fix a bleed issue on macOS - // https://github.com/chalk/chalk/pull/92 - str = str.replace(/\r?\n/g, `${code.close}$&${code.open}`); - } - - // Reset the original `dim` if we changed it to work around the Windows dimmed gray issue - ansiStyles.dim.open = originalDim; - - return str; -} - -function chalkTag(chalk, strings) { - if (!Array.isArray(strings)) { - // If chalk() was called by itself or with a string, - // return the string itself as a string. - return [].slice.call(arguments, 1).join(' '); - } - - const args = [].slice.call(arguments, 2); - const parts = [strings.raw[0]]; - - for (let i = 1; i < strings.length; i++) { - parts.push(String(args[i - 1]).replace(/[{}\\]/g, '\\$&')); - parts.push(String(strings.raw[i])); - } - - return template(chalk, parts.join('')); -} - -Object.defineProperties(Chalk.prototype, styles); - -module.exports = Chalk(); // eslint-disable-line new-cap -module.exports.supportsColor = stdoutColor; -module.exports.default = module.exports; // For TypeScript - - -/***/ }), - -/***/ "../../node_modules/@babel/highlight/node_modules/chalk/templates.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const TEMPLATE_REGEX = /(?:\\(u[a-f\d]{4}|x[a-f\d]{2}|.))|(?:\{(~)?(\w+(?:\([^)]*\))?(?:\.\w+(?:\([^)]*\))?)*)(?:[ \t]|(?=\r?\n)))|(\})|((?:.|[\r\n\f])+?)/gi; -const STYLE_REGEX = /(?:^|\.)(\w+)(?:\(([^)]*)\))?/g; -const STRING_REGEX = /^(['"])((?:\\.|(?!\1)[^\\])*)\1$/; -const ESCAPE_REGEX = /\\(u[a-f\d]{4}|x[a-f\d]{2}|.)|([^\\])/gi; - -const ESCAPES = new Map([ - ['n', '\n'], - ['r', '\r'], - ['t', '\t'], - ['b', '\b'], - ['f', '\f'], - ['v', '\v'], - ['0', '\0'], - ['\\', '\\'], - ['e', '\u001B'], - ['a', '\u0007'] -]); - -function unescape(c) { - if ((c[0] === 'u' && c.length === 5) || (c[0] === 'x' && c.length === 3)) { - return String.fromCharCode(parseInt(c.slice(1), 16)); - } - - return ESCAPES.get(c) || c; -} - -function parseArguments(name, args) { - const results = []; - const chunks = args.trim().split(/\s*,\s*/g); - let matches; - - for (const chunk of chunks) { - if (!isNaN(chunk)) { - results.push(Number(chunk)); - } else if ((matches = chunk.match(STRING_REGEX))) { - results.push(matches[2].replace(ESCAPE_REGEX, (m, escape, chr) => escape ? unescape(escape) : chr)); - } else { - throw new Error(`Invalid Chalk template style argument: ${chunk} (in style '${name}')`); - } - } - - return results; -} - -function parseStyle(style) { - STYLE_REGEX.lastIndex = 0; - - const results = []; - let matches; - - while ((matches = STYLE_REGEX.exec(style)) !== null) { - const name = matches[1]; - - if (matches[2]) { - const args = parseArguments(name, matches[2]); - results.push([name].concat(args)); - } else { - results.push([name]); - } - } - - return results; -} - -function buildStyle(chalk, styles) { - const enabled = {}; - - for (const layer of styles) { - for (const style of layer.styles) { - enabled[style[0]] = layer.inverse ? null : style.slice(1); - } - } - - let current = chalk; - for (const styleName of Object.keys(enabled)) { - if (Array.isArray(enabled[styleName])) { - if (!(styleName in current)) { - throw new Error(`Unknown Chalk style: ${styleName}`); - } - - if (enabled[styleName].length > 0) { - current = current[styleName].apply(current, enabled[styleName]); - } else { - current = current[styleName]; - } - } - } - - return current; -} - -module.exports = (chalk, tmp) => { - const styles = []; - const chunks = []; - let chunk = []; - - // eslint-disable-next-line max-params - tmp.replace(TEMPLATE_REGEX, (m, escapeChar, inverse, style, close, chr) => { - if (escapeChar) { - chunk.push(unescape(escapeChar)); - } else if (style) { - const str = chunk.join(''); - chunk = []; - chunks.push(styles.length === 0 ? str : buildStyle(chalk, styles)(str)); - styles.push({inverse, styles: parseStyle(style)}); - } else if (close) { - if (styles.length === 0) { - throw new Error('Found extraneous } in Chalk template literal'); - } - - chunks.push(buildStyle(chalk, styles)(chunk.join(''))); - chunk = []; - styles.pop(); - } else { - chunk.push(chr); - } - }); - - chunks.push(chunk.join('')); - - if (styles.length > 0) { - const errMsg = `Chalk template literal is missing ${styles.length} closing bracket${styles.length === 1 ? '' : 's'} (\`}\`)`; - throw new Error(errMsg); - } - - return chunks.join(''); -}; - - -/***/ }), - -/***/ "../../node_modules/@babel/highlight/node_modules/has-flag/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = (flag, argv) => { - argv = argv || process.argv; - const prefix = flag.startsWith('-') ? '' : (flag.length === 1 ? '-' : '--'); - const pos = argv.indexOf(prefix + flag); - const terminatorPos = argv.indexOf('--'); - return pos !== -1 && (terminatorPos === -1 ? true : pos < terminatorPos); -}; - - -/***/ }), - -/***/ "../../node_modules/@babel/highlight/node_modules/js-tokens/index.js": -/***/ (function(module, exports) { - -// Copyright 2014, 2015, 2016, 2017, 2018 Simon Lydell -// License: MIT. (See LICENSE.) - -Object.defineProperty(exports, "__esModule", { - value: true -}) - -// This regex comes from regex.coffee, and is inserted here by generate-index.js -// (run `npm run build`). -exports.default = /((['"])(?:(?!\2|\\).|\\(?:\r\n|[\s\S]))*(\2)?|`(?:[^`\\$]|\\[\s\S]|\$(?!\{)|\$\{(?:[^{}]|\{[^}]*\}?)*\}?)*(`)?)|(\/\/.*)|(\/\*(?:[^*]|\*(?!\/))*(\*\/)?)|(\/(?!\*)(?:\[(?:(?![\]\\]).|\\.)*\]|(?![\/\]\\]).|\\.)+\/(?:(?!\s*(?:\b|[\u0080-\uFFFF$\\'"~({]|[+\-!](?!=)|\.?\d))|[gmiyus]{1,6}\b(?![\u0080-\uFFFF$\\]|\s*(?:[+\-*%&|^<>!=?({]|\/(?![\/*])))))|(0[xX][\da-fA-F]+|0[oO][0-7]+|0[bB][01]+|(?:\d*\.\d+|\d+\.?)(?:[eE][+-]?\d+)?)|((?!\d)(?:(?!\s)[$\w\u0080-\uFFFF]|\\u[\da-fA-F]{4}|\\u\{[\da-fA-F]+\})+)|(--|\+\+|&&|\|\||=>|\.{3}|(?:[+\-\/%&|^]|\*{1,2}|<{1,2}|>{1,3}|!=?|={1,2})=?|[?~.,:;[\](){}])|(\s+)|(^$|[\s\S])/g - -exports.matchToToken = function(match) { - var token = {type: "invalid", value: match[0], closed: undefined} - if (match[ 1]) token.type = "string" , token.closed = !!(match[3] || match[4]) - else if (match[ 5]) token.type = "comment" - else if (match[ 6]) token.type = "comment", token.closed = !!match[7] - else if (match[ 8]) token.type = "regex" - else if (match[ 9]) token.type = "number" - else if (match[10]) token.type = "name" - else if (match[11]) token.type = "punctuator" - else if (match[12]) token.type = "whitespace" - return token -} - - -/***/ }), - -/***/ "../../node_modules/@babel/highlight/node_modules/supports-color/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const os = __webpack_require__("os"); -const hasFlag = __webpack_require__("../../node_modules/@babel/highlight/node_modules/has-flag/index.js"); - -const env = process.env; - -let forceColor; -if (hasFlag('no-color') || - hasFlag('no-colors') || - hasFlag('color=false')) { - forceColor = false; -} else if (hasFlag('color') || - hasFlag('colors') || - hasFlag('color=true') || - hasFlag('color=always')) { - forceColor = true; -} -if ('FORCE_COLOR' in env) { - forceColor = env.FORCE_COLOR.length === 0 || parseInt(env.FORCE_COLOR, 10) !== 0; -} - -function translateLevel(level) { - if (level === 0) { - return false; - } - - return { - level, - hasBasic: true, - has256: level >= 2, - has16m: level >= 3 - }; -} - -function supportsColor(stream) { - if (forceColor === false) { - return 0; - } - - if (hasFlag('color=16m') || - hasFlag('color=full') || - hasFlag('color=truecolor')) { - return 3; - } - - if (hasFlag('color=256')) { - return 2; - } - - if (stream && !stream.isTTY && forceColor !== true) { - return 0; - } - - const min = forceColor ? 1 : 0; - - if (process.platform === 'win32') { - // Node.js 7.5.0 is the first version of Node.js to include a patch to - // libuv that enables 256 color output on Windows. Anything earlier and it - // won't work. However, here we target Node.js 8 at minimum as it is an LTS - // release, and Node.js 7 is not. Windows 10 build 10586 is the first Windows - // release that supports 256 colors. Windows 10 build 14931 is the first release - // that supports 16m/TrueColor. - const osRelease = os.release().split('.'); - if ( - Number(process.versions.node.split('.')[0]) >= 8 && - Number(osRelease[0]) >= 10 && - Number(osRelease[2]) >= 10586 - ) { - return Number(osRelease[2]) >= 14931 ? 3 : 2; - } - - return 1; - } - - if ('CI' in env) { - if (['TRAVIS', 'CIRCLECI', 'APPVEYOR', 'GITLAB_CI'].some(sign => sign in env) || env.CI_NAME === 'codeship') { - return 1; - } - - return min; - } - - if ('TEAMCITY_VERSION' in env) { - return /^(9\.(0*[1-9]\d*)\.|\d{2,}\.)/.test(env.TEAMCITY_VERSION) ? 1 : 0; - } - - if (env.COLORTERM === 'truecolor') { - return 3; - } - - if ('TERM_PROGRAM' in env) { - const version = parseInt((env.TERM_PROGRAM_VERSION || '').split('.')[0], 10); - - switch (env.TERM_PROGRAM) { - case 'iTerm.app': - return version >= 3 ? 3 : 2; - case 'Apple_Terminal': - return 2; - // No default - } - } - - if (/-256(color)?$/i.test(env.TERM)) { - return 2; - } - - if (/^screen|^xterm|^vt100|^vt220|^rxvt|color|ansi|cygwin|linux/i.test(env.TERM)) { - return 1; - } - - if ('COLORTERM' in env) { - return 1; - } - - if (env.TERM === 'dumb') { - return min; - } - - return min; -} - -function getSupportLevel(stream) { - const level = supportsColor(stream); - return translateLevel(level); -} - -module.exports = { - supportsColor: getSupportLevel, - stdout: getSupportLevel(process.stdout), - stderr: getSupportLevel(process.stderr) -}; - - -/***/ }), - -/***/ "../../node_modules/@babel/runtime/helpers/defineProperty.js": -/***/ (function(module, exports) { - -function _defineProperty(obj, key, value) { - if (key in obj) { - Object.defineProperty(obj, key, { - value: value, - enumerable: true, - configurable: true, - writable: true - }); - } else { - obj[key] = value; - } - - return obj; -} - -module.exports = _defineProperty, module.exports.__esModule = true, module.exports["default"] = module.exports; - -/***/ }), - -/***/ "../../node_modules/@babel/runtime/helpers/interopRequireDefault.js": -/***/ (function(module, exports) { - -function _interopRequireDefault(obj) { - return obj && obj.__esModule ? obj : { - "default": obj - }; -} - -module.exports = _interopRequireDefault, module.exports.__esModule = true, module.exports["default"] = module.exports; - -/***/ }), - -/***/ "../../node_modules/@kbn/bazel-runner/target_node/bazel_runner.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.runBazel = runBazel; -exports.runIBazel = runIBazel; - -var _chalk = _interopRequireDefault(__webpack_require__("../../node_modules/chalk/source/index.js")); - -var _execa = _interopRequireDefault(__webpack_require__("../../node_modules/execa/index.js")); - -var Rx = _interopRequireWildcard(__webpack_require__("../../node_modules/rxjs/dist/esm5/index.js")); - -var _operators = __webpack_require__("../../node_modules/rxjs/dist/esm5/operators/index.js"); - -var _stdioDevHelpers = __webpack_require__("../../node_modules/@kbn/stdio-dev-helpers/target_node/index.js"); - -function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); } - -function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; } - -/* - * 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. - */ -async function runBazelCommandWithRunner(runner, options) { - const bazelProc = (0, _execa.default)(runner, options.offline ? [...options.bazelArgs, '--config=offline'] : options.bazelArgs, { ...options.execaOpts, - stdio: 'pipe', - preferLocal: true - }); - await Promise.all([// Bazel outputs machine readable output into stdout and human readable output goes to stderr. - // Therefore we need to get both. In order to get errors we need to parse the actual text line - Rx.lastValueFrom(Rx.merge((0, _stdioDevHelpers.observeLines)(bazelProc.stdout).pipe((0, _operators.tap)(line => options.log.info(`${_chalk.default.cyan(`[${runner}]`)} ${line}`))), (0, _stdioDevHelpers.observeLines)(bazelProc.stderr).pipe((0, _operators.tap)(line => options.log.info(`${_chalk.default.cyan(`[${runner}]`)} ${line}`)))).pipe(Rx.defaultIfEmpty(undefined))), // Wait for process and logs to finish, unsubscribing in the end - bazelProc.catch(() => { - options.log.error('HINT: If experiencing problems with node_modules try `yarn kbn bootstrap --force-install` or as last resort `yarn kbn reset && yarn kbn bootstrap`'); - throw new Error(`The bazel command that was running failed to complete.`); - })]); -} - -async function runBazel(options) { - await runBazelCommandWithRunner('bazel', options); -} - -async function runIBazel(options) { - var _options$execaOpts; - - await runBazelCommandWithRunner('ibazel', { ...options, - execaOpts: { ...options.execaOpts, - env: { ...((_options$execaOpts = options.execaOpts) === null || _options$execaOpts === void 0 ? void 0 : _options$execaOpts.env), - IBAZEL_USE_LEGACY_WATCHER: '0' - } - } - }); -} - -/***/ }), - -/***/ "../../node_modules/@kbn/bazel-runner/target_node/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); - -var _bazel_runner = __webpack_require__("../../node_modules/@kbn/bazel-runner/target_node/bazel_runner.js"); - -Object.keys(_bazel_runner).forEach(function (key) { - if (key === "default" || key === "__esModule") return; - if (key in exports && exports[key] === _bazel_runner[key]) return; - Object.defineProperty(exports, key, { - enumerable: true, - get: function () { - return _bazel_runner[key]; - } - }); -}); - -/***/ }), - -/***/ "../../node_modules/@kbn/ci-stats-core/target_node/ci_stats_config.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.parseConfig = parseConfig; - -/* - * 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. - */ - -/** - * Information about how CiStatsReporter should talk to the ci-stats service. Normally - * it is read from a JSON environment variable using the `parseConfig()` function - * exported by this module. - */ -function validateConfig(log, config) { - const validApiToken = typeof config.apiToken === 'string' && config.apiToken.length !== 0; - - if (!validApiToken) { - log.warning('KIBANA_CI_STATS_CONFIG is missing a valid api token, stats will not be reported'); - return; - } - - const validId = typeof config.buildId === 'string' && config.buildId.length !== 0; - - if (!validId) { - log.warning('KIBANA_CI_STATS_CONFIG is missing a valid build id, stats will not be reported'); - return; - } - - return config; -} - -function parseConfig(log) { - const configJson = process.env.KIBANA_CI_STATS_CONFIG; - - if (!configJson) { - log.debug('KIBANA_CI_STATS_CONFIG environment variable not found, disabling CiStatsReporter'); - return; - } - - let config; - - try { - config = JSON.parse(configJson); - } catch (_) {// handled below - } - - if (typeof config === 'object' && config !== null) { - return validateConfig(log, config); - } - - log.warning('KIBANA_CI_STATS_CONFIG is invalid, stats will not be reported'); - return; -} - -/***/ }), - -/***/ "../../node_modules/@kbn/ci-stats-core/target_node/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -Object.defineProperty(exports, "parseConfig", { - enumerable: true, - get: function () { - return _ci_stats_config.parseConfig; - } -}); - -var _ci_stats_config = __webpack_require__("../../node_modules/@kbn/ci-stats-core/target_node/ci_stats_config.js"); - -/***/ }), - -/***/ "../../node_modules/@kbn/ci-stats-reporter/target_node sync recursive": -/***/ (function(module, exports) { - -function webpackEmptyContext(req) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; -} -webpackEmptyContext.keys = function() { return []; }; -webpackEmptyContext.resolve = webpackEmptyContext; -module.exports = webpackEmptyContext; -webpackEmptyContext.id = "../../node_modules/@kbn/ci-stats-reporter/target_node sync recursive"; - -/***/ }), - -/***/ "../../node_modules/@kbn/ci-stats-reporter/target_node/ci_stats_reporter.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.CiStatsReporter = void 0; - -var _util = __webpack_require__("util"); - -var _os = _interopRequireDefault(__webpack_require__("os")); - -var _fs = _interopRequireDefault(__webpack_require__("fs")); - -var _path = _interopRequireDefault(__webpack_require__("path")); - -var _crypto = _interopRequireDefault(__webpack_require__("crypto")); - -var _execa = _interopRequireDefault(__webpack_require__("../../node_modules/execa/index.js")); - -var _axios = _interopRequireDefault(__webpack_require__("../../node_modules/axios/index.js")); - -var _http = _interopRequireDefault(__webpack_require__("../../node_modules/axios/lib/adapters/http.js")); - -var _ciStatsCore = __webpack_require__("../../node_modules/@kbn/ci-stats-core/target_node/index.js"); - -/* - * 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. - */ -// @ts-expect-error not "public", but necessary to prevent Jest shimming from breaking things -const BASE_URL = 'https://ci-stats.kibana.dev'; -const SECOND = 1000; -const MINUTE = 60 * SECOND; - -function limitMetaStrings(meta) { - return Object.fromEntries(Object.entries(meta).map(([key, value]) => { - if (typeof value === 'string' && value.length > 2000) { - return [key, value.slice(0, 2000)]; - } - - return [key, value]; - })); -} -/** A ci-stats metric record */ - - -/** Object that helps report data to the ci-stats service */ -class CiStatsReporter { - /** - * Create a CiStatsReporter by inspecting the ENV for the necessary config - */ - static fromEnv(log) { - return new CiStatsReporter((0, _ciStatsCore.parseConfig)(log), log); - } - - constructor(config, log) { - this.config = config; - this.log = log; - } - /** - * Determine if CI_STATS is explicitly disabled by the environment. To determine - * if the CiStatsReporter has enough information in the environment to send metrics - * for builds use #hasBuildConfig(). - */ - - - isEnabled() { - return process.env.CI_STATS_DISABLED !== 'true'; - } - /** - * Determines if the CiStatsReporter is disabled by the environment, or properly - * configured and able to send stats - */ - - - hasBuildConfig() { - var _this$config, _this$config2; - - return this.isEnabled() && !!((_this$config = this.config) !== null && _this$config !== void 0 && _this$config.apiToken) && !!((_this$config2 = this.config) !== null && _this$config2 !== void 0 && _this$config2.buildId); - } - /** - * Report timings data to the ci-stats service. If running in CI then the reporter - * will include the buildId in the report with the access token, otherwise the timings - * data will be recorded as anonymous timing data. - */ - - - async timings(options) { - var _this$config3, _options$upstreamBran, _Os$cpus, _Os$cpus$, _Os$cpus$2; - - if (!this.isEnabled()) { - return; - } - - const buildId = (_this$config3 = this.config) === null || _this$config3 === void 0 ? void 0 : _this$config3.buildId; - const timings = options.timings.map(timing => timing.meta ? { ...timing, - meta: limitMetaStrings(timing.meta) - } : timing); - const upstreamBranch = (_options$upstreamBran = options.upstreamBranch) !== null && _options$upstreamBran !== void 0 ? _options$upstreamBran : this.getUpstreamBranch(); - const kibanaUuid = options.kibanaUuid === undefined ? this.getKibanaUuid() : options.kibanaUuid; - let email; - let branch; - - try { - const { - stdout - } = await (0, _execa.default)('git', ['config', 'user.email']); - email = stdout; - } catch (e) { - this.log.debug(e.message); - } - - try { - const { - stdout - } = await (0, _execa.default)('git', ['rev-parse', '--abbrev-ref', 'HEAD']); - branch = stdout; - } catch (e) { - this.log.debug(e.message); - } - - const memUsage = process.memoryUsage(); - const isElasticCommitter = email && email.endsWith('@elastic.co') ? true : false; - const defaultMeta = { - kibanaUuid, - isElasticCommitter, - committerHash: email ? _crypto.default.createHash('sha256').update(email).digest('hex').substring(0, 20) : undefined, - email: isElasticCommitter ? email : undefined, - branch: isElasticCommitter ? branch : undefined, - cpuCount: (_Os$cpus = _os.default.cpus()) === null || _Os$cpus === void 0 ? void 0 : _Os$cpus.length, - cpuModel: (_Os$cpus$ = _os.default.cpus()[0]) === null || _Os$cpus$ === void 0 ? void 0 : _Os$cpus$.model, - cpuSpeed: (_Os$cpus$2 = _os.default.cpus()[0]) === null || _Os$cpus$2 === void 0 ? void 0 : _Os$cpus$2.speed, - freeMem: _os.default.freemem(), - memoryUsageRss: memUsage.rss, - memoryUsageHeapTotal: memUsage.heapTotal, - memoryUsageHeapUsed: memUsage.heapUsed, - memoryUsageExternal: memUsage.external, - memoryUsageArrayBuffers: memUsage.arrayBuffers, - nestedTiming: process.env.CI_STATS_NESTED_TIMING ? true : false, - osArch: _os.default.arch(), - osPlatform: _os.default.platform(), - osRelease: _os.default.release(), - totalMem: _os.default.totalmem() - }; - this.log.debug('CIStatsReporter committerHash: %s', defaultMeta.committerHash); - return !!(await this.req({ - auth: !!buildId, - path: '/v1/timings', - body: { - buildId, - upstreamBranch, - defaultMeta, - timings - }, - bodyDesc: timings.length === 1 ? `${timings.length} timing` : `${timings.length} timings` - })); - } - /** - * Report metrics data to the ci-stats service. If running outside of CI this method - * does nothing as metrics can only be reported when associated with a specific CI build. - */ - - - async metrics(metrics, options) { - var _this$config4; - - if (!this.hasBuildConfig()) { - return; - } - - const buildId = (_this$config4 = this.config) === null || _this$config4 === void 0 ? void 0 : _this$config4.buildId; - - if (!buildId) { - throw new Error(`metrics can't be reported without a buildId`); - } - - return !!(await this.req({ - auth: true, - path: '/v1/metrics', - body: { - buildId, - defaultMeta: options === null || options === void 0 ? void 0 : options.defaultMeta, - metrics - }, - bodyDesc: `metrics: ${metrics.map(({ - group, - id, - value - }) => `[${group}/${id}=${value}]`).join(' ')}` - })); - } - /** - * Send test reports to ci-stats - */ - - - async reportTests({ - group, - testRuns - }) { - var _this$config5, _this$config6, _this$config7; - - if (!((_this$config5 = this.config) !== null && _this$config5 !== void 0 && _this$config5.buildId) || !((_this$config6 = this.config) !== null && _this$config6 !== void 0 && _this$config6.apiToken)) { - throw new Error('unable to report tests unless buildId is configured and auth config available'); - } - - const groupResp = await this.req({ - auth: true, - path: '/v2/test_group', - query: { - buildId: (_this$config7 = this.config) === null || _this$config7 === void 0 ? void 0 : _this$config7.buildId - }, - bodyDesc: `[${group.name}/${group.type}] test group`, - body: group - }); - - if (!groupResp) { - return; - } - - let bufferBytes = 0; - const buffer = []; - - const flushBuffer = async () => { - var _this$config8; - - await this.req({ - auth: true, - path: '/v2/test_runs', - query: { - buildId: (_this$config8 = this.config) === null || _this$config8 === void 0 ? void 0 : _this$config8.buildId, - groupId: groupResp.groupId, - groupType: group.type - }, - bodyDesc: `[${group.name}/${group.type}] Chunk of ${bufferBytes} bytes`, - body: buffer.join('\n'), - timeout: 5 * MINUTE - }); - buffer.length = 0; - bufferBytes = 0; - }; // send test runs in chunks of ~500kb - - - for (const testRun of testRuns) { - const json = JSON.stringify(testRun); - bufferBytes += json.length; - buffer.push(json); - - if (bufferBytes >= 450000) { - await flushBuffer(); - } - } - - if (bufferBytes) { - await flushBuffer(); - } - } - - async reportPerformanceMetrics(metrics) { - var _this$config9; - - if (!this.hasBuildConfig()) { - return; - } - - const buildId = (_this$config9 = this.config) === null || _this$config9 === void 0 ? void 0 : _this$config9.buildId; - - if (!buildId) { - throw new Error(`Performance metrics can't be reported without a buildId`); - } - - return !!(await this.req({ - auth: true, - path: `/v1/performance_metrics_report?buildId=${buildId}`, - body: { - metrics - }, - bodyDesc: `performance metrics: ${metrics}` - })); - } - /** - * In order to allow this code to run before @kbn/utils is built, @kbn/pm will pass - * in the upstreamBranch when calling the timings() method. Outside of @kbn/pm - * we rely on @kbn/utils to find the package.json file. - */ - - - getUpstreamBranch() { - // specify the module id in a way that will keep webpack from bundling extra code into @kbn/pm - const hideFromWebpack = ['@', 'kbn/utils']; // eslint-disable-next-line @typescript-eslint/no-var-requires - - const { - kibanaPackageJson - } = __webpack_require__("../../node_modules/@kbn/ci-stats-reporter/target_node sync recursive")(hideFromWebpack.join('')); - - return kibanaPackageJson.branch; - } - /** - * In order to allow this code to run before @kbn/utils is built, @kbn/pm will pass - * in the kibanaUuid when calling the timings() method. Outside of @kbn/pm - * we rely on @kbn/utils to find the repo root. - */ - - - getKibanaUuid() { - // specify the module id in a way that will keep webpack from bundling extra code into @kbn/pm - const hideFromWebpack = ['@', 'kbn/utils']; // eslint-disable-next-line @typescript-eslint/no-var-requires - - const { - REPO_ROOT - } = __webpack_require__("../../node_modules/@kbn/ci-stats-reporter/target_node sync recursive")(hideFromWebpack.join('')); - - try { - return _fs.default.readFileSync(_path.default.resolve(REPO_ROOT, 'data/uuid'), 'utf-8').trim(); - } catch (error) { - if (error.code === 'ENOENT') { - return undefined; - } - - throw error; - } - } - - async req({ - auth, - body, - bodyDesc, - path, - query, - timeout = 60 * SECOND - }) { - let attempt = 0; - const maxAttempts = 5; - let headers; - - if (auth && this.config) { - headers = { - Authorization: `token ${this.config.apiToken}` - }; - } else if (auth) { - throw new Error('this.req() shouldnt be called with auth=true if this.config is not defined'); - } - - while (true) { - attempt += 1; - - try { - const resp = await _axios.default.request({ - method: 'POST', - url: path, - baseURL: BASE_URL, - headers, - data: body, - params: query, - adapter: _http.default, - // if it can be serialized into a string, send it - maxBodyLength: Infinity, - maxContentLength: Infinity, - timeout - }); - return resp.data; - } catch (error) { - var _error$response; - - if (!(error !== null && error !== void 0 && error.request)) { - // not an axios error, must be a usage error that we should notify user about - throw error; - } - - if (error !== null && error !== void 0 && error.response && error.response.status < 500) { - // error response from service was received so warn the user and move on - this.log.warning(`error reporting ${bodyDesc} [status=${error.response.status}] [resp=${(0, _util.inspect)(error.response.data)}]`); - return; - } - - if (attempt === maxAttempts) { - this.log.warning(`unable to report ${bodyDesc}, failed to reach ci-stats service too many times`); - return; - } // we failed to reach the backend and we have remaining attempts, lets retry after a short delay - - - const reason = error !== null && error !== void 0 && (_error$response = error.response) !== null && _error$response !== void 0 && _error$response.status ? `${error.response.status} response` : 'no response'; - const seconds = attempt * 10; - this.log.warning(`failed to reach ci-stats service, retrying in ${seconds} seconds, [reason=${reason}], [error=${error.message}]`); - await new Promise(resolve => setTimeout(resolve, seconds * 1000)); - } - } - } - -} - -exports.CiStatsReporter = CiStatsReporter; - -/***/ }), - -/***/ "../../node_modules/@kbn/ci-stats-reporter/target_node/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -Object.defineProperty(exports, "CiStatsReporter", { - enumerable: true, - get: function () { - return _ci_stats_reporter.CiStatsReporter; - } -}); -Object.defineProperty(exports, "getTimeReporter", { - enumerable: true, - get: function () { - return _report_time.getTimeReporter; - } -}); - -var _ci_stats_reporter = __webpack_require__("../../node_modules/@kbn/ci-stats-reporter/target_node/ci_stats_reporter.js"); - -var _report_time = __webpack_require__("../../node_modules/@kbn/ci-stats-reporter/target_node/report_time.js"); - -/***/ }), - -/***/ "../../node_modules/@kbn/ci-stats-reporter/target_node/report_time.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.getTimeReporter = void 0; - -var _ci_stats_reporter = __webpack_require__("../../node_modules/@kbn/ci-stats-reporter/target_node/ci_stats_reporter.js"); - -/* - * 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. - */ -const getTimeReporter = (log, group) => { - const reporter = _ci_stats_reporter.CiStatsReporter.fromEnv(log); - - return async (startTime, id, meta) => { - await reporter.timings({ - timings: [{ - group, - id, - ms: Date.now() - startTime, - meta - }] - }); - }; -}; - -exports.getTimeReporter = getTimeReporter; - -/***/ }), - -/***/ "../../node_modules/@kbn/plugin-discovery/target_node/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); - -var _parse_kibana_platform_plugin = __webpack_require__("../../node_modules/@kbn/plugin-discovery/target_node/parse_kibana_platform_plugin.js"); - -Object.keys(_parse_kibana_platform_plugin).forEach(function (key) { - if (key === "default" || key === "__esModule") return; - if (key in exports && exports[key] === _parse_kibana_platform_plugin[key]) return; - Object.defineProperty(exports, key, { - enumerable: true, - get: function () { - return _parse_kibana_platform_plugin[key]; - } - }); -}); - -var _plugin_search_paths = __webpack_require__("../../node_modules/@kbn/plugin-discovery/target_node/plugin_search_paths.js"); - -Object.keys(_plugin_search_paths).forEach(function (key) { - if (key === "default" || key === "__esModule") return; - if (key in exports && exports[key] === _plugin_search_paths[key]) return; - Object.defineProperty(exports, key, { - enumerable: true, - get: function () { - return _plugin_search_paths[key]; - } - }); -}); - -var _simple_kibana_platform_plugin_discovery = __webpack_require__("../../node_modules/@kbn/plugin-discovery/target_node/simple_kibana_platform_plugin_discovery.js"); - -Object.keys(_simple_kibana_platform_plugin_discovery).forEach(function (key) { - if (key === "default" || key === "__esModule") return; - if (key in exports && exports[key] === _simple_kibana_platform_plugin_discovery[key]) return; - Object.defineProperty(exports, key, { - enumerable: true, - get: function () { - return _simple_kibana_platform_plugin_discovery[key]; - } - }); -}); - -/***/ }), - -/***/ "../../node_modules/@kbn/plugin-discovery/target_node/parse_kibana_platform_plugin.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.parseKibanaPlatformPlugin = parseKibanaPlatformPlugin; - -var _path = _interopRequireDefault(__webpack_require__("path")); - -var _loadJsonFile = _interopRequireDefault(__webpack_require__("../../node_modules/load-json-file/index.js")); - -/* - * 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. - */ -function isValidDepsDeclaration(input, type) { - if (typeof input === 'undefined') return []; - - if (Array.isArray(input) && input.every(i => typeof i === 'string')) { - return input; - } - - throw new TypeError(`The "${type}" in plugin manifest should be an array of strings.`); -} - -function parseKibanaPlatformPlugin(manifestPath) { - if (!_path.default.isAbsolute(manifestPath)) { - throw new TypeError('expected new platform manifest path to be absolute'); - } - - const manifest = _loadJsonFile.default.sync(manifestPath); - - if (!manifest || typeof manifest !== 'object' || Array.isArray(manifest)) { - throw new TypeError('expected new platform plugin manifest to be a JSON encoded object'); - } - - if (typeof manifest.id !== 'string') { - throw new TypeError('expected new platform plugin manifest to have a string id'); - } - - if (typeof manifest.version !== 'string') { - throw new TypeError('expected new platform plugin manifest to have a string version'); - } - - if (!manifest.owner || typeof manifest.owner.name !== 'string') { - throw new TypeError(`Expected plugin ${manifest.id} manifest to have an owner with name specified (${manifestPath})`); - } - - return { - directory: _path.default.dirname(manifestPath), - manifestPath, - manifest: { ...manifest, - ui: !!manifest.ui, - server: !!manifest.server, - id: manifest.id, - version: manifest.version, - kibanaVersion: manifest.kibanaVersion || manifest.version, - serviceFolders: manifest.serviceFolders || [], - owner: manifest.owner, - description: manifest.description, - enabledOnAnonymousPages: Boolean(manifest.enabledOnAnonymousPages), - requiredPlugins: isValidDepsDeclaration(manifest.requiredPlugins, 'requiredPlugins'), - optionalPlugins: isValidDepsDeclaration(manifest.optionalPlugins, 'optionalPlugins'), - requiredBundles: isValidDepsDeclaration(manifest.requiredBundles, 'requiredBundles'), - extraPublicDirs: isValidDepsDeclaration(manifest.extraPublicDirs, 'extraPublicDirs') - } - }; -} - -/***/ }), - -/***/ "../../node_modules/@kbn/plugin-discovery/target_node/plugin_search_paths.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.getPluginSearchPaths = getPluginSearchPaths; - -var _path = __webpack_require__("path"); - -/* - * 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. - */ -function getPluginSearchPaths({ - rootDir, - oss, - examples, - testPlugins -}) { - return [(0, _path.resolve)(rootDir, 'src', 'plugins'), ...(oss ? [] : [(0, _path.resolve)(rootDir, 'x-pack', 'plugins')]), (0, _path.resolve)(rootDir, 'plugins'), ...(examples ? [(0, _path.resolve)(rootDir, 'examples')] : []), ...(examples && !oss ? [(0, _path.resolve)(rootDir, 'x-pack', 'examples')] : []), (0, _path.resolve)(rootDir, '..', 'kibana-extra'), ...(testPlugins ? [(0, _path.resolve)(rootDir, 'test/analytics/fixtures/plugins'), (0, _path.resolve)(rootDir, 'test/plugin_functional/plugins'), (0, _path.resolve)(rootDir, 'test/interpreter_functional/plugins'), (0, _path.resolve)(rootDir, 'test/common/fixtures/plugins')] : []), ...(testPlugins && !oss ? [(0, _path.resolve)(rootDir, 'x-pack/test/plugin_functional/plugins'), (0, _path.resolve)(rootDir, 'x-pack/test/functional_with_es_ssl/fixtures/plugins'), (0, _path.resolve)(rootDir, 'x-pack/test/alerting_api_integration/plugins'), (0, _path.resolve)(rootDir, 'x-pack/test/plugin_api_integration/plugins'), (0, _path.resolve)(rootDir, 'x-pack/test/plugin_api_perf/plugins'), (0, _path.resolve)(rootDir, 'x-pack/test/licensing_plugin/plugins'), (0, _path.resolve)(rootDir, 'x-pack/test/usage_collection/plugins'), (0, _path.resolve)(rootDir, 'x-pack/test/security_functional/fixtures/common')] : [])]; -} - -/***/ }), - -/***/ "../../node_modules/@kbn/plugin-discovery/target_node/simple_kibana_platform_plugin_discovery.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.simpleKibanaPlatformPluginDiscovery = simpleKibanaPlatformPluginDiscovery; - -var _path = _interopRequireDefault(__webpack_require__("path")); - -var _globby = _interopRequireDefault(__webpack_require__("../../node_modules/globby/index.js")); - -var _normalizePath = _interopRequireDefault(__webpack_require__("../../node_modules/normalize-path/index.js")); - -var _parse_kibana_platform_plugin = __webpack_require__("../../node_modules/@kbn/plugin-discovery/target_node/parse_kibana_platform_plugin.js"); - -/* - * 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. - */ - -/** - * Helper to find the new platform plugins. - */ -function simpleKibanaPlatformPluginDiscovery(scanDirs, pluginPaths) { - const patterns = Array.from(new Set([// find kibana.json files up to 5 levels within the scan dir - ...scanDirs.reduce((acc, dir) => [...acc, _path.default.resolve(dir, '*/kibana.json'), _path.default.resolve(dir, '*/*/kibana.json'), _path.default.resolve(dir, '*/*/*/kibana.json'), _path.default.resolve(dir, '*/*/*/*/kibana.json'), _path.default.resolve(dir, '*/*/*/*/*/kibana.json')], []), ...pluginPaths.map(path => _path.default.resolve(path, `kibana.json`))])).map(path => (0, _normalizePath.default)(path)); - - const manifestPaths = _globby.default.sync(patterns, { - absolute: true - }).map(path => // absolute paths returned from globby are using normalize or - // something so the path separators are `/` even on windows, - // Path.resolve solves this - _path.default.resolve(path)); - - return manifestPaths.map(_parse_kibana_platform_plugin.parseKibanaPlatformPlugin); -} - -/***/ }), - -/***/ "../../node_modules/@kbn/sort-package-json/target_node/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.sortPackageJson = sortPackageJson; - -var _sortPackageJson = _interopRequireDefault(__webpack_require__("../../node_modules/sort-package-json/index.js")); - -/* - * 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. - */ -function sortPackageJson(json) { - return JSON.stringify((0, _sortPackageJson.default)(JSON.parse(json), { - // top level keys in the order they were written when this was implemented - sortOrder: ['name', 'description', 'keywords', 'private', 'version', 'branch', 'main', 'browser', 'types', 'tsdocMetadata', 'build', 'homepage', 'bugs', 'license', 'kibana', 'author', 'scripts', 'repository', 'engines', 'resolutions'] - }), null, 2) + '\n'; -} - -/***/ }), - -/***/ "../../node_modules/@kbn/stdio-dev-helpers/target_node/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -Object.defineProperty(exports, "observeLines", { - enumerable: true, - get: function () { - return _observe_lines.observeLines; - } -}); -Object.defineProperty(exports, "observeReadable", { - enumerable: true, - get: function () { - return _observe_readable.observeReadable; - } -}); - -var _observe_lines = __webpack_require__("../../node_modules/@kbn/stdio-dev-helpers/target_node/observe_lines.js"); - -var _observe_readable = __webpack_require__("../../node_modules/@kbn/stdio-dev-helpers/target_node/observe_readable.js"); - -/***/ }), - -/***/ "../../node_modules/@kbn/stdio-dev-helpers/target_node/observe_lines.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.observeLines = observeLines; - -var Rx = _interopRequireWildcard(__webpack_require__("../../node_modules/rxjs/dist/esm5/index.js")); - -var _observe_readable = __webpack_require__("../../node_modules/@kbn/stdio-dev-helpers/target_node/observe_readable.js"); - -function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); } - -function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; } - -/* - * 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. - */ -const SEP = /\r?\n/; - -/** - * Creates an Observable from a Readable Stream that: - * - splits data from `readable` into lines - * - completes when `readable` emits "end" - * - fails if `readable` emits "errors" - * - * @param {ReadableStream} readable - * @return {Rx.Observable} - */ -function observeLines(readable) { - const done$ = (0, _observe_readable.observeReadable)(readable).pipe(Rx.share()); - const scan$ = Rx.fromEvent(readable, 'data').pipe(Rx.scan(({ - buffer - }, chunk) => { - buffer += chunk; - const lines = []; - - while (true) { - const match = buffer.match(SEP); - - if (!match || match.index === undefined) { - break; - } - - lines.push(buffer.slice(0, match.index)); - buffer = buffer.slice(match.index + match[0].length); - } - - return { - buffer, - lines - }; - }, { - buffer: '' - }), // stop if done completes or errors - Rx.takeUntil(done$.pipe(Rx.materialize())), Rx.share()); - return Rx.merge( // use done$ to provide completion/errors - done$, // merge in the "lines" from each step - scan$.pipe(Rx.mergeMap(({ - lines - }) => lines || [])), // inject the "unsplit" data at the end - scan$.pipe(Rx.takeLast(1), Rx.mergeMap(({ - buffer - }) => buffer ? [buffer] : []))); -} - -/***/ }), - -/***/ "../../node_modules/@kbn/stdio-dev-helpers/target_node/observe_readable.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.observeReadable = observeReadable; - -var Rx = _interopRequireWildcard(__webpack_require__("../../node_modules/rxjs/dist/esm5/index.js")); - -function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); } - -function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; } - -/* - * 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. - */ - -/** - * Produces an Observable from a ReadableSteam that: - * - completes on the first "end" event - * - fails on the first "error" event - */ -function observeReadable(readable) { - return Rx.race(Rx.fromEvent(readable, 'end').pipe(Rx.first(), Rx.ignoreElements()), Rx.fromEvent(readable, 'error').pipe(Rx.first(), Rx.map(err => { - throw err; - }))); -} - -/***/ }), - -/***/ "../../node_modules/@kbn/tooling-log/target_node/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -Object.defineProperty(exports, "DEFAULT_LOG_LEVEL", { - enumerable: true, - get: function () { - return _log_levels.DEFAULT_LOG_LEVEL; - } -}); -Object.defineProperty(exports, "LOG_LEVEL_FLAGS", { - enumerable: true, - get: function () { - return _log_levels.LOG_LEVEL_FLAGS; - } -}); -Object.defineProperty(exports, "ToolingLog", { - enumerable: true, - get: function () { - return _tooling_log.ToolingLog; - } -}); -Object.defineProperty(exports, "ToolingLogCollectingWriter", { - enumerable: true, - get: function () { - return _tooling_log_collecting_writer.ToolingLogCollectingWriter; - } -}); -Object.defineProperty(exports, "ToolingLogTextWriter", { - enumerable: true, - get: function () { - return _tooling_log_text_writer.ToolingLogTextWriter; - } -}); -Object.defineProperty(exports, "getLogLevelFlagsHelp", { - enumerable: true, - get: function () { - return _log_levels.getLogLevelFlagsHelp; - } -}); -Object.defineProperty(exports, "parseLogLevel", { - enumerable: true, - get: function () { - return _log_levels.parseLogLevel; - } -}); -Object.defineProperty(exports, "pickLevelFromFlags", { - enumerable: true, - get: function () { - return _log_levels.pickLevelFromFlags; - } -}); - -var _tooling_log = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/tooling_log.js"); - -var _tooling_log_text_writer = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/tooling_log_text_writer.js"); - -var _log_levels = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/log_levels.js"); - -var _tooling_log_collecting_writer = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/tooling_log_collecting_writer.js"); - -/***/ }), - -/***/ "../../node_modules/@kbn/tooling-log/target_node/log_levels.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.LOG_LEVEL_FLAGS = exports.DEFAULT_LOG_LEVEL = void 0; -exports.getLogLevelFlagsHelp = getLogLevelFlagsHelp; -exports.parseLogLevel = parseLogLevel; -exports.pickLevelFromFlags = pickLevelFromFlags; - -/* - * 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. - */ -const LEVELS = ['silent', 'error', 'warning', 'success', 'info', 'debug', 'verbose']; -const DEFAULT_LOG_LEVEL = 'info'; -exports.DEFAULT_LOG_LEVEL = DEFAULT_LOG_LEVEL; - -function pickLevelFromFlags(flags, options = {}) { - if (flags.verbose) return 'verbose'; - if (flags.debug) return 'debug'; - if (flags.info) return 'info'; - if (flags.quiet) return 'error'; - if (flags.silent) return 'silent'; - return options.default || DEFAULT_LOG_LEVEL; -} - -const LOG_LEVEL_FLAGS = [{ - name: 'verbose', - help: '--verbose, -v Log verbosely' -}, { - name: 'info', - help: "--info Don't log debug messages" -}, { - name: 'debug', - help: '--debug Log debug messages (less than verbose)' -}, { - name: 'quiet', - help: '--quiet Only log errors' -}, { - name: 'silent', - help: "--silent Don't log anything" -}]; -exports.LOG_LEVEL_FLAGS = LOG_LEVEL_FLAGS; - -function getLogLevelFlagsHelp(defaultLogLevel = DEFAULT_LOG_LEVEL) { - return LOG_LEVEL_FLAGS.filter(({ - name - }) => name !== defaultLogLevel).map(({ - help - }) => help).join('\n'); -} - -function parseLogLevel(name) { - const i = LEVELS.indexOf(name); - - if (i === -1) { - const msg = `Invalid log level "${name}" ` + `(expected one of ${LEVELS.join(',')})`; - throw new Error(msg); - } - - const flags = {}; - LEVELS.forEach((level, levelI) => { - flags[level] = levelI <= i; - }); - return { - name, - flags: flags - }; -} - -/***/ }), - -/***/ "../../node_modules/@kbn/tooling-log/target_node/tooling_log.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.ToolingLog = void 0; - -var _defineProperty2 = _interopRequireDefault(__webpack_require__("../../node_modules/@babel/runtime/helpers/defineProperty.js")); - -var Rx = _interopRequireWildcard(__webpack_require__("../../node_modules/rxjs/dist/esm5/index.js")); - -var _tooling_log_text_writer = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/tooling_log_text_writer.js"); - -function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); } - -function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; } - -/* - * 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. - */ -class ToolingLog { - constructor(writerConfig, options) { - (0, _defineProperty2.default)(this, "indentWidth$", void 0); - (0, _defineProperty2.default)(this, "writers$", void 0); - (0, _defineProperty2.default)(this, "written$", void 0); - (0, _defineProperty2.default)(this, "type", void 0); - this.indentWidth$ = options !== null && options !== void 0 && options.parent ? options.parent.indentWidth$ : new Rx.BehaviorSubject(0); - this.writers$ = options !== null && options !== void 0 && options.parent ? options.parent.writers$ : new Rx.BehaviorSubject([]); - - if (!(options !== null && options !== void 0 && options.parent) && writerConfig) { - this.writers$.next([new _tooling_log_text_writer.ToolingLogTextWriter(writerConfig)]); - } - - this.written$ = options !== null && options !== void 0 && options.parent ? options.parent.written$ : new Rx.Subject(); - this.type = options === null || options === void 0 ? void 0 : options.type; - } - /** - * Get the current indentation level of the ToolingLog - */ - - - getIndent() { - return this.indentWidth$.getValue(); - } - /** - * Indent the output of the ToolingLog by some character (4 is a good choice usually). - * - * If provided, the `block` function will be executed and once it's promise is resolved - * or rejected the indentation will be reset to its original state. - * - * @param delta the number of spaces to increase/decrease the indentation - * @param block a function to run and reset any indentation changes after - */ - - - indent(delta = 0, block) { - const originalWidth = this.indentWidth$.getValue(); - this.indentWidth$.next(Math.max(originalWidth + delta, 0)); - - if (!block) { - return; - } - - const maybePromise = block(); - - if (typeof maybePromise === 'object' && maybePromise && typeof maybePromise.then === 'function') { - return (async () => { - try { - return await maybePromise; - } finally { - this.indentWidth$.next(originalWidth); - } - })(); - } - - this.indentWidth$.next(originalWidth); - return maybePromise; - } - - verbose(...args) { - this.sendToWriters('verbose', args); - } - - debug(...args) { - this.sendToWriters('debug', args); - } - - info(...args) { - this.sendToWriters('info', args); - } - - success(...args) { - this.sendToWriters('success', args); - } - - warning(...args) { - this.sendToWriters('warning', args); - } - - error(error) { - this.sendToWriters('error', [error]); - } - - write(...args) { - this.sendToWriters('write', args); - } - - getWriters() { - return [...this.writers$.getValue()]; - } - - setWriters(writers) { - this.writers$.next([...writers]); - } - - getWritten$() { - return this.written$.asObservable(); - } - /** - * Create a new ToolingLog which sets a different "type", allowing messages to be filtered out by "source" - * @param type A string that will be passed along with messages from this logger which can be used to filter messages with `ignoreSources` - */ - - - withType(type) { - return new ToolingLog(undefined, { - type, - parent: this - }); - } - - sendToWriters(type, args) { - const indent = this.indentWidth$.getValue(); - const writers = this.writers$.getValue(); - const msg = { - type, - indent, - source: this.type, - args - }; - let written = false; - - for (const writer of writers) { - if (writer.write(msg)) { - written = true; - } - } - - if (written) { - this.written$.next(msg); - } - } - -} - -exports.ToolingLog = ToolingLog; - -/***/ }), - -/***/ "../../node_modules/@kbn/tooling-log/target_node/tooling_log_collecting_writer.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.ToolingLogCollectingWriter = void 0; - -var _defineProperty2 = _interopRequireDefault(__webpack_require__("../../node_modules/@babel/runtime/helpers/defineProperty.js")); - -var _tooling_log_text_writer = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/tooling_log_text_writer.js"); - -/* - * 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. - */ -class ToolingLogCollectingWriter extends _tooling_log_text_writer.ToolingLogTextWriter { - constructor(level = 'verbose') { - super({ - level, - writeTo: { - write: msg => { - // trim trailing new line - this.messages.push(msg.slice(0, -1)); - } - } - }); - (0, _defineProperty2.default)(this, "messages", []); - } - /** - * Called by ToolingLog, extends messages with the source if message includes one. - */ - - - write(msg) { - if (msg.source) { - return super.write({ ...msg, - args: [`source[${msg.source}]`, ...msg.args] - }); - } - - return super.write(msg); - } - -} - -exports.ToolingLogCollectingWriter = ToolingLogCollectingWriter; - -/***/ }), - -/***/ "../../node_modules/@kbn/tooling-log/target_node/tooling_log_text_writer.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var _interopRequireDefault = __webpack_require__("../../node_modules/@babel/runtime/helpers/interopRequireDefault.js"); - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.ToolingLogTextWriter = void 0; - -var _defineProperty2 = _interopRequireDefault(__webpack_require__("../../node_modules/@babel/runtime/helpers/defineProperty.js")); - -var _util = __webpack_require__("util"); - -var _chalk = _interopRequireDefault(__webpack_require__("../../node_modules/chalk/source/index.js")); - -var _log_levels = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/log_levels.js"); - -/* - * 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. - */ -const { - magentaBright, - yellow, - red, - blue, - green, - dim -} = _chalk.default; -const PREFIX_INDENT = ' '.repeat(6); -const MSG_PREFIXES = { - verbose: ` ${magentaBright('sill')} `, - debug: ` ${dim('debg')} `, - info: ` ${blue('info')} `, - success: ` ${green('succ')} `, - warning: ` ${yellow('warn')} `, - error: `${red('ERROR')} ` -}; - -const has = (obj, key) => obj.hasOwnProperty(key); - -function shouldWriteType(level, type) { - if (type === 'write') { - return level.name !== 'silent'; - } - - return Boolean(level.flags[type === 'success' ? 'info' : type]); -} - -function stringifyError(error) { - if (typeof error !== 'string' && !(error instanceof Error)) { - error = new Error(`"${error}" thrown`); - } - - if (typeof error === 'string') { - return error; - } - - return error.stack || error.message || error; -} - -class ToolingLogTextWriter { - constructor(config) { - (0, _defineProperty2.default)(this, "level", void 0); - (0, _defineProperty2.default)(this, "writeTo", void 0); - (0, _defineProperty2.default)(this, "ignoreSources", void 0); - this.level = (0, _log_levels.parseLogLevel)(config.level); - this.writeTo = config.writeTo; - this.ignoreSources = config.ignoreSources; - - if (!this.writeTo || typeof this.writeTo.write !== 'function') { - throw new Error('ToolingLogTextWriter requires the `writeTo` option be set to a stream (like process.stdout)'); - } - } - - write(msg) { - if (!shouldWriteType(this.level, msg.type)) { - return false; - } - - if (this.ignoreSources && msg.source && this.ignoreSources.includes(msg.source)) { - if (msg.type === 'write') { - const txt = (0, _util.format)(msg.args[0], ...msg.args.slice(1)); // Ensure that Elasticsearch deprecation log messages from Kibana aren't ignored - - if (!/elasticsearch\.deprecation/.test(txt)) { - return false; - } - } else { - return false; - } - } - - const prefix = has(MSG_PREFIXES, msg.type) ? MSG_PREFIXES[msg.type] : ''; - ToolingLogTextWriter.write(this.writeTo, prefix, msg); - return true; - } - - static write(writeTo, prefix, msg) { - const txt = msg.type === 'error' ? stringifyError(msg.args[0]) : (0, _util.format)(msg.args[0], ...msg.args.slice(1)); - (prefix + txt).split('\n').forEach((line, i) => { - let lineIndent = ''; - - if (msg.indent > 0) { - // if we are indenting write some spaces followed by a symbol - lineIndent += ' '.repeat(msg.indent - 1); - lineIndent += line.startsWith('-') ? '└' : '│'; - } - - if (line && prefix && i > 0) { - // apply additional indentation to lines after - // the first if this message gets a prefix - lineIndent += PREFIX_INDENT; - } - - writeTo.write(`${lineIndent}${line}\n`); - }); - } - -} - -exports.ToolingLogTextWriter = ToolingLogTextWriter; - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/adapters/fs.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fs = __webpack_require__("fs"); -exports.FILE_SYSTEM_ADAPTER = { - lstat: fs.lstat, - stat: fs.stat, - lstatSync: fs.lstatSync, - statSync: fs.statSync, - readdir: fs.readdir, - readdirSync: fs.readdirSync -}; -function createFileSystemAdapter(fsMethods) { - if (fsMethods === undefined) { - return exports.FILE_SYSTEM_ADAPTER; - } - return Object.assign(Object.assign({}, exports.FILE_SYSTEM_ADAPTER), fsMethods); -} -exports.createFileSystemAdapter = createFileSystemAdapter; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/constants.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const NODE_PROCESS_VERSION_PARTS = process.versions.node.split('.'); -const MAJOR_VERSION = parseInt(NODE_PROCESS_VERSION_PARTS[0], 10); -const MINOR_VERSION = parseInt(NODE_PROCESS_VERSION_PARTS[1], 10); -const SUPPORTED_MAJOR_VERSION = 10; -const SUPPORTED_MINOR_VERSION = 10; -const IS_MATCHED_BY_MAJOR = MAJOR_VERSION > SUPPORTED_MAJOR_VERSION; -const IS_MATCHED_BY_MAJOR_AND_MINOR = MAJOR_VERSION === SUPPORTED_MAJOR_VERSION && MINOR_VERSION >= SUPPORTED_MINOR_VERSION; -/** - * IS `true` for Node.js 10.10 and greater. - */ -exports.IS_SUPPORT_READDIR_WITH_FILE_TYPES = IS_MATCHED_BY_MAJOR || IS_MATCHED_BY_MAJOR_AND_MINOR; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const async = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/providers/async.js"); -const sync = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/providers/sync.js"); -const settings_1 = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/settings.js"); -exports.Settings = settings_1.default; -function scandir(path, optionsOrSettingsOrCallback, callback) { - if (typeof optionsOrSettingsOrCallback === 'function') { - return async.read(path, getSettings(), optionsOrSettingsOrCallback); - } - async.read(path, getSettings(optionsOrSettingsOrCallback), callback); -} -exports.scandir = scandir; -function scandirSync(path, optionsOrSettings) { - const settings = getSettings(optionsOrSettings); - return sync.read(path, settings); -} -exports.scandirSync = scandirSync; -function getSettings(settingsOrOptions = {}) { - if (settingsOrOptions instanceof settings_1.default) { - return settingsOrOptions; - } - return new settings_1.default(settingsOrOptions); -} - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/providers/async.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fsStat = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/index.js"); -const rpl = __webpack_require__("../../node_modules/run-parallel/index.js"); -const constants_1 = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/constants.js"); -const utils = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/utils/index.js"); -function read(directory, settings, callback) { - if (!settings.stats && constants_1.IS_SUPPORT_READDIR_WITH_FILE_TYPES) { - return readdirWithFileTypes(directory, settings, callback); - } - return readdir(directory, settings, callback); -} -exports.read = read; -function readdirWithFileTypes(directory, settings, callback) { - settings.fs.readdir(directory, { withFileTypes: true }, (readdirError, dirents) => { - if (readdirError !== null) { - return callFailureCallback(callback, readdirError); - } - const entries = dirents.map((dirent) => ({ - dirent, - name: dirent.name, - path: `${directory}${settings.pathSegmentSeparator}${dirent.name}` - })); - if (!settings.followSymbolicLinks) { - return callSuccessCallback(callback, entries); - } - const tasks = entries.map((entry) => makeRplTaskEntry(entry, settings)); - rpl(tasks, (rplError, rplEntries) => { - if (rplError !== null) { - return callFailureCallback(callback, rplError); - } - callSuccessCallback(callback, rplEntries); - }); - }); -} -exports.readdirWithFileTypes = readdirWithFileTypes; -function makeRplTaskEntry(entry, settings) { - return (done) => { - if (!entry.dirent.isSymbolicLink()) { - return done(null, entry); - } - settings.fs.stat(entry.path, (statError, stats) => { - if (statError !== null) { - if (settings.throwErrorOnBrokenSymbolicLink) { - return done(statError); - } - return done(null, entry); - } - entry.dirent = utils.fs.createDirentFromStats(entry.name, stats); - return done(null, entry); - }); - }; -} -function readdir(directory, settings, callback) { - settings.fs.readdir(directory, (readdirError, names) => { - if (readdirError !== null) { - return callFailureCallback(callback, readdirError); - } - const filepaths = names.map((name) => `${directory}${settings.pathSegmentSeparator}${name}`); - const tasks = filepaths.map((filepath) => { - return (done) => fsStat.stat(filepath, settings.fsStatSettings, done); - }); - rpl(tasks, (rplError, results) => { - if (rplError !== null) { - return callFailureCallback(callback, rplError); - } - const entries = []; - names.forEach((name, index) => { - const stats = results[index]; - const entry = { - name, - path: filepaths[index], - dirent: utils.fs.createDirentFromStats(name, stats) - }; - if (settings.stats) { - entry.stats = stats; - } - entries.push(entry); - }); - callSuccessCallback(callback, entries); - }); - }); -} -exports.readdir = readdir; -function callFailureCallback(callback, error) { - callback(error); -} -function callSuccessCallback(callback, result) { - callback(null, result); -} - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/providers/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fsStat = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/index.js"); -const constants_1 = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/constants.js"); -const utils = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/utils/index.js"); -function read(directory, settings) { - if (!settings.stats && constants_1.IS_SUPPORT_READDIR_WITH_FILE_TYPES) { - return readdirWithFileTypes(directory, settings); - } - return readdir(directory, settings); -} -exports.read = read; -function readdirWithFileTypes(directory, settings) { - const dirents = settings.fs.readdirSync(directory, { withFileTypes: true }); - return dirents.map((dirent) => { - const entry = { - dirent, - name: dirent.name, - path: `${directory}${settings.pathSegmentSeparator}${dirent.name}` - }; - if (entry.dirent.isSymbolicLink() && settings.followSymbolicLinks) { - try { - const stats = settings.fs.statSync(entry.path); - entry.dirent = utils.fs.createDirentFromStats(entry.name, stats); - } - catch (error) { - if (settings.throwErrorOnBrokenSymbolicLink) { - throw error; - } - } - } - return entry; - }); -} -exports.readdirWithFileTypes = readdirWithFileTypes; -function readdir(directory, settings) { - const names = settings.fs.readdirSync(directory); - return names.map((name) => { - const entryPath = `${directory}${settings.pathSegmentSeparator}${name}`; - const stats = fsStat.statSync(entryPath, settings.fsStatSettings); - const entry = { - name, - path: entryPath, - dirent: utils.fs.createDirentFromStats(name, stats) - }; - if (settings.stats) { - entry.stats = stats; - } - return entry; - }); -} -exports.readdir = readdir; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/settings.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const path = __webpack_require__("path"); -const fsStat = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/index.js"); -const fs = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/adapters/fs.js"); -class Settings { - constructor(_options = {}) { - this._options = _options; - this.followSymbolicLinks = this._getValue(this._options.followSymbolicLinks, false); - this.fs = fs.createFileSystemAdapter(this._options.fs); - this.pathSegmentSeparator = this._getValue(this._options.pathSegmentSeparator, path.sep); - this.stats = this._getValue(this._options.stats, false); - this.throwErrorOnBrokenSymbolicLink = this._getValue(this._options.throwErrorOnBrokenSymbolicLink, true); - this.fsStatSettings = new fsStat.Settings({ - followSymbolicLink: this.followSymbolicLinks, - fs: this.fs, - throwErrorOnBrokenSymbolicLink: this.throwErrorOnBrokenSymbolicLink - }); - } - _getValue(option, value) { - return option === undefined ? value : option; - } -} -exports.default = Settings; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/utils/fs.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -class DirentFromStats { - constructor(name, stats) { - this.name = name; - this.isBlockDevice = stats.isBlockDevice.bind(stats); - this.isCharacterDevice = stats.isCharacterDevice.bind(stats); - this.isDirectory = stats.isDirectory.bind(stats); - this.isFIFO = stats.isFIFO.bind(stats); - this.isFile = stats.isFile.bind(stats); - this.isSocket = stats.isSocket.bind(stats); - this.isSymbolicLink = stats.isSymbolicLink.bind(stats); - } -} -function createDirentFromStats(name, stats) { - return new DirentFromStats(name, stats); -} -exports.createDirentFromStats = createDirentFromStats; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.scandir/out/utils/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fs = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/utils/fs.js"); -exports.fs = fs; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.stat/out/adapters/fs.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fs = __webpack_require__("fs"); -exports.FILE_SYSTEM_ADAPTER = { - lstat: fs.lstat, - stat: fs.stat, - lstatSync: fs.lstatSync, - statSync: fs.statSync -}; -function createFileSystemAdapter(fsMethods) { - if (fsMethods === undefined) { - return exports.FILE_SYSTEM_ADAPTER; - } - return Object.assign(Object.assign({}, exports.FILE_SYSTEM_ADAPTER), fsMethods); -} -exports.createFileSystemAdapter = createFileSystemAdapter; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.stat/out/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const async = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/providers/async.js"); -const sync = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/providers/sync.js"); -const settings_1 = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/settings.js"); -exports.Settings = settings_1.default; -function stat(path, optionsOrSettingsOrCallback, callback) { - if (typeof optionsOrSettingsOrCallback === 'function') { - return async.read(path, getSettings(), optionsOrSettingsOrCallback); - } - async.read(path, getSettings(optionsOrSettingsOrCallback), callback); -} -exports.stat = stat; -function statSync(path, optionsOrSettings) { - const settings = getSettings(optionsOrSettings); - return sync.read(path, settings); -} -exports.statSync = statSync; -function getSettings(settingsOrOptions = {}) { - if (settingsOrOptions instanceof settings_1.default) { - return settingsOrOptions; - } - return new settings_1.default(settingsOrOptions); -} - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.stat/out/providers/async.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -function read(path, settings, callback) { - settings.fs.lstat(path, (lstatError, lstat) => { - if (lstatError !== null) { - return callFailureCallback(callback, lstatError); - } - if (!lstat.isSymbolicLink() || !settings.followSymbolicLink) { - return callSuccessCallback(callback, lstat); - } - settings.fs.stat(path, (statError, stat) => { - if (statError !== null) { - if (settings.throwErrorOnBrokenSymbolicLink) { - return callFailureCallback(callback, statError); - } - return callSuccessCallback(callback, lstat); - } - if (settings.markSymbolicLink) { - stat.isSymbolicLink = () => true; - } - callSuccessCallback(callback, stat); - }); - }); -} -exports.read = read; -function callFailureCallback(callback, error) { - callback(error); -} -function callSuccessCallback(callback, result) { - callback(null, result); -} - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.stat/out/providers/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -function read(path, settings) { - const lstat = settings.fs.lstatSync(path); - if (!lstat.isSymbolicLink() || !settings.followSymbolicLink) { - return lstat; - } - try { - const stat = settings.fs.statSync(path); - if (settings.markSymbolicLink) { - stat.isSymbolicLink = () => true; - } - return stat; - } - catch (error) { - if (!settings.throwErrorOnBrokenSymbolicLink) { - return lstat; - } - throw error; - } -} -exports.read = read; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.stat/out/settings.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fs = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/adapters/fs.js"); -class Settings { - constructor(_options = {}) { - this._options = _options; - this.followSymbolicLink = this._getValue(this._options.followSymbolicLink, true); - this.fs = fs.createFileSystemAdapter(this._options.fs); - this.markSymbolicLink = this._getValue(this._options.markSymbolicLink, false); - this.throwErrorOnBrokenSymbolicLink = this._getValue(this._options.throwErrorOnBrokenSymbolicLink, true); - } - _getValue(option, value) { - return option === undefined ? value : option; - } -} -exports.default = Settings; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const async_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/providers/async.js"); -const stream_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/providers/stream.js"); -const sync_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/providers/sync.js"); -const settings_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/settings.js"); -exports.Settings = settings_1.default; -function walk(directory, optionsOrSettingsOrCallback, callback) { - if (typeof optionsOrSettingsOrCallback === 'function') { - return new async_1.default(directory, getSettings()).read(optionsOrSettingsOrCallback); - } - new async_1.default(directory, getSettings(optionsOrSettingsOrCallback)).read(callback); -} -exports.walk = walk; -function walkSync(directory, optionsOrSettings) { - const settings = getSettings(optionsOrSettings); - const provider = new sync_1.default(directory, settings); - return provider.read(); -} -exports.walkSync = walkSync; -function walkStream(directory, optionsOrSettings) { - const settings = getSettings(optionsOrSettings); - const provider = new stream_1.default(directory, settings); - return provider.read(); -} -exports.walkStream = walkStream; -function getSettings(settingsOrOptions = {}) { - if (settingsOrOptions instanceof settings_1.default) { - return settingsOrOptions; - } - return new settings_1.default(settingsOrOptions); -} - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/providers/async.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const async_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/async.js"); -class AsyncProvider { - constructor(_root, _settings) { - this._root = _root; - this._settings = _settings; - this._reader = new async_1.default(this._root, this._settings); - this._storage = new Set(); - } - read(callback) { - this._reader.onError((error) => { - callFailureCallback(callback, error); - }); - this._reader.onEntry((entry) => { - this._storage.add(entry); - }); - this._reader.onEnd(() => { - callSuccessCallback(callback, [...this._storage]); - }); - this._reader.read(); - } -} -exports.default = AsyncProvider; -function callFailureCallback(callback, error) { - callback(error); -} -function callSuccessCallback(callback, entries) { - callback(null, entries); -} - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/providers/stream.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const stream_1 = __webpack_require__("stream"); -const async_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/async.js"); -class StreamProvider { - constructor(_root, _settings) { - this._root = _root; - this._settings = _settings; - this._reader = new async_1.default(this._root, this._settings); - this._stream = new stream_1.Readable({ - objectMode: true, - read: () => { }, - destroy: this._reader.destroy.bind(this._reader) - }); - } - read() { - this._reader.onError((error) => { - this._stream.emit('error', error); - }); - this._reader.onEntry((entry) => { - this._stream.push(entry); - }); - this._reader.onEnd(() => { - this._stream.push(null); - }); - this._reader.read(); - return this._stream; - } -} -exports.default = StreamProvider; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/providers/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const sync_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/sync.js"); -class SyncProvider { - constructor(_root, _settings) { - this._root = _root; - this._settings = _settings; - this._reader = new sync_1.default(this._root, this._settings); - } - read() { - return this._reader.read(); - } -} -exports.default = SyncProvider; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/readers/async.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const events_1 = __webpack_require__("events"); -const fsScandir = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/index.js"); -const fastq = __webpack_require__("../../node_modules/fastq/queue.js"); -const common = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/common.js"); -const reader_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/reader.js"); -class AsyncReader extends reader_1.default { - constructor(_root, _settings) { - super(_root, _settings); - this._settings = _settings; - this._scandir = fsScandir.scandir; - this._emitter = new events_1.EventEmitter(); - this._queue = fastq(this._worker.bind(this), this._settings.concurrency); - this._isFatalError = false; - this._isDestroyed = false; - this._queue.drain = () => { - if (!this._isFatalError) { - this._emitter.emit('end'); - } - }; - } - read() { - this._isFatalError = false; - this._isDestroyed = false; - setImmediate(() => { - this._pushToQueue(this._root, this._settings.basePath); - }); - return this._emitter; - } - destroy() { - if (this._isDestroyed) { - throw new Error('The reader is already destroyed'); - } - this._isDestroyed = true; - this._queue.killAndDrain(); - } - onEntry(callback) { - this._emitter.on('entry', callback); - } - onError(callback) { - this._emitter.once('error', callback); - } - onEnd(callback) { - this._emitter.once('end', callback); - } - _pushToQueue(directory, base) { - const queueItem = { directory, base }; - this._queue.push(queueItem, (error) => { - if (error !== null) { - this._handleError(error); - } - }); - } - _worker(item, done) { - this._scandir(item.directory, this._settings.fsScandirSettings, (error, entries) => { - if (error !== null) { - return done(error, undefined); - } - for (const entry of entries) { - this._handleEntry(entry, item.base); - } - done(null, undefined); - }); - } - _handleError(error) { - if (!common.isFatalError(this._settings, error)) { - return; - } - this._isFatalError = true; - this._isDestroyed = true; - this._emitter.emit('error', error); - } - _handleEntry(entry, base) { - if (this._isDestroyed || this._isFatalError) { - return; - } - const fullpath = entry.path; - if (base !== undefined) { - entry.path = common.joinPathSegments(base, entry.name, this._settings.pathSegmentSeparator); - } - if (common.isAppliedFilter(this._settings.entryFilter, entry)) { - this._emitEntry(entry); - } - if (entry.dirent.isDirectory() && common.isAppliedFilter(this._settings.deepFilter, entry)) { - this._pushToQueue(fullpath, entry.path); - } - } - _emitEntry(entry) { - this._emitter.emit('entry', entry); - } -} -exports.default = AsyncReader; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/readers/common.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -function isFatalError(settings, error) { - if (settings.errorFilter === null) { - return true; - } - return !settings.errorFilter(error); -} -exports.isFatalError = isFatalError; -function isAppliedFilter(filter, value) { - return filter === null || filter(value); -} -exports.isAppliedFilter = isAppliedFilter; -function replacePathSegmentSeparator(filepath, separator) { - return filepath.split(/[\\/]/).join(separator); -} -exports.replacePathSegmentSeparator = replacePathSegmentSeparator; -function joinPathSegments(a, b, separator) { - if (a === '') { - return b; - } - return a + separator + b; -} -exports.joinPathSegments = joinPathSegments; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/readers/reader.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const common = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/common.js"); -class Reader { - constructor(_root, _settings) { - this._root = _root; - this._settings = _settings; - this._root = common.replacePathSegmentSeparator(_root, _settings.pathSegmentSeparator); - } -} -exports.default = Reader; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/readers/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fsScandir = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/index.js"); -const common = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/common.js"); -const reader_1 = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/readers/reader.js"); -class SyncReader extends reader_1.default { - constructor() { - super(...arguments); - this._scandir = fsScandir.scandirSync; - this._storage = new Set(); - this._queue = new Set(); - } - read() { - this._pushToQueue(this._root, this._settings.basePath); - this._handleQueue(); - return [...this._storage]; - } - _pushToQueue(directory, base) { - this._queue.add({ directory, base }); - } - _handleQueue() { - for (const item of this._queue.values()) { - this._handleDirectory(item.directory, item.base); - } - } - _handleDirectory(directory, base) { - try { - const entries = this._scandir(directory, this._settings.fsScandirSettings); - for (const entry of entries) { - this._handleEntry(entry, base); - } - } - catch (error) { - this._handleError(error); - } - } - _handleError(error) { - if (!common.isFatalError(this._settings, error)) { - return; - } - throw error; - } - _handleEntry(entry, base) { - const fullpath = entry.path; - if (base !== undefined) { - entry.path = common.joinPathSegments(base, entry.name, this._settings.pathSegmentSeparator); - } - if (common.isAppliedFilter(this._settings.entryFilter, entry)) { - this._pushToStorage(entry); - } - if (entry.dirent.isDirectory() && common.isAppliedFilter(this._settings.deepFilter, entry)) { - this._pushToQueue(fullpath, entry.path); - } - } - _pushToStorage(entry) { - this._storage.add(entry); - } -} -exports.default = SyncReader; - - -/***/ }), - -/***/ "../../node_modules/@nodelib/fs.walk/out/settings.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const path = __webpack_require__("path"); -const fsScandir = __webpack_require__("../../node_modules/@nodelib/fs.scandir/out/index.js"); -class Settings { - constructor(_options = {}) { - this._options = _options; - this.basePath = this._getValue(this._options.basePath, undefined); - this.concurrency = this._getValue(this._options.concurrency, Infinity); - this.deepFilter = this._getValue(this._options.deepFilter, null); - this.entryFilter = this._getValue(this._options.entryFilter, null); - this.errorFilter = this._getValue(this._options.errorFilter, null); - this.pathSegmentSeparator = this._getValue(this._options.pathSegmentSeparator, path.sep); - this.fsScandirSettings = new fsScandir.Settings({ - followSymbolicLinks: this._options.followSymbolicLinks, - fs: this._options.fs, - pathSegmentSeparator: this._options.pathSegmentSeparator, - stats: this._options.stats, - throwErrorOnBrokenSymbolicLink: this._options.throwErrorOnBrokenSymbolicLink - }); - } - _getValue(option, value) { - return option === undefined ? value : option; - } -} -exports.default = Settings; - - -/***/ }), - -/***/ "../../node_modules/@yarnpkg/lockfile/index.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = -/******/ (function(modules) { // webpackBootstrap -/******/ // The module cache -/******/ var installedModules = {}; -/******/ -/******/ // The require function -/******/ function __webpack_require__(moduleId) { -/******/ -/******/ // Check if module is in cache -/******/ if(installedModules[moduleId]) { -/******/ return installedModules[moduleId].exports; -/******/ } -/******/ // Create a new module (and put it into the cache) -/******/ var module = installedModules[moduleId] = { -/******/ i: moduleId, -/******/ l: false, -/******/ exports: {} -/******/ }; -/******/ -/******/ // Execute the module function -/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__); -/******/ -/******/ // Flag the module as loaded -/******/ module.l = true; -/******/ -/******/ // Return the exports of the module -/******/ return module.exports; -/******/ } -/******/ -/******/ -/******/ // expose the modules object (__webpack_modules__) -/******/ __webpack_require__.m = modules; -/******/ -/******/ // expose the module cache -/******/ __webpack_require__.c = installedModules; -/******/ -/******/ // identity function for calling harmony imports with the correct context -/******/ __webpack_require__.i = function(value) { return value; }; -/******/ -/******/ // define getter function for harmony exports -/******/ __webpack_require__.d = function(exports, name, getter) { -/******/ if(!__webpack_require__.o(exports, name)) { -/******/ Object.defineProperty(exports, name, { -/******/ configurable: false, -/******/ enumerable: true, -/******/ get: getter -/******/ }); -/******/ } -/******/ }; -/******/ -/******/ // getDefaultExport function for compatibility with non-harmony modules -/******/ __webpack_require__.n = function(module) { -/******/ var getter = module && module.__esModule ? -/******/ function getDefault() { return module['default']; } : -/******/ function getModuleExports() { return module; }; -/******/ __webpack_require__.d(getter, 'a', getter); -/******/ return getter; -/******/ }; -/******/ -/******/ // Object.prototype.hasOwnProperty.call -/******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); }; -/******/ -/******/ // __webpack_public_path__ -/******/ __webpack_require__.p = ""; -/******/ -/******/ // Load entry module and return exports -/******/ return __webpack_require__(__webpack_require__.s = 14); -/******/ }) -/************************************************************************/ -/******/ ([ -/* 0 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("path"); - -/***/ }), -/* 1 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -exports.__esModule = true; - -var _promise = __webpack_require__(173); - -var _promise2 = _interopRequireDefault(_promise); - -function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } - -exports.default = function (fn) { - return function () { - var gen = fn.apply(this, arguments); - return new _promise2.default(function (resolve, reject) { - function step(key, arg) { - try { - var info = gen[key](arg); - var value = info.value; - } catch (error) { - reject(error); - return; - } - - if (info.done) { - resolve(value); - } else { - return _promise2.default.resolve(value).then(function (value) { - step("next", value); - }, function (err) { - step("throw", err); - }); - } - } - - return step("next"); - }); - }; -}; - -/***/ }), -/* 2 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("util"); - -/***/ }), -/* 3 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("fs"); - -/***/ }), -/* 4 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -class MessageError extends Error { - constructor(msg, code) { - super(msg); - this.code = code; - } - -} - -exports.MessageError = MessageError; -class ProcessSpawnError extends MessageError { - constructor(msg, code, process) { - super(msg, code); - this.process = process; - } - -} - -exports.ProcessSpawnError = ProcessSpawnError; -class SecurityError extends MessageError {} - -exports.SecurityError = SecurityError; -class ProcessTermError extends MessageError {} - -exports.ProcessTermError = ProcessTermError; -class ResponseError extends Error { - constructor(msg, responseCode) { - super(msg); - this.responseCode = responseCode; - } - -} -exports.ResponseError = ResponseError; - -/***/ }), -/* 5 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.getFirstSuitableFolder = exports.readFirstAvailableStream = exports.makeTempDir = exports.hardlinksWork = exports.writeFilePreservingEol = exports.getFileSizeOnDisk = exports.walk = exports.symlink = exports.find = exports.readJsonAndFile = exports.readJson = exports.readFileAny = exports.hardlinkBulk = exports.copyBulk = exports.unlink = exports.glob = exports.link = exports.chmod = exports.lstat = exports.exists = exports.mkdirp = exports.stat = exports.access = exports.rename = exports.readdir = exports.realpath = exports.readlink = exports.writeFile = exports.open = exports.readFileBuffer = exports.lockQueue = exports.constants = undefined; - -var _asyncToGenerator2; - -function _load_asyncToGenerator() { - return _asyncToGenerator2 = _interopRequireDefault(__webpack_require__(1)); -} - -let buildActionsForCopy = (() => { - var _ref = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (queue, events, possibleExtraneous, reporter) { - - // - let build = (() => { - var _ref5 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (data) { - const src = data.src, - dest = data.dest, - type = data.type; - - const onFresh = data.onFresh || noop; - const onDone = data.onDone || noop; - - // TODO https://github.com/yarnpkg/yarn/issues/3751 - // related to bundled dependencies handling - if (files.has(dest.toLowerCase())) { - reporter.verbose(`The case-insensitive file ${dest} shouldn't be copied twice in one bulk copy`); - } else { - files.add(dest.toLowerCase()); - } - - if (type === 'symlink') { - yield mkdirp((_path || _load_path()).default.dirname(dest)); - onFresh(); - actions.symlink.push({ - dest, - linkname: src - }); - onDone(); - return; - } - - if (events.ignoreBasenames.indexOf((_path || _load_path()).default.basename(src)) >= 0) { - // ignored file - return; - } - - const srcStat = yield lstat(src); - let srcFiles; - - if (srcStat.isDirectory()) { - srcFiles = yield readdir(src); - } - - let destStat; - try { - // try accessing the destination - destStat = yield lstat(dest); - } catch (e) { - // proceed if destination doesn't exist, otherwise error - if (e.code !== 'ENOENT') { - throw e; - } - } - - // if destination exists - if (destStat) { - const bothSymlinks = srcStat.isSymbolicLink() && destStat.isSymbolicLink(); - const bothFolders = srcStat.isDirectory() && destStat.isDirectory(); - const bothFiles = srcStat.isFile() && destStat.isFile(); - - // EINVAL access errors sometimes happen which shouldn't because node shouldn't be giving - // us modes that aren't valid. investigate this, it's generally safe to proceed. - - /* if (srcStat.mode !== destStat.mode) { - try { - await access(dest, srcStat.mode); - } catch (err) {} - } */ - - if (bothFiles && artifactFiles.has(dest)) { - // this file gets changed during build, likely by a custom install script. Don't bother checking it. - onDone(); - reporter.verbose(reporter.lang('verboseFileSkipArtifact', src)); - return; - } - - if (bothFiles && srcStat.size === destStat.size && (0, (_fsNormalized || _load_fsNormalized()).fileDatesEqual)(srcStat.mtime, destStat.mtime)) { - // we can safely assume this is the same file - onDone(); - reporter.verbose(reporter.lang('verboseFileSkip', src, dest, srcStat.size, +srcStat.mtime)); - return; - } - - if (bothSymlinks) { - const srcReallink = yield readlink(src); - if (srcReallink === (yield readlink(dest))) { - // if both symlinks are the same then we can continue on - onDone(); - reporter.verbose(reporter.lang('verboseFileSkipSymlink', src, dest, srcReallink)); - return; - } - } - - if (bothFolders) { - // mark files that aren't in this folder as possibly extraneous - const destFiles = yield readdir(dest); - invariant(srcFiles, 'src files not initialised'); - - for (var _iterator4 = destFiles, _isArray4 = Array.isArray(_iterator4), _i4 = 0, _iterator4 = _isArray4 ? _iterator4 : _iterator4[Symbol.iterator]();;) { - var _ref6; - - if (_isArray4) { - if (_i4 >= _iterator4.length) break; - _ref6 = _iterator4[_i4++]; - } else { - _i4 = _iterator4.next(); - if (_i4.done) break; - _ref6 = _i4.value; - } - - const file = _ref6; - - if (srcFiles.indexOf(file) < 0) { - const loc = (_path || _load_path()).default.join(dest, file); - possibleExtraneous.add(loc); - - if ((yield lstat(loc)).isDirectory()) { - for (var _iterator5 = yield readdir(loc), _isArray5 = Array.isArray(_iterator5), _i5 = 0, _iterator5 = _isArray5 ? _iterator5 : _iterator5[Symbol.iterator]();;) { - var _ref7; - - if (_isArray5) { - if (_i5 >= _iterator5.length) break; - _ref7 = _iterator5[_i5++]; - } else { - _i5 = _iterator5.next(); - if (_i5.done) break; - _ref7 = _i5.value; - } - - const file = _ref7; - - possibleExtraneous.add((_path || _load_path()).default.join(loc, file)); - } - } - } - } - } - } - - if (destStat && destStat.isSymbolicLink()) { - yield (0, (_fsNormalized || _load_fsNormalized()).unlink)(dest); - destStat = null; - } - - if (srcStat.isSymbolicLink()) { - onFresh(); - const linkname = yield readlink(src); - actions.symlink.push({ - dest, - linkname - }); - onDone(); - } else if (srcStat.isDirectory()) { - if (!destStat) { - reporter.verbose(reporter.lang('verboseFileFolder', dest)); - yield mkdirp(dest); - } - - const destParts = dest.split((_path || _load_path()).default.sep); - while (destParts.length) { - files.add(destParts.join((_path || _load_path()).default.sep).toLowerCase()); - destParts.pop(); - } - - // push all files to queue - invariant(srcFiles, 'src files not initialised'); - let remaining = srcFiles.length; - if (!remaining) { - onDone(); - } - for (var _iterator6 = srcFiles, _isArray6 = Array.isArray(_iterator6), _i6 = 0, _iterator6 = _isArray6 ? _iterator6 : _iterator6[Symbol.iterator]();;) { - var _ref8; - - if (_isArray6) { - if (_i6 >= _iterator6.length) break; - _ref8 = _iterator6[_i6++]; - } else { - _i6 = _iterator6.next(); - if (_i6.done) break; - _ref8 = _i6.value; - } - - const file = _ref8; - - queue.push({ - dest: (_path || _load_path()).default.join(dest, file), - onFresh, - onDone: function (_onDone) { - function onDone() { - return _onDone.apply(this, arguments); - } - - onDone.toString = function () { - return _onDone.toString(); - }; - - return onDone; - }(function () { - if (--remaining === 0) { - onDone(); - } - }), - src: (_path || _load_path()).default.join(src, file) - }); - } - } else if (srcStat.isFile()) { - onFresh(); - actions.file.push({ - src, - dest, - atime: srcStat.atime, - mtime: srcStat.mtime, - mode: srcStat.mode - }); - onDone(); - } else { - throw new Error(`unsure how to copy this: ${src}`); - } - }); - - return function build(_x5) { - return _ref5.apply(this, arguments); - }; - })(); - - const artifactFiles = new Set(events.artifactFiles || []); - const files = new Set(); - - // initialise events - for (var _iterator = queue, _isArray = Array.isArray(_iterator), _i = 0, _iterator = _isArray ? _iterator : _iterator[Symbol.iterator]();;) { - var _ref2; - - if (_isArray) { - if (_i >= _iterator.length) break; - _ref2 = _iterator[_i++]; - } else { - _i = _iterator.next(); - if (_i.done) break; - _ref2 = _i.value; - } - - const item = _ref2; - - const onDone = item.onDone; - item.onDone = function () { - events.onProgress(item.dest); - if (onDone) { - onDone(); - } - }; - } - events.onStart(queue.length); - - // start building actions - const actions = { - file: [], - symlink: [], - link: [] - }; - - // custom concurrency logic as we're always executing stacks of CONCURRENT_QUEUE_ITEMS queue items - // at a time due to the requirement to push items onto the queue - while (queue.length) { - const items = queue.splice(0, CONCURRENT_QUEUE_ITEMS); - yield Promise.all(items.map(build)); - } - - // simulate the existence of some files to prevent considering them extraneous - for (var _iterator2 = artifactFiles, _isArray2 = Array.isArray(_iterator2), _i2 = 0, _iterator2 = _isArray2 ? _iterator2 : _iterator2[Symbol.iterator]();;) { - var _ref3; - - if (_isArray2) { - if (_i2 >= _iterator2.length) break; - _ref3 = _iterator2[_i2++]; - } else { - _i2 = _iterator2.next(); - if (_i2.done) break; - _ref3 = _i2.value; - } - - const file = _ref3; - - if (possibleExtraneous.has(file)) { - reporter.verbose(reporter.lang('verboseFilePhantomExtraneous', file)); - possibleExtraneous.delete(file); - } - } - - for (var _iterator3 = possibleExtraneous, _isArray3 = Array.isArray(_iterator3), _i3 = 0, _iterator3 = _isArray3 ? _iterator3 : _iterator3[Symbol.iterator]();;) { - var _ref4; - - if (_isArray3) { - if (_i3 >= _iterator3.length) break; - _ref4 = _iterator3[_i3++]; - } else { - _i3 = _iterator3.next(); - if (_i3.done) break; - _ref4 = _i3.value; - } - - const loc = _ref4; - - if (files.has(loc.toLowerCase())) { - possibleExtraneous.delete(loc); - } - } - - return actions; - }); - - return function buildActionsForCopy(_x, _x2, _x3, _x4) { - return _ref.apply(this, arguments); - }; -})(); - -let buildActionsForHardlink = (() => { - var _ref9 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (queue, events, possibleExtraneous, reporter) { - - // - let build = (() => { - var _ref13 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (data) { - const src = data.src, - dest = data.dest; - - const onFresh = data.onFresh || noop; - const onDone = data.onDone || noop; - if (files.has(dest.toLowerCase())) { - // Fixes issue https://github.com/yarnpkg/yarn/issues/2734 - // When bulk hardlinking we have A -> B structure that we want to hardlink to A1 -> B1, - // package-linker passes that modules A1 and B1 need to be hardlinked, - // the recursive linking algorithm of A1 ends up scheduling files in B1 to be linked twice which will case - // an exception. - onDone(); - return; - } - files.add(dest.toLowerCase()); - - if (events.ignoreBasenames.indexOf((_path || _load_path()).default.basename(src)) >= 0) { - // ignored file - return; - } - - const srcStat = yield lstat(src); - let srcFiles; - - if (srcStat.isDirectory()) { - srcFiles = yield readdir(src); - } - - const destExists = yield exists(dest); - if (destExists) { - const destStat = yield lstat(dest); - - const bothSymlinks = srcStat.isSymbolicLink() && destStat.isSymbolicLink(); - const bothFolders = srcStat.isDirectory() && destStat.isDirectory(); - const bothFiles = srcStat.isFile() && destStat.isFile(); - - if (srcStat.mode !== destStat.mode) { - try { - yield access(dest, srcStat.mode); - } catch (err) { - // EINVAL access errors sometimes happen which shouldn't because node shouldn't be giving - // us modes that aren't valid. investigate this, it's generally safe to proceed. - reporter.verbose(err); - } - } - - if (bothFiles && artifactFiles.has(dest)) { - // this file gets changed during build, likely by a custom install script. Don't bother checking it. - onDone(); - reporter.verbose(reporter.lang('verboseFileSkipArtifact', src)); - return; - } - - // correct hardlink - if (bothFiles && srcStat.ino !== null && srcStat.ino === destStat.ino) { - onDone(); - reporter.verbose(reporter.lang('verboseFileSkip', src, dest, srcStat.ino)); - return; - } - - if (bothSymlinks) { - const srcReallink = yield readlink(src); - if (srcReallink === (yield readlink(dest))) { - // if both symlinks are the same then we can continue on - onDone(); - reporter.verbose(reporter.lang('verboseFileSkipSymlink', src, dest, srcReallink)); - return; - } - } - - if (bothFolders) { - // mark files that aren't in this folder as possibly extraneous - const destFiles = yield readdir(dest); - invariant(srcFiles, 'src files not initialised'); - - for (var _iterator10 = destFiles, _isArray10 = Array.isArray(_iterator10), _i10 = 0, _iterator10 = _isArray10 ? _iterator10 : _iterator10[Symbol.iterator]();;) { - var _ref14; - - if (_isArray10) { - if (_i10 >= _iterator10.length) break; - _ref14 = _iterator10[_i10++]; - } else { - _i10 = _iterator10.next(); - if (_i10.done) break; - _ref14 = _i10.value; - } - - const file = _ref14; - - if (srcFiles.indexOf(file) < 0) { - const loc = (_path || _load_path()).default.join(dest, file); - possibleExtraneous.add(loc); - - if ((yield lstat(loc)).isDirectory()) { - for (var _iterator11 = yield readdir(loc), _isArray11 = Array.isArray(_iterator11), _i11 = 0, _iterator11 = _isArray11 ? _iterator11 : _iterator11[Symbol.iterator]();;) { - var _ref15; - - if (_isArray11) { - if (_i11 >= _iterator11.length) break; - _ref15 = _iterator11[_i11++]; - } else { - _i11 = _iterator11.next(); - if (_i11.done) break; - _ref15 = _i11.value; - } - - const file = _ref15; - - possibleExtraneous.add((_path || _load_path()).default.join(loc, file)); - } - } - } - } - } - } - - if (srcStat.isSymbolicLink()) { - onFresh(); - const linkname = yield readlink(src); - actions.symlink.push({ - dest, - linkname - }); - onDone(); - } else if (srcStat.isDirectory()) { - reporter.verbose(reporter.lang('verboseFileFolder', dest)); - yield mkdirp(dest); - - const destParts = dest.split((_path || _load_path()).default.sep); - while (destParts.length) { - files.add(destParts.join((_path || _load_path()).default.sep).toLowerCase()); - destParts.pop(); - } - - // push all files to queue - invariant(srcFiles, 'src files not initialised'); - let remaining = srcFiles.length; - if (!remaining) { - onDone(); - } - for (var _iterator12 = srcFiles, _isArray12 = Array.isArray(_iterator12), _i12 = 0, _iterator12 = _isArray12 ? _iterator12 : _iterator12[Symbol.iterator]();;) { - var _ref16; - - if (_isArray12) { - if (_i12 >= _iterator12.length) break; - _ref16 = _iterator12[_i12++]; - } else { - _i12 = _iterator12.next(); - if (_i12.done) break; - _ref16 = _i12.value; - } - - const file = _ref16; - - queue.push({ - onFresh, - src: (_path || _load_path()).default.join(src, file), - dest: (_path || _load_path()).default.join(dest, file), - onDone: function (_onDone2) { - function onDone() { - return _onDone2.apply(this, arguments); - } - - onDone.toString = function () { - return _onDone2.toString(); - }; - - return onDone; - }(function () { - if (--remaining === 0) { - onDone(); - } - }) - }); - } - } else if (srcStat.isFile()) { - onFresh(); - actions.link.push({ - src, - dest, - removeDest: destExists - }); - onDone(); - } else { - throw new Error(`unsure how to copy this: ${src}`); - } - }); - - return function build(_x10) { - return _ref13.apply(this, arguments); - }; - })(); - - const artifactFiles = new Set(events.artifactFiles || []); - const files = new Set(); - - // initialise events - for (var _iterator7 = queue, _isArray7 = Array.isArray(_iterator7), _i7 = 0, _iterator7 = _isArray7 ? _iterator7 : _iterator7[Symbol.iterator]();;) { - var _ref10; - - if (_isArray7) { - if (_i7 >= _iterator7.length) break; - _ref10 = _iterator7[_i7++]; - } else { - _i7 = _iterator7.next(); - if (_i7.done) break; - _ref10 = _i7.value; - } - - const item = _ref10; - - const onDone = item.onDone || noop; - item.onDone = function () { - events.onProgress(item.dest); - onDone(); - }; - } - events.onStart(queue.length); - - // start building actions - const actions = { - file: [], - symlink: [], - link: [] - }; - - // custom concurrency logic as we're always executing stacks of CONCURRENT_QUEUE_ITEMS queue items - // at a time due to the requirement to push items onto the queue - while (queue.length) { - const items = queue.splice(0, CONCURRENT_QUEUE_ITEMS); - yield Promise.all(items.map(build)); - } - - // simulate the existence of some files to prevent considering them extraneous - for (var _iterator8 = artifactFiles, _isArray8 = Array.isArray(_iterator8), _i8 = 0, _iterator8 = _isArray8 ? _iterator8 : _iterator8[Symbol.iterator]();;) { - var _ref11; - - if (_isArray8) { - if (_i8 >= _iterator8.length) break; - _ref11 = _iterator8[_i8++]; - } else { - _i8 = _iterator8.next(); - if (_i8.done) break; - _ref11 = _i8.value; - } - - const file = _ref11; - - if (possibleExtraneous.has(file)) { - reporter.verbose(reporter.lang('verboseFilePhantomExtraneous', file)); - possibleExtraneous.delete(file); - } - } - - for (var _iterator9 = possibleExtraneous, _isArray9 = Array.isArray(_iterator9), _i9 = 0, _iterator9 = _isArray9 ? _iterator9 : _iterator9[Symbol.iterator]();;) { - var _ref12; - - if (_isArray9) { - if (_i9 >= _iterator9.length) break; - _ref12 = _iterator9[_i9++]; - } else { - _i9 = _iterator9.next(); - if (_i9.done) break; - _ref12 = _i9.value; - } - - const loc = _ref12; - - if (files.has(loc.toLowerCase())) { - possibleExtraneous.delete(loc); - } - } - - return actions; - }); - - return function buildActionsForHardlink(_x6, _x7, _x8, _x9) { - return _ref9.apply(this, arguments); - }; -})(); - -let copyBulk = exports.copyBulk = (() => { - var _ref17 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (queue, reporter, _events) { - const events = { - onStart: _events && _events.onStart || noop, - onProgress: _events && _events.onProgress || noop, - possibleExtraneous: _events ? _events.possibleExtraneous : new Set(), - ignoreBasenames: _events && _events.ignoreBasenames || [], - artifactFiles: _events && _events.artifactFiles || [] - }; - - const actions = yield buildActionsForCopy(queue, events, events.possibleExtraneous, reporter); - events.onStart(actions.file.length + actions.symlink.length + actions.link.length); - - const fileActions = actions.file; - - const currentlyWriting = new Map(); - - yield (_promise || _load_promise()).queue(fileActions, (() => { - var _ref18 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (data) { - let writePromise; - while (writePromise = currentlyWriting.get(data.dest)) { - yield writePromise; - } - - reporter.verbose(reporter.lang('verboseFileCopy', data.src, data.dest)); - const copier = (0, (_fsNormalized || _load_fsNormalized()).copyFile)(data, function () { - return currentlyWriting.delete(data.dest); - }); - currentlyWriting.set(data.dest, copier); - events.onProgress(data.dest); - return copier; - }); - - return function (_x14) { - return _ref18.apply(this, arguments); - }; - })(), CONCURRENT_QUEUE_ITEMS); - - // we need to copy symlinks last as they could reference files we were copying - const symlinkActions = actions.symlink; - yield (_promise || _load_promise()).queue(symlinkActions, function (data) { - const linkname = (_path || _load_path()).default.resolve((_path || _load_path()).default.dirname(data.dest), data.linkname); - reporter.verbose(reporter.lang('verboseFileSymlink', data.dest, linkname)); - return symlink(linkname, data.dest); - }); - }); - - return function copyBulk(_x11, _x12, _x13) { - return _ref17.apply(this, arguments); - }; -})(); - -let hardlinkBulk = exports.hardlinkBulk = (() => { - var _ref19 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (queue, reporter, _events) { - const events = { - onStart: _events && _events.onStart || noop, - onProgress: _events && _events.onProgress || noop, - possibleExtraneous: _events ? _events.possibleExtraneous : new Set(), - artifactFiles: _events && _events.artifactFiles || [], - ignoreBasenames: [] - }; - - const actions = yield buildActionsForHardlink(queue, events, events.possibleExtraneous, reporter); - events.onStart(actions.file.length + actions.symlink.length + actions.link.length); - - const fileActions = actions.link; - - yield (_promise || _load_promise()).queue(fileActions, (() => { - var _ref20 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (data) { - reporter.verbose(reporter.lang('verboseFileLink', data.src, data.dest)); - if (data.removeDest) { - yield (0, (_fsNormalized || _load_fsNormalized()).unlink)(data.dest); - } - yield link(data.src, data.dest); - }); - - return function (_x18) { - return _ref20.apply(this, arguments); - }; - })(), CONCURRENT_QUEUE_ITEMS); - - // we need to copy symlinks last as they could reference files we were copying - const symlinkActions = actions.symlink; - yield (_promise || _load_promise()).queue(symlinkActions, function (data) { - const linkname = (_path || _load_path()).default.resolve((_path || _load_path()).default.dirname(data.dest), data.linkname); - reporter.verbose(reporter.lang('verboseFileSymlink', data.dest, linkname)); - return symlink(linkname, data.dest); - }); - }); - - return function hardlinkBulk(_x15, _x16, _x17) { - return _ref19.apply(this, arguments); - }; -})(); - -let readFileAny = exports.readFileAny = (() => { - var _ref21 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (files) { - for (var _iterator13 = files, _isArray13 = Array.isArray(_iterator13), _i13 = 0, _iterator13 = _isArray13 ? _iterator13 : _iterator13[Symbol.iterator]();;) { - var _ref22; - - if (_isArray13) { - if (_i13 >= _iterator13.length) break; - _ref22 = _iterator13[_i13++]; - } else { - _i13 = _iterator13.next(); - if (_i13.done) break; - _ref22 = _i13.value; - } - - const file = _ref22; - - if (yield exists(file)) { - return readFile(file); - } - } - return null; - }); - - return function readFileAny(_x19) { - return _ref21.apply(this, arguments); - }; -})(); - -let readJson = exports.readJson = (() => { - var _ref23 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (loc) { - return (yield readJsonAndFile(loc)).object; - }); - - return function readJson(_x20) { - return _ref23.apply(this, arguments); - }; -})(); - -let readJsonAndFile = exports.readJsonAndFile = (() => { - var _ref24 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (loc) { - const file = yield readFile(loc); - try { - return { - object: (0, (_map || _load_map()).default)(JSON.parse(stripBOM(file))), - content: file - }; - } catch (err) { - err.message = `${loc}: ${err.message}`; - throw err; - } - }); - - return function readJsonAndFile(_x21) { - return _ref24.apply(this, arguments); - }; -})(); - -let find = exports.find = (() => { - var _ref25 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (filename, dir) { - const parts = dir.split((_path || _load_path()).default.sep); - - while (parts.length) { - const loc = parts.concat(filename).join((_path || _load_path()).default.sep); - - if (yield exists(loc)) { - return loc; - } else { - parts.pop(); - } - } - - return false; - }); - - return function find(_x22, _x23) { - return _ref25.apply(this, arguments); - }; -})(); - -let symlink = exports.symlink = (() => { - var _ref26 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (src, dest) { - try { - const stats = yield lstat(dest); - if (stats.isSymbolicLink()) { - const resolved = yield realpath(dest); - if (resolved === src) { - return; - } - } - } catch (err) { - if (err.code !== 'ENOENT') { - throw err; - } - } - // We use rimraf for unlink which never throws an ENOENT on missing target - yield (0, (_fsNormalized || _load_fsNormalized()).unlink)(dest); - - if (process.platform === 'win32') { - // use directory junctions if possible on win32, this requires absolute paths - yield fsSymlink(src, dest, 'junction'); - } else { - // use relative paths otherwise which will be retained if the directory is moved - let relative; - try { - relative = (_path || _load_path()).default.relative((_fs || _load_fs()).default.realpathSync((_path || _load_path()).default.dirname(dest)), (_fs || _load_fs()).default.realpathSync(src)); - } catch (err) { - if (err.code !== 'ENOENT') { - throw err; - } - relative = (_path || _load_path()).default.relative((_path || _load_path()).default.dirname(dest), src); - } - // When path.relative returns an empty string for the current directory, we should instead use - // '.', which is a valid fs.symlink target. - yield fsSymlink(relative || '.', dest); - } - }); - - return function symlink(_x24, _x25) { - return _ref26.apply(this, arguments); - }; -})(); - -let walk = exports.walk = (() => { - var _ref27 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (dir, relativeDir, ignoreBasenames = new Set()) { - let files = []; - - let filenames = yield readdir(dir); - if (ignoreBasenames.size) { - filenames = filenames.filter(function (name) { - return !ignoreBasenames.has(name); - }); - } - - for (var _iterator14 = filenames, _isArray14 = Array.isArray(_iterator14), _i14 = 0, _iterator14 = _isArray14 ? _iterator14 : _iterator14[Symbol.iterator]();;) { - var _ref28; - - if (_isArray14) { - if (_i14 >= _iterator14.length) break; - _ref28 = _iterator14[_i14++]; - } else { - _i14 = _iterator14.next(); - if (_i14.done) break; - _ref28 = _i14.value; - } - - const name = _ref28; - - const relative = relativeDir ? (_path || _load_path()).default.join(relativeDir, name) : name; - const loc = (_path || _load_path()).default.join(dir, name); - const stat = yield lstat(loc); - - files.push({ - relative, - basename: name, - absolute: loc, - mtime: +stat.mtime - }); - - if (stat.isDirectory()) { - files = files.concat((yield walk(loc, relative, ignoreBasenames))); - } - } - - return files; - }); - - return function walk(_x26, _x27) { - return _ref27.apply(this, arguments); - }; -})(); - -let getFileSizeOnDisk = exports.getFileSizeOnDisk = (() => { - var _ref29 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (loc) { - const stat = yield lstat(loc); - const size = stat.size, - blockSize = stat.blksize; - - - return Math.ceil(size / blockSize) * blockSize; - }); - - return function getFileSizeOnDisk(_x28) { - return _ref29.apply(this, arguments); - }; -})(); - -let getEolFromFile = (() => { - var _ref30 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (path) { - if (!(yield exists(path))) { - return undefined; - } - - const buffer = yield readFileBuffer(path); - - for (let i = 0; i < buffer.length; ++i) { - if (buffer[i] === cr) { - return '\r\n'; - } - if (buffer[i] === lf) { - return '\n'; - } - } - return undefined; - }); - - return function getEolFromFile(_x29) { - return _ref30.apply(this, arguments); - }; -})(); - -let writeFilePreservingEol = exports.writeFilePreservingEol = (() => { - var _ref31 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (path, data) { - const eol = (yield getEolFromFile(path)) || (_os || _load_os()).default.EOL; - if (eol !== '\n') { - data = data.replace(/\n/g, eol); - } - yield writeFile(path, data); - }); - - return function writeFilePreservingEol(_x30, _x31) { - return _ref31.apply(this, arguments); - }; -})(); - -let hardlinksWork = exports.hardlinksWork = (() => { - var _ref32 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (dir) { - const filename = 'test-file' + Math.random(); - const file = (_path || _load_path()).default.join(dir, filename); - const fileLink = (_path || _load_path()).default.join(dir, filename + '-link'); - try { - yield writeFile(file, 'test'); - yield link(file, fileLink); - } catch (err) { - return false; - } finally { - yield (0, (_fsNormalized || _load_fsNormalized()).unlink)(file); - yield (0, (_fsNormalized || _load_fsNormalized()).unlink)(fileLink); - } - return true; - }); - - return function hardlinksWork(_x32) { - return _ref32.apply(this, arguments); - }; -})(); - -// not a strict polyfill for Node's fs.mkdtemp - - -let makeTempDir = exports.makeTempDir = (() => { - var _ref33 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (prefix) { - const dir = (_path || _load_path()).default.join((_os || _load_os()).default.tmpdir(), `yarn-${prefix || ''}-${Date.now()}-${Math.random()}`); - yield (0, (_fsNormalized || _load_fsNormalized()).unlink)(dir); - yield mkdirp(dir); - return dir; - }); - - return function makeTempDir(_x33) { - return _ref33.apply(this, arguments); - }; -})(); - -let readFirstAvailableStream = exports.readFirstAvailableStream = (() => { - var _ref34 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (paths) { - for (var _iterator15 = paths, _isArray15 = Array.isArray(_iterator15), _i15 = 0, _iterator15 = _isArray15 ? _iterator15 : _iterator15[Symbol.iterator]();;) { - var _ref35; - - if (_isArray15) { - if (_i15 >= _iterator15.length) break; - _ref35 = _iterator15[_i15++]; - } else { - _i15 = _iterator15.next(); - if (_i15.done) break; - _ref35 = _i15.value; - } - - const path = _ref35; - - try { - const fd = yield open(path, 'r'); - return (_fs || _load_fs()).default.createReadStream(path, { fd }); - } catch (err) { - // Try the next one - } - } - return null; - }); - - return function readFirstAvailableStream(_x34) { - return _ref34.apply(this, arguments); - }; -})(); - -let getFirstSuitableFolder = exports.getFirstSuitableFolder = (() => { - var _ref36 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (paths, mode = constants.W_OK | constants.X_OK) { - const result = { - skipped: [], - folder: null - }; - - for (var _iterator16 = paths, _isArray16 = Array.isArray(_iterator16), _i16 = 0, _iterator16 = _isArray16 ? _iterator16 : _iterator16[Symbol.iterator]();;) { - var _ref37; - - if (_isArray16) { - if (_i16 >= _iterator16.length) break; - _ref37 = _iterator16[_i16++]; - } else { - _i16 = _iterator16.next(); - if (_i16.done) break; - _ref37 = _i16.value; - } - - const folder = _ref37; - - try { - yield mkdirp(folder); - yield access(folder, mode); - - result.folder = folder; - - return result; - } catch (error) { - result.skipped.push({ - error, - folder - }); - } - } - return result; - }); - - return function getFirstSuitableFolder(_x35) { - return _ref36.apply(this, arguments); - }; -})(); - -exports.copy = copy; -exports.readFile = readFile; -exports.readFileRaw = readFileRaw; -exports.normalizeOS = normalizeOS; - -var _fs; - -function _load_fs() { - return _fs = _interopRequireDefault(__webpack_require__(3)); -} - -var _glob; - -function _load_glob() { - return _glob = _interopRequireDefault(__webpack_require__(75)); -} - -var _os; - -function _load_os() { - return _os = _interopRequireDefault(__webpack_require__(36)); -} - -var _path; - -function _load_path() { - return _path = _interopRequireDefault(__webpack_require__(0)); -} - -var _blockingQueue; - -function _load_blockingQueue() { - return _blockingQueue = _interopRequireDefault(__webpack_require__(84)); -} - -var _promise; - -function _load_promise() { - return _promise = _interopRequireWildcard(__webpack_require__(40)); -} - -var _promise2; - -function _load_promise2() { - return _promise2 = __webpack_require__(40); -} - -var _map; - -function _load_map() { - return _map = _interopRequireDefault(__webpack_require__(20)); -} - -var _fsNormalized; - -function _load_fsNormalized() { - return _fsNormalized = __webpack_require__(164); -} - -function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } - -function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } - -const constants = exports.constants = typeof (_fs || _load_fs()).default.constants !== 'undefined' ? (_fs || _load_fs()).default.constants : { - R_OK: (_fs || _load_fs()).default.R_OK, - W_OK: (_fs || _load_fs()).default.W_OK, - X_OK: (_fs || _load_fs()).default.X_OK -}; - -const lockQueue = exports.lockQueue = new (_blockingQueue || _load_blockingQueue()).default('fs lock'); - -const readFileBuffer = exports.readFileBuffer = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.readFile); -const open = exports.open = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.open); -const writeFile = exports.writeFile = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.writeFile); -const readlink = exports.readlink = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.readlink); -const realpath = exports.realpath = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.realpath); -const readdir = exports.readdir = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.readdir); -const rename = exports.rename = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.rename); -const access = exports.access = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.access); -const stat = exports.stat = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.stat); -const mkdirp = exports.mkdirp = (0, (_promise2 || _load_promise2()).promisify)(__webpack_require__(116)); -const exists = exports.exists = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.exists, true); -const lstat = exports.lstat = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.lstat); -const chmod = exports.chmod = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.chmod); -const link = exports.link = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.link); -const glob = exports.glob = (0, (_promise2 || _load_promise2()).promisify)((_glob || _load_glob()).default); -exports.unlink = (_fsNormalized || _load_fsNormalized()).unlink; - -// fs.copyFile uses the native file copying instructions on the system, performing much better -// than any JS-based solution and consumes fewer resources. Repeated testing to fine tune the -// concurrency level revealed 128 as the sweet spot on a quad-core, 16 CPU Intel system with SSD. - -const CONCURRENT_QUEUE_ITEMS = (_fs || _load_fs()).default.copyFile ? 128 : 4; - -const fsSymlink = (0, (_promise2 || _load_promise2()).promisify)((_fs || _load_fs()).default.symlink); -const invariant = __webpack_require__(7); -const stripBOM = __webpack_require__(122); - -const noop = () => {}; - -function copy(src, dest, reporter) { - return copyBulk([{ src, dest }], reporter); -} - -function _readFile(loc, encoding) { - return new Promise((resolve, reject) => { - (_fs || _load_fs()).default.readFile(loc, encoding, function (err, content) { - if (err) { - reject(err); - } else { - resolve(content); - } - }); - }); -} - -function readFile(loc) { - return _readFile(loc, 'utf8').then(normalizeOS); -} - -function readFileRaw(loc) { - return _readFile(loc, 'binary'); -} - -function normalizeOS(body) { - return body.replace(/\r\n/g, '\n'); -} - -const cr = '\r'.charCodeAt(0); -const lf = '\n'.charCodeAt(0); - -/***/ }), -/* 6 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.getPathKey = getPathKey; -const os = __webpack_require__(36); -const path = __webpack_require__(0); -const userHome = __webpack_require__(45).default; - -var _require = __webpack_require__(171); - -const getCacheDir = _require.getCacheDir, - getConfigDir = _require.getConfigDir, - getDataDir = _require.getDataDir; - -const isWebpackBundle = __webpack_require__(227); - -const DEPENDENCY_TYPES = exports.DEPENDENCY_TYPES = ['devDependencies', 'dependencies', 'optionalDependencies', 'peerDependencies']; -const RESOLUTIONS = exports.RESOLUTIONS = 'resolutions'; -const MANIFEST_FIELDS = exports.MANIFEST_FIELDS = [RESOLUTIONS, ...DEPENDENCY_TYPES]; - -const SUPPORTED_NODE_VERSIONS = exports.SUPPORTED_NODE_VERSIONS = '^4.8.0 || ^5.7.0 || ^6.2.2 || >=8.0.0'; - -const YARN_REGISTRY = exports.YARN_REGISTRY = 'https://registry.yarnpkg.com'; - -const YARN_DOCS = exports.YARN_DOCS = 'https://yarnpkg.com/en/docs/cli/'; -const YARN_INSTALLER_SH = exports.YARN_INSTALLER_SH = 'https://yarnpkg.com/install.sh'; -const YARN_INSTALLER_MSI = exports.YARN_INSTALLER_MSI = 'https://yarnpkg.com/latest.msi'; - -const SELF_UPDATE_VERSION_URL = exports.SELF_UPDATE_VERSION_URL = 'https://yarnpkg.com/latest-version'; - -// cache version, bump whenever we make backwards incompatible changes -const CACHE_VERSION = exports.CACHE_VERSION = 2; - -// lockfile version, bump whenever we make backwards incompatible changes -const LOCKFILE_VERSION = exports.LOCKFILE_VERSION = 1; - -// max amount of network requests to perform concurrently -const NETWORK_CONCURRENCY = exports.NETWORK_CONCURRENCY = 8; - -// HTTP timeout used when downloading packages -const NETWORK_TIMEOUT = exports.NETWORK_TIMEOUT = 30 * 1000; // in milliseconds - -// max amount of child processes to execute concurrently -const CHILD_CONCURRENCY = exports.CHILD_CONCURRENCY = 5; - -const REQUIRED_PACKAGE_KEYS = exports.REQUIRED_PACKAGE_KEYS = ['name', 'version', '_uid']; - -function getPreferredCacheDirectories() { - const preferredCacheDirectories = [getCacheDir()]; - - if (process.getuid) { - // $FlowFixMe: process.getuid exists, dammit - preferredCacheDirectories.push(path.join(os.tmpdir(), `.yarn-cache-${process.getuid()}`)); - } - - preferredCacheDirectories.push(path.join(os.tmpdir(), `.yarn-cache`)); - - return preferredCacheDirectories; -} - -const PREFERRED_MODULE_CACHE_DIRECTORIES = exports.PREFERRED_MODULE_CACHE_DIRECTORIES = getPreferredCacheDirectories(); -const CONFIG_DIRECTORY = exports.CONFIG_DIRECTORY = getConfigDir(); -const DATA_DIRECTORY = exports.DATA_DIRECTORY = getDataDir(); -const LINK_REGISTRY_DIRECTORY = exports.LINK_REGISTRY_DIRECTORY = path.join(DATA_DIRECTORY, 'link'); -const GLOBAL_MODULE_DIRECTORY = exports.GLOBAL_MODULE_DIRECTORY = path.join(DATA_DIRECTORY, 'global'); - -const NODE_BIN_PATH = exports.NODE_BIN_PATH = process.execPath; -const YARN_BIN_PATH = exports.YARN_BIN_PATH = getYarnBinPath(); - -// Webpack needs to be configured with node.__dirname/__filename = false -function getYarnBinPath() { - if (isWebpackBundle) { - return __filename; - } else { - return path.join(__dirname, '..', 'bin', 'yarn.js'); - } -} - -const NODE_MODULES_FOLDER = exports.NODE_MODULES_FOLDER = 'node_modules'; -const NODE_PACKAGE_JSON = exports.NODE_PACKAGE_JSON = 'package.json'; - -const POSIX_GLOBAL_PREFIX = exports.POSIX_GLOBAL_PREFIX = `${process.env.DESTDIR || ''}/usr/local`; -const FALLBACK_GLOBAL_PREFIX = exports.FALLBACK_GLOBAL_PREFIX = path.join(userHome, '.yarn'); - -const META_FOLDER = exports.META_FOLDER = '.yarn-meta'; -const INTEGRITY_FILENAME = exports.INTEGRITY_FILENAME = '.yarn-integrity'; -const LOCKFILE_FILENAME = exports.LOCKFILE_FILENAME = 'yarn.lock'; -const METADATA_FILENAME = exports.METADATA_FILENAME = '.yarn-metadata.json'; -const TARBALL_FILENAME = exports.TARBALL_FILENAME = '.yarn-tarball.tgz'; -const CLEAN_FILENAME = exports.CLEAN_FILENAME = '.yarnclean'; - -const NPM_LOCK_FILENAME = exports.NPM_LOCK_FILENAME = 'package-lock.json'; -const NPM_SHRINKWRAP_FILENAME = exports.NPM_SHRINKWRAP_FILENAME = 'npm-shrinkwrap.json'; - -const DEFAULT_INDENT = exports.DEFAULT_INDENT = ' '; -const SINGLE_INSTANCE_PORT = exports.SINGLE_INSTANCE_PORT = 31997; -const SINGLE_INSTANCE_FILENAME = exports.SINGLE_INSTANCE_FILENAME = '.yarn-single-instance'; - -const ENV_PATH_KEY = exports.ENV_PATH_KEY = getPathKey(process.platform, process.env); - -function getPathKey(platform, env) { - let pathKey = 'PATH'; - - // windows calls its path "Path" usually, but this is not guaranteed. - if (platform === 'win32') { - pathKey = 'Path'; - - for (const key in env) { - if (key.toLowerCase() === 'path') { - pathKey = key; - } - } - } - - return pathKey; -} - -const VERSION_COLOR_SCHEME = exports.VERSION_COLOR_SCHEME = { - major: 'red', - premajor: 'red', - minor: 'yellow', - preminor: 'yellow', - patch: 'green', - prepatch: 'green', - prerelease: 'red', - unchanged: 'white', - unknown: 'red' -}; - -/***/ }), -/* 7 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/** - * Copyright (c) 2013-present, Facebook, Inc. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - - - -/** - * Use invariant() to assert state which your program assumes to be true. - * - * Provide sprintf-style format (only %s is supported) and arguments - * to provide information about what broke and what you were - * expecting. - * - * The invariant message will be stripped in production, but the invariant - * will remain to ensure logic does not differ in production. - */ - -var NODE_ENV = "production"; - -var invariant = function(condition, format, a, b, c, d, e, f) { - if (NODE_ENV !== 'production') { - if (format === undefined) { - throw new Error('invariant requires an error message argument'); - } - } - - if (!condition) { - var error; - if (format === undefined) { - error = new Error( - 'Minified exception occurred; use the non-minified dev environment ' + - 'for the full error message and additional helpful warnings.' - ); - } else { - var args = [a, b, c, d, e, f]; - var argIndex = 0; - error = new Error( - format.replace(/%s/g, function() { return args[argIndex++]; }) - ); - error.name = 'Invariant Violation'; - } - - error.framesToPop = 1; // we don't care about invariant's own frame - throw error; - } -}; - -module.exports = invariant; - - -/***/ }), -/* 8 */, -/* 9 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("crypto"); - -/***/ }), -/* 10 */, -/* 11 */ -/***/ (function(module, exports) { - -// https://github.com/zloirock/core-js/issues/86#issuecomment-115759028 -var global = module.exports = typeof window != 'undefined' && window.Math == Math - ? window : typeof self != 'undefined' && self.Math == Math ? self - // eslint-disable-next-line no-new-func - : Function('return this')(); -if (typeof __g == 'number') __g = global; // eslint-disable-line no-undef - - -/***/ }), -/* 12 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.sortAlpha = sortAlpha; -exports.entries = entries; -exports.removePrefix = removePrefix; -exports.removeSuffix = removeSuffix; -exports.addSuffix = addSuffix; -exports.hyphenate = hyphenate; -exports.camelCase = camelCase; -exports.compareSortedArrays = compareSortedArrays; -exports.sleep = sleep; -const _camelCase = __webpack_require__(176); - -function sortAlpha(a, b) { - // sort alphabetically in a deterministic way - const shortLen = Math.min(a.length, b.length); - for (let i = 0; i < shortLen; i++) { - const aChar = a.charCodeAt(i); - const bChar = b.charCodeAt(i); - if (aChar !== bChar) { - return aChar - bChar; - } - } - return a.length - b.length; -} - -function entries(obj) { - const entries = []; - if (obj) { - for (const key in obj) { - entries.push([key, obj[key]]); - } - } - return entries; -} - -function removePrefix(pattern, prefix) { - if (pattern.startsWith(prefix)) { - pattern = pattern.slice(prefix.length); - } - - return pattern; -} - -function removeSuffix(pattern, suffix) { - if (pattern.endsWith(suffix)) { - return pattern.slice(0, -suffix.length); - } - - return pattern; -} - -function addSuffix(pattern, suffix) { - if (!pattern.endsWith(suffix)) { - return pattern + suffix; - } - - return pattern; -} - -function hyphenate(str) { - return str.replace(/[A-Z]/g, match => { - return '-' + match.charAt(0).toLowerCase(); - }); -} - -function camelCase(str) { - if (/[A-Z]/.test(str)) { - return null; - } else { - return _camelCase(str); - } -} - -function compareSortedArrays(array1, array2) { - if (array1.length !== array2.length) { - return false; - } - for (let i = 0, len = array1.length; i < len; i++) { - if (array1[i] !== array2[i]) { - return false; - } - } - return true; -} - -function sleep(ms) { - return new Promise(resolve => { - setTimeout(resolve, ms); - }); -} - -/***/ }), -/* 13 */ -/***/ (function(module, exports, __webpack_require__) { - -var store = __webpack_require__(107)('wks'); -var uid = __webpack_require__(111); -var Symbol = __webpack_require__(11).Symbol; -var USE_SYMBOL = typeof Symbol == 'function'; - -var $exports = module.exports = function (name) { - return store[name] || (store[name] = - USE_SYMBOL && Symbol[name] || (USE_SYMBOL ? Symbol : uid)('Symbol.' + name)); -}; - -$exports.store = store; - - -/***/ }), -/* 14 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.stringify = exports.parse = undefined; - -var _asyncToGenerator2; - -function _load_asyncToGenerator() { - return _asyncToGenerator2 = _interopRequireDefault(__webpack_require__(1)); -} - -var _parse; - -function _load_parse() { - return _parse = __webpack_require__(81); -} - -Object.defineProperty(exports, 'parse', { - enumerable: true, - get: function get() { - return _interopRequireDefault(_parse || _load_parse()).default; - } -}); - -var _stringify; - -function _load_stringify() { - return _stringify = __webpack_require__(150); -} - -Object.defineProperty(exports, 'stringify', { - enumerable: true, - get: function get() { - return _interopRequireDefault(_stringify || _load_stringify()).default; - } -}); -exports.implodeEntry = implodeEntry; -exports.explodeEntry = explodeEntry; - -var _misc; - -function _load_misc() { - return _misc = __webpack_require__(12); -} - -var _normalizePattern; - -function _load_normalizePattern() { - return _normalizePattern = __webpack_require__(29); -} - -var _parse2; - -function _load_parse2() { - return _parse2 = _interopRequireDefault(__webpack_require__(81)); -} - -var _constants; - -function _load_constants() { - return _constants = __webpack_require__(6); -} - -var _fs; - -function _load_fs() { - return _fs = _interopRequireWildcard(__webpack_require__(5)); -} - -function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key]; } } newObj.default = obj; return newObj; } } - -function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } - -const invariant = __webpack_require__(7); - -const path = __webpack_require__(0); -const ssri = __webpack_require__(55); - -function getName(pattern) { - return (0, (_normalizePattern || _load_normalizePattern()).normalizePattern)(pattern).name; -} - -function blankObjectUndefined(obj) { - return obj && Object.keys(obj).length ? obj : undefined; -} - -function keyForRemote(remote) { - return remote.resolved || (remote.reference && remote.hash ? `${remote.reference}#${remote.hash}` : null); -} - -function serializeIntegrity(integrity) { - // We need this because `Integrity.toString()` does not use sorting to ensure a stable string output - // See https://git.io/vx2Hy - return integrity.toString().split(' ').sort().join(' '); -} - -function implodeEntry(pattern, obj) { - const inferredName = getName(pattern); - const integrity = obj.integrity ? serializeIntegrity(obj.integrity) : ''; - const imploded = { - name: inferredName === obj.name ? undefined : obj.name, - version: obj.version, - uid: obj.uid === obj.version ? undefined : obj.uid, - resolved: obj.resolved, - registry: obj.registry === 'npm' ? undefined : obj.registry, - dependencies: blankObjectUndefined(obj.dependencies), - optionalDependencies: blankObjectUndefined(obj.optionalDependencies), - permissions: blankObjectUndefined(obj.permissions), - prebuiltVariants: blankObjectUndefined(obj.prebuiltVariants) - }; - if (integrity) { - imploded.integrity = integrity; - } - return imploded; -} - -function explodeEntry(pattern, obj) { - obj.optionalDependencies = obj.optionalDependencies || {}; - obj.dependencies = obj.dependencies || {}; - obj.uid = obj.uid || obj.version; - obj.permissions = obj.permissions || {}; - obj.registry = obj.registry || 'npm'; - obj.name = obj.name || getName(pattern); - const integrity = obj.integrity; - if (integrity && integrity.isIntegrity) { - obj.integrity = ssri.parse(integrity); - } - return obj; -} - -class Lockfile { - constructor({ cache, source, parseResultType } = {}) { - this.source = source || ''; - this.cache = cache; - this.parseResultType = parseResultType; - } - - // source string if the `cache` was parsed - - - // if true, we're parsing an old yarn file and need to update integrity fields - hasEntriesExistWithoutIntegrity() { - if (!this.cache) { - return false; - } - - for (const key in this.cache) { - // $FlowFixMe - `this.cache` is clearly defined at this point - if (!/^.*@(file:|http)/.test(key) && this.cache[key] && !this.cache[key].integrity) { - return true; - } - } - - return false; - } - - static fromDirectory(dir, reporter) { - return (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* () { - // read the manifest in this directory - const lockfileLoc = path.join(dir, (_constants || _load_constants()).LOCKFILE_FILENAME); - - let lockfile; - let rawLockfile = ''; - let parseResult; - - if (yield (_fs || _load_fs()).exists(lockfileLoc)) { - rawLockfile = yield (_fs || _load_fs()).readFile(lockfileLoc); - parseResult = (0, (_parse2 || _load_parse2()).default)(rawLockfile, lockfileLoc); - - if (reporter) { - if (parseResult.type === 'merge') { - reporter.info(reporter.lang('lockfileMerged')); - } else if (parseResult.type === 'conflict') { - reporter.warn(reporter.lang('lockfileConflict')); - } - } - - lockfile = parseResult.object; - } else if (reporter) { - reporter.info(reporter.lang('noLockfileFound')); - } - - return new Lockfile({ cache: lockfile, source: rawLockfile, parseResultType: parseResult && parseResult.type }); - })(); - } - - getLocked(pattern) { - const cache = this.cache; - if (!cache) { - return undefined; - } - - const shrunk = pattern in cache && cache[pattern]; - - if (typeof shrunk === 'string') { - return this.getLocked(shrunk); - } else if (shrunk) { - explodeEntry(pattern, shrunk); - return shrunk; - } - - return undefined; - } - - removePattern(pattern) { - const cache = this.cache; - if (!cache) { - return; - } - delete cache[pattern]; - } - - getLockfile(patterns) { - const lockfile = {}; - const seen = new Map(); - - // order by name so that lockfile manifest is assigned to the first dependency with this manifest - // the others that have the same remoteKey will just refer to the first - // ordering allows for consistency in lockfile when it is serialized - const sortedPatternsKeys = Object.keys(patterns).sort((_misc || _load_misc()).sortAlpha); - - for (var _iterator = sortedPatternsKeys, _isArray = Array.isArray(_iterator), _i = 0, _iterator = _isArray ? _iterator : _iterator[Symbol.iterator]();;) { - var _ref; - - if (_isArray) { - if (_i >= _iterator.length) break; - _ref = _iterator[_i++]; - } else { - _i = _iterator.next(); - if (_i.done) break; - _ref = _i.value; - } - - const pattern = _ref; - - const pkg = patterns[pattern]; - const remote = pkg._remote, - ref = pkg._reference; - - invariant(ref, 'Package is missing a reference'); - invariant(remote, 'Package is missing a remote'); - - const remoteKey = keyForRemote(remote); - const seenPattern = remoteKey && seen.get(remoteKey); - if (seenPattern) { - // no point in duplicating it - lockfile[pattern] = seenPattern; - - // if we're relying on our name being inferred and two of the patterns have - // different inferred names then we need to set it - if (!seenPattern.name && getName(pattern) !== pkg.name) { - seenPattern.name = pkg.name; - } - continue; - } - const obj = implodeEntry(pattern, { - name: pkg.name, - version: pkg.version, - uid: pkg._uid, - resolved: remote.resolved, - integrity: remote.integrity, - registry: remote.registry, - dependencies: pkg.dependencies, - peerDependencies: pkg.peerDependencies, - optionalDependencies: pkg.optionalDependencies, - permissions: ref.permissions, - prebuiltVariants: pkg.prebuiltVariants - }); - - lockfile[pattern] = obj; - - if (remoteKey) { - seen.set(remoteKey, obj); - } - } - - return lockfile; - } -} -exports.default = Lockfile; - -/***/ }), -/* 15 */, -/* 16 */, -/* 17 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("stream"); - -/***/ }), -/* 18 */, -/* 19 */, -/* 20 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.default = nullify; -function nullify(obj = {}) { - if (Array.isArray(obj)) { - for (var _iterator = obj, _isArray = Array.isArray(_iterator), _i = 0, _iterator = _isArray ? _iterator : _iterator[Symbol.iterator]();;) { - var _ref; - - if (_isArray) { - if (_i >= _iterator.length) break; - _ref = _iterator[_i++]; - } else { - _i = _iterator.next(); - if (_i.done) break; - _ref = _i.value; - } - - const item = _ref; - - nullify(item); - } - } else if (obj !== null && typeof obj === 'object' || typeof obj === 'function') { - Object.setPrototypeOf(obj, null); - - // for..in can only be applied to 'object', not 'function' - if (typeof obj === 'object') { - for (const key in obj) { - nullify(obj[key]); - } - } - } - - return obj; -} - -/***/ }), -/* 21 */, -/* 22 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("assert"); - -/***/ }), -/* 23 */ -/***/ (function(module, exports) { - -var core = module.exports = { version: '2.5.7' }; -if (typeof __e == 'number') __e = core; // eslint-disable-line no-undef - - -/***/ }), -/* 24 */, -/* 25 */, -/* 26 */, -/* 27 */ -/***/ (function(module, exports, __webpack_require__) { - -var isObject = __webpack_require__(34); -module.exports = function (it) { - if (!isObject(it)) throw TypeError(it + ' is not an object!'); - return it; -}; - - -/***/ }), -/* 28 */, -/* 29 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.normalizePattern = normalizePattern; - -/** - * Explode and normalize a pattern into its name and range. - */ - -function normalizePattern(pattern) { - let hasVersion = false; - let range = 'latest'; - let name = pattern; - - // if we're a scope then remove the @ and add it back later - let isScoped = false; - if (name[0] === '@') { - isScoped = true; - name = name.slice(1); - } - - // take first part as the name - const parts = name.split('@'); - if (parts.length > 1) { - name = parts.shift(); - range = parts.join('@'); - - if (range) { - hasVersion = true; - } else { - range = '*'; - } - } - - // add back @ scope suffix - if (isScoped) { - name = `@${name}`; - } - - return { name, range, hasVersion }; -} - -/***/ }), -/* 30 */, -/* 31 */ -/***/ (function(module, exports, __webpack_require__) { - -var dP = __webpack_require__(50); -var createDesc = __webpack_require__(106); -module.exports = __webpack_require__(33) ? function (object, key, value) { - return dP.f(object, key, createDesc(1, value)); -} : function (object, key, value) { - object[key] = value; - return object; -}; - - -/***/ }), -/* 32 */ -/***/ (function(module, exports, __webpack_require__) { - -/* eslint-disable node/no-deprecated-api */ -var buffer = __webpack_require__(63) -var Buffer = buffer.Buffer - -// alternative to using Object.keys for old browsers -function copyProps (src, dst) { - for (var key in src) { - dst[key] = src[key] - } -} -if (Buffer.from && Buffer.alloc && Buffer.allocUnsafe && Buffer.allocUnsafeSlow) { - module.exports = buffer -} else { - // Copy properties from require('buffer') - copyProps(buffer, exports) - exports.Buffer = SafeBuffer -} - -function SafeBuffer (arg, encodingOrOffset, length) { - return Buffer(arg, encodingOrOffset, length) -} - -// Copy static methods from Buffer -copyProps(Buffer, SafeBuffer) - -SafeBuffer.from = function (arg, encodingOrOffset, length) { - if (typeof arg === 'number') { - throw new TypeError('Argument must not be a number') - } - return Buffer(arg, encodingOrOffset, length) -} - -SafeBuffer.alloc = function (size, fill, encoding) { - if (typeof size !== 'number') { - throw new TypeError('Argument must be a number') - } - var buf = Buffer(size) - if (fill !== undefined) { - if (typeof encoding === 'string') { - buf.fill(fill, encoding) - } else { - buf.fill(fill) - } - } else { - buf.fill(0) - } - return buf -} - -SafeBuffer.allocUnsafe = function (size) { - if (typeof size !== 'number') { - throw new TypeError('Argument must be a number') - } - return Buffer(size) -} - -SafeBuffer.allocUnsafeSlow = function (size) { - if (typeof size !== 'number') { - throw new TypeError('Argument must be a number') - } - return buffer.SlowBuffer(size) -} - - -/***/ }), -/* 33 */ -/***/ (function(module, exports, __webpack_require__) { - -// Thank's IE8 for his funny defineProperty -module.exports = !__webpack_require__(85)(function () { - return Object.defineProperty({}, 'a', { get: function () { return 7; } }).a != 7; -}); - - -/***/ }), -/* 34 */ -/***/ (function(module, exports) { - -module.exports = function (it) { - return typeof it === 'object' ? it !== null : typeof it === 'function'; -}; - - -/***/ }), -/* 35 */ -/***/ (function(module, exports) { - -module.exports = {}; - - -/***/ }), -/* 36 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("os"); - -/***/ }), -/* 37 */, -/* 38 */, -/* 39 */, -/* 40 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.wait = wait; -exports.promisify = promisify; -exports.queue = queue; -function wait(delay) { - return new Promise(resolve => { - setTimeout(resolve, delay); - }); -} - -function promisify(fn, firstData) { - return function (...args) { - return new Promise(function (resolve, reject) { - args.push(function (err, ...result) { - let res = result; - - if (result.length <= 1) { - res = result[0]; - } - - if (firstData) { - res = err; - err = null; - } - - if (err) { - reject(err); - } else { - resolve(res); - } - }); - - fn.apply(null, args); - }); - }; -} - -function queue(arr, promiseProducer, concurrency = Infinity) { - concurrency = Math.min(concurrency, arr.length); - - // clone - arr = arr.slice(); - - const results = []; - let total = arr.length; - if (!total) { - return Promise.resolve(results); - } - - return new Promise((resolve, reject) => { - for (let i = 0; i < concurrency; i++) { - next(); - } - - function next() { - const item = arr.shift(); - const promise = promiseProducer(item); - - promise.then(function (result) { - results.push(result); - - total--; - if (total === 0) { - resolve(results); - } else { - if (arr.length) { - next(); - } - } - }, reject); - } - }); -} - -/***/ }), -/* 41 */ -/***/ (function(module, exports, __webpack_require__) { - -var global = __webpack_require__(11); -var core = __webpack_require__(23); -var ctx = __webpack_require__(48); -var hide = __webpack_require__(31); -var has = __webpack_require__(49); -var PROTOTYPE = 'prototype'; - -var $export = function (type, name, source) { - var IS_FORCED = type & $export.F; - var IS_GLOBAL = type & $export.G; - var IS_STATIC = type & $export.S; - var IS_PROTO = type & $export.P; - var IS_BIND = type & $export.B; - var IS_WRAP = type & $export.W; - var exports = IS_GLOBAL ? core : core[name] || (core[name] = {}); - var expProto = exports[PROTOTYPE]; - var target = IS_GLOBAL ? global : IS_STATIC ? global[name] : (global[name] || {})[PROTOTYPE]; - var key, own, out; - if (IS_GLOBAL) source = name; - for (key in source) { - // contains in native - own = !IS_FORCED && target && target[key] !== undefined; - if (own && has(exports, key)) continue; - // export native or passed - out = own ? target[key] : source[key]; - // prevent global pollution for namespaces - exports[key] = IS_GLOBAL && typeof target[key] != 'function' ? source[key] - // bind timers to global for call from export context - : IS_BIND && own ? ctx(out, global) - // wrap global constructors for prevent change them in library - : IS_WRAP && target[key] == out ? (function (C) { - var F = function (a, b, c) { - if (this instanceof C) { - switch (arguments.length) { - case 0: return new C(); - case 1: return new C(a); - case 2: return new C(a, b); - } return new C(a, b, c); - } return C.apply(this, arguments); - }; - F[PROTOTYPE] = C[PROTOTYPE]; - return F; - // make static versions for prototype methods - })(out) : IS_PROTO && typeof out == 'function' ? ctx(Function.call, out) : out; - // export proto methods to core.%CONSTRUCTOR%.methods.%NAME% - if (IS_PROTO) { - (exports.virtual || (exports.virtual = {}))[key] = out; - // export proto methods to core.%CONSTRUCTOR%.prototype.%NAME% - if (type & $export.R && expProto && !expProto[key]) hide(expProto, key, out); - } - } -}; -// type bitmap -$export.F = 1; // forced -$export.G = 2; // global -$export.S = 4; // static -$export.P = 8; // proto -$export.B = 16; // bind -$export.W = 32; // wrap -$export.U = 64; // safe -$export.R = 128; // real proto method for `library` -module.exports = $export; - - -/***/ }), -/* 42 */ -/***/ (function(module, exports, __webpack_require__) { - -try { - var util = __webpack_require__(2); - if (typeof util.inherits !== 'function') throw ''; - module.exports = util.inherits; -} catch (e) { - module.exports = __webpack_require__(224); -} - - -/***/ }), -/* 43 */, -/* 44 */, -/* 45 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.home = undefined; - -var _rootUser; - -function _load_rootUser() { - return _rootUser = _interopRequireDefault(__webpack_require__(169)); -} - -function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } - -const path = __webpack_require__(0); - -const home = exports.home = __webpack_require__(36).homedir(); - -const userHomeDir = (_rootUser || _load_rootUser()).default ? path.resolve('/usr/local/share') : home; - -exports.default = userHomeDir; - -/***/ }), -/* 46 */ -/***/ (function(module, exports) { - -module.exports = function (it) { - if (typeof it != 'function') throw TypeError(it + ' is not a function!'); - return it; -}; - - -/***/ }), -/* 47 */ -/***/ (function(module, exports) { - -var toString = {}.toString; - -module.exports = function (it) { - return toString.call(it).slice(8, -1); -}; - - -/***/ }), -/* 48 */ -/***/ (function(module, exports, __webpack_require__) { - -// optional / simple context binding -var aFunction = __webpack_require__(46); -module.exports = function (fn, that, length) { - aFunction(fn); - if (that === undefined) return fn; - switch (length) { - case 1: return function (a) { - return fn.call(that, a); - }; - case 2: return function (a, b) { - return fn.call(that, a, b); - }; - case 3: return function (a, b, c) { - return fn.call(that, a, b, c); - }; - } - return function (/* ...args */) { - return fn.apply(that, arguments); - }; -}; - - -/***/ }), -/* 49 */ -/***/ (function(module, exports) { - -var hasOwnProperty = {}.hasOwnProperty; -module.exports = function (it, key) { - return hasOwnProperty.call(it, key); -}; - - -/***/ }), -/* 50 */ -/***/ (function(module, exports, __webpack_require__) { - -var anObject = __webpack_require__(27); -var IE8_DOM_DEFINE = __webpack_require__(184); -var toPrimitive = __webpack_require__(201); -var dP = Object.defineProperty; - -exports.f = __webpack_require__(33) ? Object.defineProperty : function defineProperty(O, P, Attributes) { - anObject(O); - P = toPrimitive(P, true); - anObject(Attributes); - if (IE8_DOM_DEFINE) try { - return dP(O, P, Attributes); - } catch (e) { /* empty */ } - if ('get' in Attributes || 'set' in Attributes) throw TypeError('Accessors not supported!'); - if ('value' in Attributes) O[P] = Attributes.value; - return O; -}; - - -/***/ }), -/* 51 */, -/* 52 */, -/* 53 */, -/* 54 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("events"); - -/***/ }), -/* 55 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const Buffer = __webpack_require__(32).Buffer - -const crypto = __webpack_require__(9) -const Transform = __webpack_require__(17).Transform - -const SPEC_ALGORITHMS = ['sha256', 'sha384', 'sha512'] - -const BASE64_REGEX = /^[a-z0-9+/]+(?:=?=?)$/i -const SRI_REGEX = /^([^-]+)-([^?]+)([?\S*]*)$/ -const STRICT_SRI_REGEX = /^([^-]+)-([A-Za-z0-9+/=]{44,88})(\?[\x21-\x7E]*)*$/ -const VCHAR_REGEX = /^[\x21-\x7E]+$/ - -class Hash { - get isHash () { return true } - constructor (hash, opts) { - const strict = !!(opts && opts.strict) - this.source = hash.trim() - // 3.1. Integrity metadata (called "Hash" by ssri) - // https://w3c.github.io/webappsec-subresource-integrity/#integrity-metadata-description - const match = this.source.match( - strict - ? STRICT_SRI_REGEX - : SRI_REGEX - ) - if (!match) { return } - if (strict && !SPEC_ALGORITHMS.some(a => a === match[1])) { return } - this.algorithm = match[1] - this.digest = match[2] - - const rawOpts = match[3] - this.options = rawOpts ? rawOpts.slice(1).split('?') : [] - } - hexDigest () { - return this.digest && Buffer.from(this.digest, 'base64').toString('hex') - } - toJSON () { - return this.toString() - } - toString (opts) { - if (opts && opts.strict) { - // Strict mode enforces the standard as close to the foot of the - // letter as it can. - if (!( - // The spec has very restricted productions for algorithms. - // https://www.w3.org/TR/CSP2/#source-list-syntax - SPEC_ALGORITHMS.some(x => x === this.algorithm) && - // Usually, if someone insists on using a "different" base64, we - // leave it as-is, since there's multiple standards, and the - // specified is not a URL-safe variant. - // https://www.w3.org/TR/CSP2/#base64_value - this.digest.match(BASE64_REGEX) && - // Option syntax is strictly visual chars. - // https://w3c.github.io/webappsec-subresource-integrity/#grammardef-option-expression - // https://tools.ietf.org/html/rfc5234#appendix-B.1 - (this.options || []).every(opt => opt.match(VCHAR_REGEX)) - )) { - return '' - } - } - const options = this.options && this.options.length - ? `?${this.options.join('?')}` - : '' - return `${this.algorithm}-${this.digest}${options}` - } -} - -class Integrity { - get isIntegrity () { return true } - toJSON () { - return this.toString() - } - toString (opts) { - opts = opts || {} - let sep = opts.sep || ' ' - if (opts.strict) { - // Entries must be separated by whitespace, according to spec. - sep = sep.replace(/\S+/g, ' ') - } - return Object.keys(this).map(k => { - return this[k].map(hash => { - return Hash.prototype.toString.call(hash, opts) - }).filter(x => x.length).join(sep) - }).filter(x => x.length).join(sep) - } - concat (integrity, opts) { - const other = typeof integrity === 'string' - ? integrity - : stringify(integrity, opts) - return parse(`${this.toString(opts)} ${other}`, opts) - } - hexDigest () { - return parse(this, {single: true}).hexDigest() - } - match (integrity, opts) { - const other = parse(integrity, opts) - const algo = other.pickAlgorithm(opts) - return ( - this[algo] && - other[algo] && - this[algo].find(hash => - other[algo].find(otherhash => - hash.digest === otherhash.digest - ) - ) - ) || false - } - pickAlgorithm (opts) { - const pickAlgorithm = (opts && opts.pickAlgorithm) || getPrioritizedHash - const keys = Object.keys(this) - if (!keys.length) { - throw new Error(`No algorithms available for ${ - JSON.stringify(this.toString()) - }`) - } - return keys.reduce((acc, algo) => { - return pickAlgorithm(acc, algo) || acc - }) - } -} - -module.exports.parse = parse -function parse (sri, opts) { - opts = opts || {} - if (typeof sri === 'string') { - return _parse(sri, opts) - } else if (sri.algorithm && sri.digest) { - const fullSri = new Integrity() - fullSri[sri.algorithm] = [sri] - return _parse(stringify(fullSri, opts), opts) - } else { - return _parse(stringify(sri, opts), opts) - } -} - -function _parse (integrity, opts) { - // 3.4.3. Parse metadata - // https://w3c.github.io/webappsec-subresource-integrity/#parse-metadata - if (opts.single) { - return new Hash(integrity, opts) - } - return integrity.trim().split(/\s+/).reduce((acc, string) => { - const hash = new Hash(string, opts) - if (hash.algorithm && hash.digest) { - const algo = hash.algorithm - if (!acc[algo]) { acc[algo] = [] } - acc[algo].push(hash) - } - return acc - }, new Integrity()) -} - -module.exports.stringify = stringify -function stringify (obj, opts) { - if (obj.algorithm && obj.digest) { - return Hash.prototype.toString.call(obj, opts) - } else if (typeof obj === 'string') { - return stringify(parse(obj, opts), opts) - } else { - return Integrity.prototype.toString.call(obj, opts) - } -} - -module.exports.fromHex = fromHex -function fromHex (hexDigest, algorithm, opts) { - const optString = (opts && opts.options && opts.options.length) - ? `?${opts.options.join('?')}` - : '' - return parse( - `${algorithm}-${ - Buffer.from(hexDigest, 'hex').toString('base64') - }${optString}`, opts - ) -} - -module.exports.fromData = fromData -function fromData (data, opts) { - opts = opts || {} - const algorithms = opts.algorithms || ['sha512'] - const optString = opts.options && opts.options.length - ? `?${opts.options.join('?')}` - : '' - return algorithms.reduce((acc, algo) => { - const digest = crypto.createHash(algo).update(data).digest('base64') - const hash = new Hash( - `${algo}-${digest}${optString}`, - opts - ) - if (hash.algorithm && hash.digest) { - const algo = hash.algorithm - if (!acc[algo]) { acc[algo] = [] } - acc[algo].push(hash) - } - return acc - }, new Integrity()) -} - -module.exports.fromStream = fromStream -function fromStream (stream, opts) { - opts = opts || {} - const P = opts.Promise || Promise - const istream = integrityStream(opts) - return new P((resolve, reject) => { - stream.pipe(istream) - stream.on('error', reject) - istream.on('error', reject) - let sri - istream.on('integrity', s => { sri = s }) - istream.on('end', () => resolve(sri)) - istream.on('data', () => {}) - }) -} - -module.exports.checkData = checkData -function checkData (data, sri, opts) { - opts = opts || {} - sri = parse(sri, opts) - if (!Object.keys(sri).length) { - if (opts.error) { - throw Object.assign( - new Error('No valid integrity hashes to check against'), { - code: 'EINTEGRITY' - } - ) - } else { - return false - } - } - const algorithm = sri.pickAlgorithm(opts) - const digest = crypto.createHash(algorithm).update(data).digest('base64') - const newSri = parse({algorithm, digest}) - const match = newSri.match(sri, opts) - if (match || !opts.error) { - return match - } else if (typeof opts.size === 'number' && (data.length !== opts.size)) { - const err = new Error(`data size mismatch when checking ${sri}.\n Wanted: ${opts.size}\n Found: ${data.length}`) - err.code = 'EBADSIZE' - err.found = data.length - err.expected = opts.size - err.sri = sri - throw err - } else { - const err = new Error(`Integrity checksum failed when using ${algorithm}: Wanted ${sri}, but got ${newSri}. (${data.length} bytes)`) - err.code = 'EINTEGRITY' - err.found = newSri - err.expected = sri - err.algorithm = algorithm - err.sri = sri - throw err - } -} - -module.exports.checkStream = checkStream -function checkStream (stream, sri, opts) { - opts = opts || {} - const P = opts.Promise || Promise - const checker = integrityStream(Object.assign({}, opts, { - integrity: sri - })) - return new P((resolve, reject) => { - stream.pipe(checker) - stream.on('error', reject) - checker.on('error', reject) - let sri - checker.on('verified', s => { sri = s }) - checker.on('end', () => resolve(sri)) - checker.on('data', () => {}) - }) -} - -module.exports.integrityStream = integrityStream -function integrityStream (opts) { - opts = opts || {} - // For verification - const sri = opts.integrity && parse(opts.integrity, opts) - const goodSri = sri && Object.keys(sri).length - const algorithm = goodSri && sri.pickAlgorithm(opts) - const digests = goodSri && sri[algorithm] - // Calculating stream - const algorithms = Array.from( - new Set( - (opts.algorithms || ['sha512']) - .concat(algorithm ? [algorithm] : []) - ) - ) - const hashes = algorithms.map(crypto.createHash) - let streamSize = 0 - const stream = new Transform({ - transform (chunk, enc, cb) { - streamSize += chunk.length - hashes.forEach(h => h.update(chunk, enc)) - cb(null, chunk, enc) - } - }).on('end', () => { - const optString = (opts.options && opts.options.length) - ? `?${opts.options.join('?')}` - : '' - const newSri = parse(hashes.map((h, i) => { - return `${algorithms[i]}-${h.digest('base64')}${optString}` - }).join(' '), opts) - // Integrity verification mode - const match = goodSri && newSri.match(sri, opts) - if (typeof opts.size === 'number' && streamSize !== opts.size) { - const err = new Error(`stream size mismatch when checking ${sri}.\n Wanted: ${opts.size}\n Found: ${streamSize}`) - err.code = 'EBADSIZE' - err.found = streamSize - err.expected = opts.size - err.sri = sri - stream.emit('error', err) - } else if (opts.integrity && !match) { - const err = new Error(`${sri} integrity checksum failed when using ${algorithm}: wanted ${digests} but got ${newSri}. (${streamSize} bytes)`) - err.code = 'EINTEGRITY' - err.found = newSri - err.expected = digests - err.algorithm = algorithm - err.sri = sri - stream.emit('error', err) - } else { - stream.emit('size', streamSize) - stream.emit('integrity', newSri) - match && stream.emit('verified', match) - } - }) - return stream -} - -module.exports.create = createIntegrity -function createIntegrity (opts) { - opts = opts || {} - const algorithms = opts.algorithms || ['sha512'] - const optString = opts.options && opts.options.length - ? `?${opts.options.join('?')}` - : '' - - const hashes = algorithms.map(crypto.createHash) - - return { - update: function (chunk, enc) { - hashes.forEach(h => h.update(chunk, enc)) - return this - }, - digest: function (enc) { - const integrity = algorithms.reduce((acc, algo) => { - const digest = hashes.shift().digest('base64') - const hash = new Hash( - `${algo}-${digest}${optString}`, - opts - ) - if (hash.algorithm && hash.digest) { - const algo = hash.algorithm - if (!acc[algo]) { acc[algo] = [] } - acc[algo].push(hash) - } - return acc - }, new Integrity()) - - return integrity - } - } -} - -const NODE_HASHES = new Set(crypto.getHashes()) - -// This is a Best Effort™ at a reasonable priority for hash algos -const DEFAULT_PRIORITY = [ - 'md5', 'whirlpool', 'sha1', 'sha224', 'sha256', 'sha384', 'sha512', - // TODO - it's unclear _which_ of these Node will actually use as its name - // for the algorithm, so we guesswork it based on the OpenSSL names. - 'sha3', - 'sha3-256', 'sha3-384', 'sha3-512', - 'sha3_256', 'sha3_384', 'sha3_512' -].filter(algo => NODE_HASHES.has(algo)) - -function getPrioritizedHash (algo1, algo2) { - return DEFAULT_PRIORITY.indexOf(algo1.toLowerCase()) >= DEFAULT_PRIORITY.indexOf(algo2.toLowerCase()) - ? algo1 - : algo2 -} - - -/***/ }), -/* 56 */, -/* 57 */, -/* 58 */, -/* 59 */, -/* 60 */ -/***/ (function(module, exports, __webpack_require__) { - -module.exports = minimatch -minimatch.Minimatch = Minimatch - -var path = { sep: '/' } -try { - path = __webpack_require__(0) -} catch (er) {} - -var GLOBSTAR = minimatch.GLOBSTAR = Minimatch.GLOBSTAR = {} -var expand = __webpack_require__(175) - -var plTypes = { - '!': { open: '(?:(?!(?:', close: '))[^/]*?)'}, - '?': { open: '(?:', close: ')?' }, - '+': { open: '(?:', close: ')+' }, - '*': { open: '(?:', close: ')*' }, - '@': { open: '(?:', close: ')' } -} - -// any single thing other than / -// don't need to escape / when using new RegExp() -var qmark = '[^/]' - -// * => any number of characters -var star = qmark + '*?' - -// ** when dots are allowed. Anything goes, except .. and . -// not (^ or / followed by one or two dots followed by $ or /), -// followed by anything, any number of times. -var twoStarDot = '(?:(?!(?:\\\/|^)(?:\\.{1,2})($|\\\/)).)*?' - -// not a ^ or / followed by a dot, -// followed by anything, any number of times. -var twoStarNoDot = '(?:(?!(?:\\\/|^)\\.).)*?' - -// characters that need to be escaped in RegExp. -var reSpecials = charSet('().*{}+?[]^$\\!') - -// "abc" -> { a:true, b:true, c:true } -function charSet (s) { - return s.split('').reduce(function (set, c) { - set[c] = true - return set - }, {}) -} - -// normalizes slashes. -var slashSplit = /\/+/ - -minimatch.filter = filter -function filter (pattern, options) { - options = options || {} - return function (p, i, list) { - return minimatch(p, pattern, options) - } -} - -function ext (a, b) { - a = a || {} - b = b || {} - var t = {} - Object.keys(b).forEach(function (k) { - t[k] = b[k] - }) - Object.keys(a).forEach(function (k) { - t[k] = a[k] - }) - return t -} - -minimatch.defaults = function (def) { - if (!def || !Object.keys(def).length) return minimatch - - var orig = minimatch - - var m = function minimatch (p, pattern, options) { - return orig.minimatch(p, pattern, ext(def, options)) - } - - m.Minimatch = function Minimatch (pattern, options) { - return new orig.Minimatch(pattern, ext(def, options)) - } - - return m -} - -Minimatch.defaults = function (def) { - if (!def || !Object.keys(def).length) return Minimatch - return minimatch.defaults(def).Minimatch -} - -function minimatch (p, pattern, options) { - if (typeof pattern !== 'string') { - throw new TypeError('glob pattern string required') - } - - if (!options) options = {} - - // shortcut: comments match nothing. - if (!options.nocomment && pattern.charAt(0) === '#') { - return false - } - - // "" only matches "" - if (pattern.trim() === '') return p === '' - - return new Minimatch(pattern, options).match(p) -} - -function Minimatch (pattern, options) { - if (!(this instanceof Minimatch)) { - return new Minimatch(pattern, options) - } - - if (typeof pattern !== 'string') { - throw new TypeError('glob pattern string required') - } - - if (!options) options = {} - pattern = pattern.trim() - - // windows support: need to use /, not \ - if (path.sep !== '/') { - pattern = pattern.split(path.sep).join('/') - } - - this.options = options - this.set = [] - this.pattern = pattern - this.regexp = null - this.negate = false - this.comment = false - this.empty = false - - // make the set of regexps etc. - this.make() -} - -Minimatch.prototype.debug = function () {} - -Minimatch.prototype.make = make -function make () { - // don't do it more than once. - if (this._made) return - - var pattern = this.pattern - var options = this.options - - // empty patterns and comments match nothing. - if (!options.nocomment && pattern.charAt(0) === '#') { - this.comment = true - return - } - if (!pattern) { - this.empty = true - return - } - - // step 1: figure out negation, etc. - this.parseNegate() - - // step 2: expand braces - var set = this.globSet = this.braceExpand() - - if (options.debug) this.debug = console.error - - this.debug(this.pattern, set) - - // step 3: now we have a set, so turn each one into a series of path-portion - // matching patterns. - // These will be regexps, except in the case of "**", which is - // set to the GLOBSTAR object for globstar behavior, - // and will not contain any / characters - set = this.globParts = set.map(function (s) { - return s.split(slashSplit) - }) - - this.debug(this.pattern, set) - - // glob --> regexps - set = set.map(function (s, si, set) { - return s.map(this.parse, this) - }, this) - - this.debug(this.pattern, set) - - // filter out everything that didn't compile properly. - set = set.filter(function (s) { - return s.indexOf(false) === -1 - }) - - this.debug(this.pattern, set) - - this.set = set -} - -Minimatch.prototype.parseNegate = parseNegate -function parseNegate () { - var pattern = this.pattern - var negate = false - var options = this.options - var negateOffset = 0 - - if (options.nonegate) return - - for (var i = 0, l = pattern.length - ; i < l && pattern.charAt(i) === '!' - ; i++) { - negate = !negate - negateOffset++ - } - - if (negateOffset) this.pattern = pattern.substr(negateOffset) - this.negate = negate -} - -// Brace expansion: -// a{b,c}d -> abd acd -// a{b,}c -> abc ac -// a{0..3}d -> a0d a1d a2d a3d -// a{b,c{d,e}f}g -> abg acdfg acefg -// a{b,c}d{e,f}g -> abdeg acdeg abdeg abdfg -// -// Invalid sets are not expanded. -// a{2..}b -> a{2..}b -// a{b}c -> a{b}c -minimatch.braceExpand = function (pattern, options) { - return braceExpand(pattern, options) -} - -Minimatch.prototype.braceExpand = braceExpand - -function braceExpand (pattern, options) { - if (!options) { - if (this instanceof Minimatch) { - options = this.options - } else { - options = {} - } - } - - pattern = typeof pattern === 'undefined' - ? this.pattern : pattern - - if (typeof pattern === 'undefined') { - throw new TypeError('undefined pattern') - } - - if (options.nobrace || - !pattern.match(/\{.*\}/)) { - // shortcut. no need to expand. - return [pattern] - } - - return expand(pattern) -} - -// parse a component of the expanded set. -// At this point, no pattern may contain "/" in it -// so we're going to return a 2d array, where each entry is the full -// pattern, split on '/', and then turned into a regular expression. -// A regexp is made at the end which joins each array with an -// escaped /, and another full one which joins each regexp with |. -// -// Following the lead of Bash 4.1, note that "**" only has special meaning -// when it is the *only* thing in a path portion. Otherwise, any series -// of * is equivalent to a single *. Globstar behavior is enabled by -// default, and can be disabled by setting options.noglobstar. -Minimatch.prototype.parse = parse -var SUBPARSE = {} -function parse (pattern, isSub) { - if (pattern.length > 1024 * 64) { - throw new TypeError('pattern is too long') - } - - var options = this.options - - // shortcuts - if (!options.noglobstar && pattern === '**') return GLOBSTAR - if (pattern === '') return '' - - var re = '' - var hasMagic = !!options.nocase - var escaping = false - // ? => one single character - var patternListStack = [] - var negativeLists = [] - var stateChar - var inClass = false - var reClassStart = -1 - var classStart = -1 - // . and .. never match anything that doesn't start with ., - // even when options.dot is set. - var patternStart = pattern.charAt(0) === '.' ? '' // anything - // not (start or / followed by . or .. followed by / or end) - : options.dot ? '(?!(?:^|\\\/)\\.{1,2}(?:$|\\\/))' - : '(?!\\.)' - var self = this - - function clearStateChar () { - if (stateChar) { - // we had some state-tracking character - // that wasn't consumed by this pass. - switch (stateChar) { - case '*': - re += star - hasMagic = true - break - case '?': - re += qmark - hasMagic = true - break - default: - re += '\\' + stateChar - break - } - self.debug('clearStateChar %j %j', stateChar, re) - stateChar = false - } - } - - for (var i = 0, len = pattern.length, c - ; (i < len) && (c = pattern.charAt(i)) - ; i++) { - this.debug('%s\t%s %s %j', pattern, i, re, c) - - // skip over any that are escaped. - if (escaping && reSpecials[c]) { - re += '\\' + c - escaping = false - continue - } - - switch (c) { - case '/': - // completely not allowed, even escaped. - // Should already be path-split by now. - return false - - case '\\': - clearStateChar() - escaping = true - continue - - // the various stateChar values - // for the "extglob" stuff. - case '?': - case '*': - case '+': - case '@': - case '!': - this.debug('%s\t%s %s %j <-- stateChar', pattern, i, re, c) - - // all of those are literals inside a class, except that - // the glob [!a] means [^a] in regexp - if (inClass) { - this.debug(' in class') - if (c === '!' && i === classStart + 1) c = '^' - re += c - continue - } - - // if we already have a stateChar, then it means - // that there was something like ** or +? in there. - // Handle the stateChar, then proceed with this one. - self.debug('call clearStateChar %j', stateChar) - clearStateChar() - stateChar = c - // if extglob is disabled, then +(asdf|foo) isn't a thing. - // just clear the statechar *now*, rather than even diving into - // the patternList stuff. - if (options.noext) clearStateChar() - continue - - case '(': - if (inClass) { - re += '(' - continue - } - - if (!stateChar) { - re += '\\(' - continue - } - - patternListStack.push({ - type: stateChar, - start: i - 1, - reStart: re.length, - open: plTypes[stateChar].open, - close: plTypes[stateChar].close - }) - // negation is (?:(?!js)[^/]*) - re += stateChar === '!' ? '(?:(?!(?:' : '(?:' - this.debug('plType %j %j', stateChar, re) - stateChar = false - continue - - case ')': - if (inClass || !patternListStack.length) { - re += '\\)' - continue - } - - clearStateChar() - hasMagic = true - var pl = patternListStack.pop() - // negation is (?:(?!js)[^/]*) - // The others are (?:) - re += pl.close - if (pl.type === '!') { - negativeLists.push(pl) - } - pl.reEnd = re.length - continue - - case '|': - if (inClass || !patternListStack.length || escaping) { - re += '\\|' - escaping = false - continue - } - - clearStateChar() - re += '|' - continue - - // these are mostly the same in regexp and glob - case '[': - // swallow any state-tracking char before the [ - clearStateChar() - - if (inClass) { - re += '\\' + c - continue - } - - inClass = true - classStart = i - reClassStart = re.length - re += c - continue - - case ']': - // a right bracket shall lose its special - // meaning and represent itself in - // a bracket expression if it occurs - // first in the list. -- POSIX.2 2.8.3.2 - if (i === classStart + 1 || !inClass) { - re += '\\' + c - escaping = false - continue - } - - // handle the case where we left a class open. - // "[z-a]" is valid, equivalent to "\[z-a\]" - if (inClass) { - // split where the last [ was, make sure we don't have - // an invalid re. if so, re-walk the contents of the - // would-be class to re-translate any characters that - // were passed through as-is - // TODO: It would probably be faster to determine this - // without a try/catch and a new RegExp, but it's tricky - // to do safely. For now, this is safe and works. - var cs = pattern.substring(classStart + 1, i) - try { - RegExp('[' + cs + ']') - } catch (er) { - // not a valid class! - var sp = this.parse(cs, SUBPARSE) - re = re.substr(0, reClassStart) + '\\[' + sp[0] + '\\]' - hasMagic = hasMagic || sp[1] - inClass = false - continue - } - } - - // finish up the class. - hasMagic = true - inClass = false - re += c - continue - - default: - // swallow any state char that wasn't consumed - clearStateChar() - - if (escaping) { - // no need - escaping = false - } else if (reSpecials[c] - && !(c === '^' && inClass)) { - re += '\\' - } - - re += c - - } // switch - } // for - - // handle the case where we left a class open. - // "[abc" is valid, equivalent to "\[abc" - if (inClass) { - // split where the last [ was, and escape it - // this is a huge pita. We now have to re-walk - // the contents of the would-be class to re-translate - // any characters that were passed through as-is - cs = pattern.substr(classStart + 1) - sp = this.parse(cs, SUBPARSE) - re = re.substr(0, reClassStart) + '\\[' + sp[0] - hasMagic = hasMagic || sp[1] - } - - // handle the case where we had a +( thing at the *end* - // of the pattern. - // each pattern list stack adds 3 chars, and we need to go through - // and escape any | chars that were passed through as-is for the regexp. - // Go through and escape them, taking care not to double-escape any - // | chars that were already escaped. - for (pl = patternListStack.pop(); pl; pl = patternListStack.pop()) { - var tail = re.slice(pl.reStart + pl.open.length) - this.debug('setting tail', re, pl) - // maybe some even number of \, then maybe 1 \, followed by a | - tail = tail.replace(/((?:\\{2}){0,64})(\\?)\|/g, function (_, $1, $2) { - if (!$2) { - // the | isn't already escaped, so escape it. - $2 = '\\' - } - - // need to escape all those slashes *again*, without escaping the - // one that we need for escaping the | character. As it works out, - // escaping an even number of slashes can be done by simply repeating - // it exactly after itself. That's why this trick works. - // - // I am sorry that you have to see this. - return $1 + $1 + $2 + '|' - }) - - this.debug('tail=%j\n %s', tail, tail, pl, re) - var t = pl.type === '*' ? star - : pl.type === '?' ? qmark - : '\\' + pl.type - - hasMagic = true - re = re.slice(0, pl.reStart) + t + '\\(' + tail - } - - // handle trailing things that only matter at the very end. - clearStateChar() - if (escaping) { - // trailing \\ - re += '\\\\' - } - - // only need to apply the nodot start if the re starts with - // something that could conceivably capture a dot - var addPatternStart = false - switch (re.charAt(0)) { - case '.': - case '[': - case '(': addPatternStart = true - } - - // Hack to work around lack of negative lookbehind in JS - // A pattern like: *.!(x).!(y|z) needs to ensure that a name - // like 'a.xyz.yz' doesn't match. So, the first negative - // lookahead, has to look ALL the way ahead, to the end of - // the pattern. - for (var n = negativeLists.length - 1; n > -1; n--) { - var nl = negativeLists[n] - - var nlBefore = re.slice(0, nl.reStart) - var nlFirst = re.slice(nl.reStart, nl.reEnd - 8) - var nlLast = re.slice(nl.reEnd - 8, nl.reEnd) - var nlAfter = re.slice(nl.reEnd) - - nlLast += nlAfter - - // Handle nested stuff like *(*.js|!(*.json)), where open parens - // mean that we should *not* include the ) in the bit that is considered - // "after" the negated section. - var openParensBefore = nlBefore.split('(').length - 1 - var cleanAfter = nlAfter - for (i = 0; i < openParensBefore; i++) { - cleanAfter = cleanAfter.replace(/\)[+*?]?/, '') - } - nlAfter = cleanAfter - - var dollar = '' - if (nlAfter === '' && isSub !== SUBPARSE) { - dollar = '$' - } - var newRe = nlBefore + nlFirst + nlAfter + dollar + nlLast - re = newRe - } - - // if the re is not "" at this point, then we need to make sure - // it doesn't match against an empty path part. - // Otherwise a/* will match a/, which it should not. - if (re !== '' && hasMagic) { - re = '(?=.)' + re - } - - if (addPatternStart) { - re = patternStart + re - } - - // parsing just a piece of a larger pattern. - if (isSub === SUBPARSE) { - return [re, hasMagic] - } - - // skip the regexp for non-magical patterns - // unescape anything in it, though, so that it'll be - // an exact match against a file etc. - if (!hasMagic) { - return globUnescape(pattern) - } - - var flags = options.nocase ? 'i' : '' - try { - var regExp = new RegExp('^' + re + '$', flags) - } catch (er) { - // If it was an invalid regular expression, then it can't match - // anything. This trick looks for a character after the end of - // the string, which is of course impossible, except in multi-line - // mode, but it's not a /m regex. - return new RegExp('$.') - } - - regExp._glob = pattern - regExp._src = re - - return regExp -} - -minimatch.makeRe = function (pattern, options) { - return new Minimatch(pattern, options || {}).makeRe() -} - -Minimatch.prototype.makeRe = makeRe -function makeRe () { - if (this.regexp || this.regexp === false) return this.regexp - - // at this point, this.set is a 2d array of partial - // pattern strings, or "**". - // - // It's better to use .match(). This function shouldn't - // be used, really, but it's pretty convenient sometimes, - // when you just want to work with a regex. - var set = this.set - - if (!set.length) { - this.regexp = false - return this.regexp - } - var options = this.options - - var twoStar = options.noglobstar ? star - : options.dot ? twoStarDot - : twoStarNoDot - var flags = options.nocase ? 'i' : '' - - var re = set.map(function (pattern) { - return pattern.map(function (p) { - return (p === GLOBSTAR) ? twoStar - : (typeof p === 'string') ? regExpEscape(p) - : p._src - }).join('\\\/') - }).join('|') - - // must match entire pattern - // ending in a * or ** will make it less strict. - re = '^(?:' + re + ')$' - - // can match anything, as long as it's not this. - if (this.negate) re = '^(?!' + re + ').*$' - - try { - this.regexp = new RegExp(re, flags) - } catch (ex) { - this.regexp = false - } - return this.regexp -} - -minimatch.match = function (list, pattern, options) { - options = options || {} - var mm = new Minimatch(pattern, options) - list = list.filter(function (f) { - return mm.match(f) - }) - if (mm.options.nonull && !list.length) { - list.push(pattern) - } - return list -} - -Minimatch.prototype.match = match -function match (f, partial) { - this.debug('match', f, this.pattern) - // short-circuit in the case of busted things. - // comments, etc. - if (this.comment) return false - if (this.empty) return f === '' - - if (f === '/' && partial) return true - - var options = this.options - - // windows: need to use /, not \ - if (path.sep !== '/') { - f = f.split(path.sep).join('/') - } - - // treat the test path as a set of pathparts. - f = f.split(slashSplit) - this.debug(this.pattern, 'split', f) - - // just ONE of the pattern sets in this.set needs to match - // in order for it to be valid. If negating, then just one - // match means that we have failed. - // Either way, return on the first hit. - - var set = this.set - this.debug(this.pattern, 'set', set) - - // Find the basename of the path by looking for the last non-empty segment - var filename - var i - for (i = f.length - 1; i >= 0; i--) { - filename = f[i] - if (filename) break - } - - for (i = 0; i < set.length; i++) { - var pattern = set[i] - var file = f - if (options.matchBase && pattern.length === 1) { - file = [filename] - } - var hit = this.matchOne(file, pattern, partial) - if (hit) { - if (options.flipNegate) return true - return !this.negate - } - } - - // didn't get any hits. this is success if it's a negative - // pattern, failure otherwise. - if (options.flipNegate) return false - return this.negate -} - -// set partial to true to test if, for example, -// "/a/b" matches the start of "/*/b/*/d" -// Partial means, if you run out of file before you run -// out of pattern, then that's fine, as long as all -// the parts match. -Minimatch.prototype.matchOne = function (file, pattern, partial) { - var options = this.options - - this.debug('matchOne', - { 'this': this, file: file, pattern: pattern }) - - this.debug('matchOne', file.length, pattern.length) - - for (var fi = 0, - pi = 0, - fl = file.length, - pl = pattern.length - ; (fi < fl) && (pi < pl) - ; fi++, pi++) { - this.debug('matchOne loop') - var p = pattern[pi] - var f = file[fi] - - this.debug(pattern, p, f) - - // should be impossible. - // some invalid regexp stuff in the set. - if (p === false) return false - - if (p === GLOBSTAR) { - this.debug('GLOBSTAR', [pattern, p, f]) - - // "**" - // a/**/b/**/c would match the following: - // a/b/x/y/z/c - // a/x/y/z/b/c - // a/b/x/b/x/c - // a/b/c - // To do this, take the rest of the pattern after - // the **, and see if it would match the file remainder. - // If so, return success. - // If not, the ** "swallows" a segment, and try again. - // This is recursively awful. - // - // a/**/b/**/c matching a/b/x/y/z/c - // - a matches a - // - doublestar - // - matchOne(b/x/y/z/c, b/**/c) - // - b matches b - // - doublestar - // - matchOne(x/y/z/c, c) -> no - // - matchOne(y/z/c, c) -> no - // - matchOne(z/c, c) -> no - // - matchOne(c, c) yes, hit - var fr = fi - var pr = pi + 1 - if (pr === pl) { - this.debug('** at the end') - // a ** at the end will just swallow the rest. - // We have found a match. - // however, it will not swallow /.x, unless - // options.dot is set. - // . and .. are *never* matched by **, for explosively - // exponential reasons. - for (; fi < fl; fi++) { - if (file[fi] === '.' || file[fi] === '..' || - (!options.dot && file[fi].charAt(0) === '.')) return false - } - return true - } - - // ok, let's see if we can swallow whatever we can. - while (fr < fl) { - var swallowee = file[fr] - - this.debug('\nglobstar while', file, fr, pattern, pr, swallowee) - - // XXX remove this slice. Just pass the start index. - if (this.matchOne(file.slice(fr), pattern.slice(pr), partial)) { - this.debug('globstar found match!', fr, fl, swallowee) - // found a match. - return true - } else { - // can't swallow "." or ".." ever. - // can only swallow ".foo" when explicitly asked. - if (swallowee === '.' || swallowee === '..' || - (!options.dot && swallowee.charAt(0) === '.')) { - this.debug('dot detected!', file, fr, pattern, pr) - break - } - - // ** swallows a segment, and continue. - this.debug('globstar swallow a segment, and continue') - fr++ - } - } - - // no match was found. - // However, in partial mode, we can't say this is necessarily over. - // If there's more *pattern* left, then - if (partial) { - // ran out of file - this.debug('\n>>> no match, partial?', file, fr, pattern, pr) - if (fr === fl) return true - } - return false - } - - // something other than ** - // non-magic patterns just have to match exactly - // patterns with magic have been turned into regexps. - var hit - if (typeof p === 'string') { - if (options.nocase) { - hit = f.toLowerCase() === p.toLowerCase() - } else { - hit = f === p - } - this.debug('string match', p, f, hit) - } else { - hit = f.match(p) - this.debug('pattern match', p, f, hit) - } - - if (!hit) return false - } - - // Note: ending in / means that we'll get a final "" - // at the end of the pattern. This can only match a - // corresponding "" at the end of the file. - // If the file ends in /, then it can only match a - // a pattern that ends in /, unless the pattern just - // doesn't have any more for it. But, a/b/ should *not* - // match "a/b/*", even though "" matches against the - // [^/]*? pattern, except in partial mode, where it might - // simply not be reached yet. - // However, a/b/ should still satisfy a/* - - // now either we fell off the end of the pattern, or we're done. - if (fi === fl && pi === pl) { - // ran out of pattern and filename at the same time. - // an exact hit! - return true - } else if (fi === fl) { - // ran out of file, but still had pattern left. - // this is ok if we're doing the match as part of - // a glob fs traversal. - return partial - } else if (pi === pl) { - // ran out of pattern, still have file left. - // this is only acceptable if we're on the very last - // empty segment of a file with a trailing slash. - // a/* should match a/b/ - var emptyFileEnd = (fi === fl - 1) && (file[fi] === '') - return emptyFileEnd - } - - // should be unreachable. - throw new Error('wtf?') -} - -// replace stuff like \* with * -function globUnescape (s) { - return s.replace(/\\(.)/g, '$1') -} - -function regExpEscape (s) { - return s.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, '\\$&') -} - - -/***/ }), -/* 61 */ -/***/ (function(module, exports, __webpack_require__) { - -var wrappy = __webpack_require__(123) -module.exports = wrappy(once) -module.exports.strict = wrappy(onceStrict) - -once.proto = once(function () { - Object.defineProperty(Function.prototype, 'once', { - value: function () { - return once(this) - }, - configurable: true - }) - - Object.defineProperty(Function.prototype, 'onceStrict', { - value: function () { - return onceStrict(this) - }, - configurable: true - }) -}) - -function once (fn) { - var f = function () { - if (f.called) return f.value - f.called = true - return f.value = fn.apply(this, arguments) - } - f.called = false - return f -} - -function onceStrict (fn) { - var f = function () { - if (f.called) - throw new Error(f.onceError) - f.called = true - return f.value = fn.apply(this, arguments) - } - var name = fn.name || 'Function wrapped with `once`' - f.onceError = name + " shouldn't be called more than once" - f.called = false - return f -} - - -/***/ }), -/* 62 */, -/* 63 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("buffer"); - -/***/ }), -/* 64 */, -/* 65 */, -/* 66 */, -/* 67 */ -/***/ (function(module, exports) { - -// 7.2.1 RequireObjectCoercible(argument) -module.exports = function (it) { - if (it == undefined) throw TypeError("Can't call method on " + it); - return it; -}; - - -/***/ }), -/* 68 */ -/***/ (function(module, exports, __webpack_require__) { - -var isObject = __webpack_require__(34); -var document = __webpack_require__(11).document; -// typeof document.createElement is 'object' in old IE -var is = isObject(document) && isObject(document.createElement); -module.exports = function (it) { - return is ? document.createElement(it) : {}; -}; - - -/***/ }), -/* 69 */ -/***/ (function(module, exports) { - -module.exports = true; - - -/***/ }), -/* 70 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -// 25.4.1.5 NewPromiseCapability(C) -var aFunction = __webpack_require__(46); - -function PromiseCapability(C) { - var resolve, reject; - this.promise = new C(function ($$resolve, $$reject) { - if (resolve !== undefined || reject !== undefined) throw TypeError('Bad Promise constructor'); - resolve = $$resolve; - reject = $$reject; - }); - this.resolve = aFunction(resolve); - this.reject = aFunction(reject); -} - -module.exports.f = function (C) { - return new PromiseCapability(C); -}; - - -/***/ }), -/* 71 */ -/***/ (function(module, exports, __webpack_require__) { - -var def = __webpack_require__(50).f; -var has = __webpack_require__(49); -var TAG = __webpack_require__(13)('toStringTag'); - -module.exports = function (it, tag, stat) { - if (it && !has(it = stat ? it : it.prototype, TAG)) def(it, TAG, { configurable: true, value: tag }); -}; - - -/***/ }), -/* 72 */ -/***/ (function(module, exports, __webpack_require__) { - -var shared = __webpack_require__(107)('keys'); -var uid = __webpack_require__(111); -module.exports = function (key) { - return shared[key] || (shared[key] = uid(key)); -}; - - -/***/ }), -/* 73 */ -/***/ (function(module, exports) { - -// 7.1.4 ToInteger -var ceil = Math.ceil; -var floor = Math.floor; -module.exports = function (it) { - return isNaN(it = +it) ? 0 : (it > 0 ? floor : ceil)(it); -}; - - -/***/ }), -/* 74 */ -/***/ (function(module, exports, __webpack_require__) { - -// to indexed object, toObject with fallback for non-array-like ES3 strings -var IObject = __webpack_require__(131); -var defined = __webpack_require__(67); -module.exports = function (it) { - return IObject(defined(it)); -}; - - -/***/ }), -/* 75 */ -/***/ (function(module, exports, __webpack_require__) { - -// Approach: -// -// 1. Get the minimatch set -// 2. For each pattern in the set, PROCESS(pattern, false) -// 3. Store matches per-set, then uniq them -// -// PROCESS(pattern, inGlobStar) -// Get the first [n] items from pattern that are all strings -// Join these together. This is PREFIX. -// If there is no more remaining, then stat(PREFIX) and -// add to matches if it succeeds. END. -// -// If inGlobStar and PREFIX is symlink and points to dir -// set ENTRIES = [] -// else readdir(PREFIX) as ENTRIES -// If fail, END -// -// with ENTRIES -// If pattern[n] is GLOBSTAR -// // handle the case where the globstar match is empty -// // by pruning it out, and testing the resulting pattern -// PROCESS(pattern[0..n] + pattern[n+1 .. $], false) -// // handle other cases. -// for ENTRY in ENTRIES (not dotfiles) -// // attach globstar + tail onto the entry -// // Mark that this entry is a globstar match -// PROCESS(pattern[0..n] + ENTRY + pattern[n .. $], true) -// -// else // not globstar -// for ENTRY in ENTRIES (not dotfiles, unless pattern[n] is dot) -// Test ENTRY against pattern[n] -// If fails, continue -// If passes, PROCESS(pattern[0..n] + item + pattern[n+1 .. $]) -// -// Caveat: -// Cache all stats and readdirs results to minimize syscall. Since all -// we ever care about is existence and directory-ness, we can just keep -// `true` for files, and [children,...] for directories, or `false` for -// things that don't exist. - -module.exports = glob - -var fs = __webpack_require__(3) -var rp = __webpack_require__(114) -var minimatch = __webpack_require__(60) -var Minimatch = minimatch.Minimatch -var inherits = __webpack_require__(42) -var EE = __webpack_require__(54).EventEmitter -var path = __webpack_require__(0) -var assert = __webpack_require__(22) -var isAbsolute = __webpack_require__(76) -var globSync = __webpack_require__(218) -var common = __webpack_require__(115) -var alphasort = common.alphasort -var alphasorti = common.alphasorti -var setopts = common.setopts -var ownProp = common.ownProp -var inflight = __webpack_require__(223) -var util = __webpack_require__(2) -var childrenIgnored = common.childrenIgnored -var isIgnored = common.isIgnored - -var once = __webpack_require__(61) - -function glob (pattern, options, cb) { - if (typeof options === 'function') cb = options, options = {} - if (!options) options = {} - - if (options.sync) { - if (cb) - throw new TypeError('callback provided to sync glob') - return globSync(pattern, options) - } - - return new Glob(pattern, options, cb) -} - -glob.sync = globSync -var GlobSync = glob.GlobSync = globSync.GlobSync - -// old api surface -glob.glob = glob - -function extend (origin, add) { - if (add === null || typeof add !== 'object') { - return origin - } - - var keys = Object.keys(add) - var i = keys.length - while (i--) { - origin[keys[i]] = add[keys[i]] - } - return origin -} - -glob.hasMagic = function (pattern, options_) { - var options = extend({}, options_) - options.noprocess = true - - var g = new Glob(pattern, options) - var set = g.minimatch.set - - if (!pattern) - return false - - if (set.length > 1) - return true - - for (var j = 0; j < set[0].length; j++) { - if (typeof set[0][j] !== 'string') - return true - } - - return false -} - -glob.Glob = Glob -inherits(Glob, EE) -function Glob (pattern, options, cb) { - if (typeof options === 'function') { - cb = options - options = null - } - - if (options && options.sync) { - if (cb) - throw new TypeError('callback provided to sync glob') - return new GlobSync(pattern, options) - } - - if (!(this instanceof Glob)) - return new Glob(pattern, options, cb) - - setopts(this, pattern, options) - this._didRealPath = false - - // process each pattern in the minimatch set - var n = this.minimatch.set.length - - // The matches are stored as {: true,...} so that - // duplicates are automagically pruned. - // Later, we do an Object.keys() on these. - // Keep them as a list so we can fill in when nonull is set. - this.matches = new Array(n) - - if (typeof cb === 'function') { - cb = once(cb) - this.on('error', cb) - this.on('end', function (matches) { - cb(null, matches) - }) - } - - var self = this - this._processing = 0 - - this._emitQueue = [] - this._processQueue = [] - this.paused = false - - if (this.noprocess) - return this - - if (n === 0) - return done() - - var sync = true - for (var i = 0; i < n; i ++) { - this._process(this.minimatch.set[i], i, false, done) - } - sync = false - - function done () { - --self._processing - if (self._processing <= 0) { - if (sync) { - process.nextTick(function () { - self._finish() - }) - } else { - self._finish() - } - } - } -} - -Glob.prototype._finish = function () { - assert(this instanceof Glob) - if (this.aborted) - return - - if (this.realpath && !this._didRealpath) - return this._realpath() - - common.finish(this) - this.emit('end', this.found) -} - -Glob.prototype._realpath = function () { - if (this._didRealpath) - return - - this._didRealpath = true - - var n = this.matches.length - if (n === 0) - return this._finish() - - var self = this - for (var i = 0; i < this.matches.length; i++) - this._realpathSet(i, next) - - function next () { - if (--n === 0) - self._finish() - } -} - -Glob.prototype._realpathSet = function (index, cb) { - var matchset = this.matches[index] - if (!matchset) - return cb() - - var found = Object.keys(matchset) - var self = this - var n = found.length - - if (n === 0) - return cb() - - var set = this.matches[index] = Object.create(null) - found.forEach(function (p, i) { - // If there's a problem with the stat, then it means that - // one or more of the links in the realpath couldn't be - // resolved. just return the abs value in that case. - p = self._makeAbs(p) - rp.realpath(p, self.realpathCache, function (er, real) { - if (!er) - set[real] = true - else if (er.syscall === 'stat') - set[p] = true - else - self.emit('error', er) // srsly wtf right here - - if (--n === 0) { - self.matches[index] = set - cb() - } - }) - }) -} - -Glob.prototype._mark = function (p) { - return common.mark(this, p) -} - -Glob.prototype._makeAbs = function (f) { - return common.makeAbs(this, f) -} - -Glob.prototype.abort = function () { - this.aborted = true - this.emit('abort') -} - -Glob.prototype.pause = function () { - if (!this.paused) { - this.paused = true - this.emit('pause') - } -} - -Glob.prototype.resume = function () { - if (this.paused) { - this.emit('resume') - this.paused = false - if (this._emitQueue.length) { - var eq = this._emitQueue.slice(0) - this._emitQueue.length = 0 - for (var i = 0; i < eq.length; i ++) { - var e = eq[i] - this._emitMatch(e[0], e[1]) - } - } - if (this._processQueue.length) { - var pq = this._processQueue.slice(0) - this._processQueue.length = 0 - for (var i = 0; i < pq.length; i ++) { - var p = pq[i] - this._processing-- - this._process(p[0], p[1], p[2], p[3]) - } - } - } -} - -Glob.prototype._process = function (pattern, index, inGlobStar, cb) { - assert(this instanceof Glob) - assert(typeof cb === 'function') - - if (this.aborted) - return - - this._processing++ - if (this.paused) { - this._processQueue.push([pattern, index, inGlobStar, cb]) - return - } - - //console.error('PROCESS %d', this._processing, pattern) - - // Get the first [n] parts of pattern that are all strings. - var n = 0 - while (typeof pattern[n] === 'string') { - n ++ - } - // now n is the index of the first one that is *not* a string. - - // see if there's anything else - var prefix - switch (n) { - // if not, then this is rather simple - case pattern.length: - this._processSimple(pattern.join('/'), index, cb) - return - - case 0: - // pattern *starts* with some non-trivial item. - // going to readdir(cwd), but not include the prefix in matches. - prefix = null - break - - default: - // pattern has some string bits in the front. - // whatever it starts with, whether that's 'absolute' like /foo/bar, - // or 'relative' like '../baz' - prefix = pattern.slice(0, n).join('/') - break - } - - var remain = pattern.slice(n) - - // get the list of entries. - var read - if (prefix === null) - read = '.' - else if (isAbsolute(prefix) || isAbsolute(pattern.join('/'))) { - if (!prefix || !isAbsolute(prefix)) - prefix = '/' + prefix - read = prefix - } else - read = prefix - - var abs = this._makeAbs(read) - - //if ignored, skip _processing - if (childrenIgnored(this, read)) - return cb() - - var isGlobStar = remain[0] === minimatch.GLOBSTAR - if (isGlobStar) - this._processGlobStar(prefix, read, abs, remain, index, inGlobStar, cb) - else - this._processReaddir(prefix, read, abs, remain, index, inGlobStar, cb) -} - -Glob.prototype._processReaddir = function (prefix, read, abs, remain, index, inGlobStar, cb) { - var self = this - this._readdir(abs, inGlobStar, function (er, entries) { - return self._processReaddir2(prefix, read, abs, remain, index, inGlobStar, entries, cb) - }) -} - -Glob.prototype._processReaddir2 = function (prefix, read, abs, remain, index, inGlobStar, entries, cb) { - - // if the abs isn't a dir, then nothing can match! - if (!entries) - return cb() - - // It will only match dot entries if it starts with a dot, or if - // dot is set. Stuff like @(.foo|.bar) isn't allowed. - var pn = remain[0] - var negate = !!this.minimatch.negate - var rawGlob = pn._glob - var dotOk = this.dot || rawGlob.charAt(0) === '.' - - var matchedEntries = [] - for (var i = 0; i < entries.length; i++) { - var e = entries[i] - if (e.charAt(0) !== '.' || dotOk) { - var m - if (negate && !prefix) { - m = !e.match(pn) - } else { - m = e.match(pn) - } - if (m) - matchedEntries.push(e) - } - } - - //console.error('prd2', prefix, entries, remain[0]._glob, matchedEntries) - - var len = matchedEntries.length - // If there are no matched entries, then nothing matches. - if (len === 0) - return cb() - - // if this is the last remaining pattern bit, then no need for - // an additional stat *unless* the user has specified mark or - // stat explicitly. We know they exist, since readdir returned - // them. - - if (remain.length === 1 && !this.mark && !this.stat) { - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - if (prefix) { - if (prefix !== '/') - e = prefix + '/' + e - else - e = prefix + e - } - - if (e.charAt(0) === '/' && !this.nomount) { - e = path.join(this.root, e) - } - this._emitMatch(index, e) - } - // This was the last one, and no stats were needed - return cb() - } - - // now test all matched entries as stand-ins for that part - // of the pattern. - remain.shift() - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - var newPattern - if (prefix) { - if (prefix !== '/') - e = prefix + '/' + e - else - e = prefix + e - } - this._process([e].concat(remain), index, inGlobStar, cb) - } - cb() -} - -Glob.prototype._emitMatch = function (index, e) { - if (this.aborted) - return - - if (isIgnored(this, e)) - return - - if (this.paused) { - this._emitQueue.push([index, e]) - return - } - - var abs = isAbsolute(e) ? e : this._makeAbs(e) - - if (this.mark) - e = this._mark(e) - - if (this.absolute) - e = abs - - if (this.matches[index][e]) - return - - if (this.nodir) { - var c = this.cache[abs] - if (c === 'DIR' || Array.isArray(c)) - return - } - - this.matches[index][e] = true - - var st = this.statCache[abs] - if (st) - this.emit('stat', e, st) - - this.emit('match', e) -} - -Glob.prototype._readdirInGlobStar = function (abs, cb) { - if (this.aborted) - return - - // follow all symlinked directories forever - // just proceed as if this is a non-globstar situation - if (this.follow) - return this._readdir(abs, false, cb) - - var lstatkey = 'lstat\0' + abs - var self = this - var lstatcb = inflight(lstatkey, lstatcb_) - - if (lstatcb) - fs.lstat(abs, lstatcb) - - function lstatcb_ (er, lstat) { - if (er && er.code === 'ENOENT') - return cb() - - var isSym = lstat && lstat.isSymbolicLink() - self.symlinks[abs] = isSym - - // If it's not a symlink or a dir, then it's definitely a regular file. - // don't bother doing a readdir in that case. - if (!isSym && lstat && !lstat.isDirectory()) { - self.cache[abs] = 'FILE' - cb() - } else - self._readdir(abs, false, cb) - } -} - -Glob.prototype._readdir = function (abs, inGlobStar, cb) { - if (this.aborted) - return - - cb = inflight('readdir\0'+abs+'\0'+inGlobStar, cb) - if (!cb) - return - - //console.error('RD %j %j', +inGlobStar, abs) - if (inGlobStar && !ownProp(this.symlinks, abs)) - return this._readdirInGlobStar(abs, cb) - - if (ownProp(this.cache, abs)) { - var c = this.cache[abs] - if (!c || c === 'FILE') - return cb() - - if (Array.isArray(c)) - return cb(null, c) - } - - var self = this - fs.readdir(abs, readdirCb(this, abs, cb)) -} - -function readdirCb (self, abs, cb) { - return function (er, entries) { - if (er) - self._readdirError(abs, er, cb) - else - self._readdirEntries(abs, entries, cb) - } -} - -Glob.prototype._readdirEntries = function (abs, entries, cb) { - if (this.aborted) - return - - // if we haven't asked to stat everything, then just - // assume that everything in there exists, so we can avoid - // having to stat it a second time. - if (!this.mark && !this.stat) { - for (var i = 0; i < entries.length; i ++) { - var e = entries[i] - if (abs === '/') - e = abs + e - else - e = abs + '/' + e - this.cache[e] = true - } - } - - this.cache[abs] = entries - return cb(null, entries) -} - -Glob.prototype._readdirError = function (f, er, cb) { - if (this.aborted) - return - - // handle errors, and cache the information - switch (er.code) { - case 'ENOTSUP': // https://github.com/isaacs/node-glob/issues/205 - case 'ENOTDIR': // totally normal. means it *does* exist. - var abs = this._makeAbs(f) - this.cache[abs] = 'FILE' - if (abs === this.cwdAbs) { - var error = new Error(er.code + ' invalid cwd ' + this.cwd) - error.path = this.cwd - error.code = er.code - this.emit('error', error) - this.abort() - } - break - - case 'ENOENT': // not terribly unusual - case 'ELOOP': - case 'ENAMETOOLONG': - case 'UNKNOWN': - this.cache[this._makeAbs(f)] = false - break - - default: // some unusual error. Treat as failure. - this.cache[this._makeAbs(f)] = false - if (this.strict) { - this.emit('error', er) - // If the error is handled, then we abort - // if not, we threw out of here - this.abort() - } - if (!this.silent) - console.error('glob error', er) - break - } - - return cb() -} - -Glob.prototype._processGlobStar = function (prefix, read, abs, remain, index, inGlobStar, cb) { - var self = this - this._readdir(abs, inGlobStar, function (er, entries) { - self._processGlobStar2(prefix, read, abs, remain, index, inGlobStar, entries, cb) - }) -} - - -Glob.prototype._processGlobStar2 = function (prefix, read, abs, remain, index, inGlobStar, entries, cb) { - //console.error('pgs2', prefix, remain[0], entries) - - // no entries means not a dir, so it can never have matches - // foo.txt/** doesn't match foo.txt - if (!entries) - return cb() - - // test without the globstar, and with every child both below - // and replacing the globstar. - var remainWithoutGlobStar = remain.slice(1) - var gspref = prefix ? [ prefix ] : [] - var noGlobStar = gspref.concat(remainWithoutGlobStar) - - // the noGlobStar pattern exits the inGlobStar state - this._process(noGlobStar, index, false, cb) - - var isSym = this.symlinks[abs] - var len = entries.length - - // If it's a symlink, and we're in a globstar, then stop - if (isSym && inGlobStar) - return cb() - - for (var i = 0; i < len; i++) { - var e = entries[i] - if (e.charAt(0) === '.' && !this.dot) - continue - - // these two cases enter the inGlobStar state - var instead = gspref.concat(entries[i], remainWithoutGlobStar) - this._process(instead, index, true, cb) - - var below = gspref.concat(entries[i], remain) - this._process(below, index, true, cb) - } - - cb() -} - -Glob.prototype._processSimple = function (prefix, index, cb) { - // XXX review this. Shouldn't it be doing the mounting etc - // before doing stat? kinda weird? - var self = this - this._stat(prefix, function (er, exists) { - self._processSimple2(prefix, index, er, exists, cb) - }) -} -Glob.prototype._processSimple2 = function (prefix, index, er, exists, cb) { - - //console.error('ps2', prefix, exists) - - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - // If it doesn't exist, then just mark the lack of results - if (!exists) - return cb() - - if (prefix && isAbsolute(prefix) && !this.nomount) { - var trail = /[\/\\]$/.test(prefix) - if (prefix.charAt(0) === '/') { - prefix = path.join(this.root, prefix) - } else { - prefix = path.resolve(this.root, prefix) - if (trail) - prefix += '/' - } - } - - if (process.platform === 'win32') - prefix = prefix.replace(/\\/g, '/') - - // Mark this as a match - this._emitMatch(index, prefix) - cb() -} - -// Returns either 'DIR', 'FILE', or false -Glob.prototype._stat = function (f, cb) { - var abs = this._makeAbs(f) - var needDir = f.slice(-1) === '/' - - if (f.length > this.maxLength) - return cb() - - if (!this.stat && ownProp(this.cache, abs)) { - var c = this.cache[abs] - - if (Array.isArray(c)) - c = 'DIR' - - // It exists, but maybe not how we need it - if (!needDir || c === 'DIR') - return cb(null, c) - - if (needDir && c === 'FILE') - return cb() - - // otherwise we have to stat, because maybe c=true - // if we know it exists, but not what it is. - } - - var exists - var stat = this.statCache[abs] - if (stat !== undefined) { - if (stat === false) - return cb(null, stat) - else { - var type = stat.isDirectory() ? 'DIR' : 'FILE' - if (needDir && type === 'FILE') - return cb() - else - return cb(null, type, stat) - } - } - - var self = this - var statcb = inflight('stat\0' + abs, lstatcb_) - if (statcb) - fs.lstat(abs, statcb) - - function lstatcb_ (er, lstat) { - if (lstat && lstat.isSymbolicLink()) { - // If it's a symlink, then treat it as the target, unless - // the target does not exist, then treat it as a file. - return fs.stat(abs, function (er, stat) { - if (er) - self._stat2(f, abs, null, lstat, cb) - else - self._stat2(f, abs, er, stat, cb) - }) - } else { - self._stat2(f, abs, er, lstat, cb) - } - } -} - -Glob.prototype._stat2 = function (f, abs, er, stat, cb) { - if (er && (er.code === 'ENOENT' || er.code === 'ENOTDIR')) { - this.statCache[abs] = false - return cb() - } - - var needDir = f.slice(-1) === '/' - this.statCache[abs] = stat - - if (abs.slice(-1) === '/' && stat && !stat.isDirectory()) - return cb(null, false, stat) - - var c = true - if (stat) - c = stat.isDirectory() ? 'DIR' : 'FILE' - this.cache[abs] = this.cache[abs] || c - - if (needDir && c === 'FILE') - return cb() - - return cb(null, c, stat) -} - - -/***/ }), -/* 76 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -function posix(path) { - return path.charAt(0) === '/'; -} - -function win32(path) { - // https://github.com/nodejs/node/blob/b3fcc245fb25539909ef1d5eaa01dbf92e168633/lib/path.js#L56 - var splitDeviceRe = /^([a-zA-Z]:|[\\\/]{2}[^\\\/]+[\\\/]+[^\\\/]+)?([\\\/])?([\s\S]*?)$/; - var result = splitDeviceRe.exec(path); - var device = result[1] || ''; - var isUnc = Boolean(device && device.charAt(1) !== ':'); - - // UNC paths are always absolute - return Boolean(result[2] || isUnc); -} - -module.exports = process.platform === 'win32' ? win32 : posix; -module.exports.posix = posix; -module.exports.win32 = win32; - - -/***/ }), -/* 77 */, -/* 78 */, -/* 79 */ -/***/ (function(module, exports) { - -module.exports = __webpack_require__("tty"); - -/***/ }), -/* 80 */, -/* 81 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); - -exports.default = function (str, fileLoc = 'lockfile') { - str = (0, (_stripBom || _load_stripBom()).default)(str); - return hasMergeConflicts(str) ? parseWithConflict(str, fileLoc) : { type: 'success', object: parse(str, fileLoc) }; -}; - -var _util; - -function _load_util() { - return _util = _interopRequireDefault(__webpack_require__(2)); -} - -var _invariant; - -function _load_invariant() { - return _invariant = _interopRequireDefault(__webpack_require__(7)); -} - -var _stripBom; - -function _load_stripBom() { - return _stripBom = _interopRequireDefault(__webpack_require__(122)); -} - -var _constants; - -function _load_constants() { - return _constants = __webpack_require__(6); -} - -var _errors; - -function _load_errors() { - return _errors = __webpack_require__(4); -} - -var _map; - -function _load_map() { - return _map = _interopRequireDefault(__webpack_require__(20)); -} - -function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } - -/* eslint quotes: 0 */ - -const VERSION_REGEX = /^yarn lockfile v(\d+)$/; - -const TOKEN_TYPES = { - boolean: 'BOOLEAN', - string: 'STRING', - identifier: 'IDENTIFIER', - eof: 'EOF', - colon: 'COLON', - newline: 'NEWLINE', - comment: 'COMMENT', - indent: 'INDENT', - invalid: 'INVALID', - number: 'NUMBER', - comma: 'COMMA' -}; - -const VALID_PROP_VALUE_TOKENS = [TOKEN_TYPES.boolean, TOKEN_TYPES.string, TOKEN_TYPES.number]; - -function isValidPropValueToken(token) { - return VALID_PROP_VALUE_TOKENS.indexOf(token.type) >= 0; -} - -function* tokenise(input) { - let lastNewline = false; - let line = 1; - let col = 0; - - function buildToken(type, value) { - return { line, col, type, value }; - } - - while (input.length) { - let chop = 0; - - if (input[0] === '\n' || input[0] === '\r') { - chop++; - // If this is a \r\n line, ignore both chars but only add one new line - if (input[1] === '\n') { - chop++; - } - line++; - col = 0; - yield buildToken(TOKEN_TYPES.newline); - } else if (input[0] === '#') { - chop++; - - let val = ''; - while (input[chop] !== '\n') { - val += input[chop]; - chop++; - } - yield buildToken(TOKEN_TYPES.comment, val); - } else if (input[0] === ' ') { - if (lastNewline) { - let indent = ''; - for (let i = 0; input[i] === ' '; i++) { - indent += input[i]; - } - - if (indent.length % 2) { - throw new TypeError('Invalid number of spaces'); - } else { - chop = indent.length; - yield buildToken(TOKEN_TYPES.indent, indent.length / 2); - } - } else { - chop++; - } - } else if (input[0] === '"') { - let val = ''; - - for (let i = 0;; i++) { - const currentChar = input[i]; - val += currentChar; - - if (i > 0 && currentChar === '"') { - const isEscaped = input[i - 1] === '\\' && input[i - 2] !== '\\'; - if (!isEscaped) { - break; - } - } - } - - chop = val.length; - - try { - yield buildToken(TOKEN_TYPES.string, JSON.parse(val)); - } catch (err) { - if (err instanceof SyntaxError) { - yield buildToken(TOKEN_TYPES.invalid); - } else { - throw err; - } - } - } else if (/^[0-9]/.test(input)) { - let val = ''; - for (let i = 0; /^[0-9]$/.test(input[i]); i++) { - val += input[i]; - } - chop = val.length; - - yield buildToken(TOKEN_TYPES.number, +val); - } else if (/^true/.test(input)) { - yield buildToken(TOKEN_TYPES.boolean, true); - chop = 4; - } else if (/^false/.test(input)) { - yield buildToken(TOKEN_TYPES.boolean, false); - chop = 5; - } else if (input[0] === ':') { - yield buildToken(TOKEN_TYPES.colon); - chop++; - } else if (input[0] === ',') { - yield buildToken(TOKEN_TYPES.comma); - chop++; - } else if (/^[a-zA-Z\/-]/g.test(input)) { - let name = ''; - for (let i = 0; i < input.length; i++) { - const char = input[i]; - if (char === ':' || char === ' ' || char === '\n' || char === '\r' || char === ',') { - break; - } else { - name += char; - } - } - chop = name.length; - - yield buildToken(TOKEN_TYPES.string, name); - } else { - yield buildToken(TOKEN_TYPES.invalid); - } - - if (!chop) { - // will trigger infinite recursion - yield buildToken(TOKEN_TYPES.invalid); - } - - col += chop; - lastNewline = input[0] === '\n' || input[0] === '\r' && input[1] === '\n'; - input = input.slice(chop); - } - - yield buildToken(TOKEN_TYPES.eof); -} - -class Parser { - constructor(input, fileLoc = 'lockfile') { - this.comments = []; - this.tokens = tokenise(input); - this.fileLoc = fileLoc; - } - - onComment(token) { - const value = token.value; - (0, (_invariant || _load_invariant()).default)(typeof value === 'string', 'expected token value to be a string'); - - const comment = value.trim(); - - const versionMatch = comment.match(VERSION_REGEX); - if (versionMatch) { - const version = +versionMatch[1]; - if (version > (_constants || _load_constants()).LOCKFILE_VERSION) { - throw new (_errors || _load_errors()).MessageError(`Can't install from a lockfile of version ${version} as you're on an old yarn version that only supports ` + `versions up to ${(_constants || _load_constants()).LOCKFILE_VERSION}. Run \`$ yarn self-update\` to upgrade to the latest version.`); - } - } - - this.comments.push(comment); - } - - next() { - const item = this.tokens.next(); - (0, (_invariant || _load_invariant()).default)(item, 'expected a token'); - - const done = item.done, - value = item.value; - - if (done || !value) { - throw new Error('No more tokens'); - } else if (value.type === TOKEN_TYPES.comment) { - this.onComment(value); - return this.next(); - } else { - return this.token = value; - } - } - - unexpected(msg = 'Unexpected token') { - throw new SyntaxError(`${msg} ${this.token.line}:${this.token.col} in ${this.fileLoc}`); - } - - expect(tokType) { - if (this.token.type === tokType) { - this.next(); - } else { - this.unexpected(); - } - } - - eat(tokType) { - if (this.token.type === tokType) { - this.next(); - return true; - } else { - return false; - } - } - - parse(indent = 0) { - const obj = (0, (_map || _load_map()).default)(); - - while (true) { - const propToken = this.token; - - if (propToken.type === TOKEN_TYPES.newline) { - const nextToken = this.next(); - if (!indent) { - // if we have 0 indentation then the next token doesn't matter - continue; - } - - if (nextToken.type !== TOKEN_TYPES.indent) { - // if we have no indentation after a newline then we've gone down a level - break; - } - - if (nextToken.value === indent) { - // all is good, the indent is on our level - this.next(); - } else { - // the indentation is less than our level - break; - } - } else if (propToken.type === TOKEN_TYPES.indent) { - if (propToken.value === indent) { - this.next(); - } else { - break; - } - } else if (propToken.type === TOKEN_TYPES.eof) { - break; - } else if (propToken.type === TOKEN_TYPES.string) { - // property key - const key = propToken.value; - (0, (_invariant || _load_invariant()).default)(key, 'Expected a key'); - - const keys = [key]; - this.next(); - - // support multiple keys - while (this.token.type === TOKEN_TYPES.comma) { - this.next(); // skip comma - - const keyToken = this.token; - if (keyToken.type !== TOKEN_TYPES.string) { - this.unexpected('Expected string'); - } - - const key = keyToken.value; - (0, (_invariant || _load_invariant()).default)(key, 'Expected a key'); - keys.push(key); - this.next(); - } - - const valToken = this.token; - - if (valToken.type === TOKEN_TYPES.colon) { - // object - this.next(); - - // parse object - const val = this.parse(indent + 1); - - for (var _iterator = keys, _isArray = Array.isArray(_iterator), _i = 0, _iterator = _isArray ? _iterator : _iterator[Symbol.iterator]();;) { - var _ref; - - if (_isArray) { - if (_i >= _iterator.length) break; - _ref = _iterator[_i++]; - } else { - _i = _iterator.next(); - if (_i.done) break; - _ref = _i.value; - } - - const key = _ref; - - obj[key] = val; - } - - if (indent && this.token.type !== TOKEN_TYPES.indent) { - break; - } - } else if (isValidPropValueToken(valToken)) { - // plain value - for (var _iterator2 = keys, _isArray2 = Array.isArray(_iterator2), _i2 = 0, _iterator2 = _isArray2 ? _iterator2 : _iterator2[Symbol.iterator]();;) { - var _ref2; - - if (_isArray2) { - if (_i2 >= _iterator2.length) break; - _ref2 = _iterator2[_i2++]; - } else { - _i2 = _iterator2.next(); - if (_i2.done) break; - _ref2 = _i2.value; - } - - const key = _ref2; - - obj[key] = valToken.value; - } - - this.next(); - } else { - this.unexpected('Invalid value type'); - } - } else { - this.unexpected(`Unknown token: ${(_util || _load_util()).default.inspect(propToken)}`); - } - } - - return obj; - } -} - -const MERGE_CONFLICT_ANCESTOR = '|||||||'; -const MERGE_CONFLICT_END = '>>>>>>>'; -const MERGE_CONFLICT_SEP = '======='; -const MERGE_CONFLICT_START = '<<<<<<<'; - -/** - * Extract the two versions of the lockfile from a merge conflict. - */ -function extractConflictVariants(str) { - const variants = [[], []]; - const lines = str.split(/\r?\n/g); - let skip = false; - - while (lines.length) { - const line = lines.shift(); - if (line.startsWith(MERGE_CONFLICT_START)) { - // get the first variant - while (lines.length) { - const conflictLine = lines.shift(); - if (conflictLine === MERGE_CONFLICT_SEP) { - skip = false; - break; - } else if (skip || conflictLine.startsWith(MERGE_CONFLICT_ANCESTOR)) { - skip = true; - continue; - } else { - variants[0].push(conflictLine); - } - } - - // get the second variant - while (lines.length) { - const conflictLine = lines.shift(); - if (conflictLine.startsWith(MERGE_CONFLICT_END)) { - break; - } else { - variants[1].push(conflictLine); - } - } - } else { - variants[0].push(line); - variants[1].push(line); - } - } - - return [variants[0].join('\n'), variants[1].join('\n')]; -} - -/** - * Check if a lockfile has merge conflicts. - */ -function hasMergeConflicts(str) { - return str.includes(MERGE_CONFLICT_START) && str.includes(MERGE_CONFLICT_SEP) && str.includes(MERGE_CONFLICT_END); -} - -/** - * Parse the lockfile. - */ -function parse(str, fileLoc) { - const parser = new Parser(str, fileLoc); - parser.next(); - return parser.parse(); -} - -/** - * Parse and merge the two variants in a conflicted lockfile. - */ -function parseWithConflict(str, fileLoc) { - const variants = extractConflictVariants(str); - try { - return { type: 'merge', object: Object.assign({}, parse(variants[0], fileLoc), parse(variants[1], fileLoc)) }; - } catch (err) { - if (err instanceof SyntaxError) { - return { type: 'conflict', object: {} }; - } else { - throw err; - } - } -} - -/***/ }), -/* 82 */, -/* 83 */, -/* 84 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); - -var _map; - -function _load_map() { - return _map = _interopRequireDefault(__webpack_require__(20)); -} - -function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } - -const debug = __webpack_require__(212)('yarn'); - -class BlockingQueue { - constructor(alias, maxConcurrency = Infinity) { - this.concurrencyQueue = []; - this.maxConcurrency = maxConcurrency; - this.runningCount = 0; - this.warnedStuck = false; - this.alias = alias; - this.first = true; - - this.running = (0, (_map || _load_map()).default)(); - this.queue = (0, (_map || _load_map()).default)(); - - this.stuckTick = this.stuckTick.bind(this); - } - - stillActive() { - if (this.stuckTimer) { - clearTimeout(this.stuckTimer); - } - - this.stuckTimer = setTimeout(this.stuckTick, 5000); - - // We need to check the existence of unref because of https://github.com/facebook/jest/issues/4559 - // $FlowFixMe: Node's setInterval returns a Timeout, not a Number - this.stuckTimer.unref && this.stuckTimer.unref(); - } - - stuckTick() { - if (this.runningCount === 1) { - this.warnedStuck = true; - debug(`The ${JSON.stringify(this.alias)} blocking queue may be stuck. 5 seconds ` + `without any activity with 1 worker: ${Object.keys(this.running)[0]}`); - } - } - - push(key, factory) { - if (this.first) { - this.first = false; - } else { - this.stillActive(); - } - - return new Promise((resolve, reject) => { - // we're already running so push ourselves to the queue - const queue = this.queue[key] = this.queue[key] || []; - queue.push({ factory, resolve, reject }); - - if (!this.running[key]) { - this.shift(key); - } - }); - } - - shift(key) { - if (this.running[key]) { - delete this.running[key]; - this.runningCount--; - - if (this.stuckTimer) { - clearTimeout(this.stuckTimer); - this.stuckTimer = null; - } - - if (this.warnedStuck) { - this.warnedStuck = false; - debug(`${JSON.stringify(this.alias)} blocking queue finally resolved. Nothing to worry about.`); - } - } - - const queue = this.queue[key]; - if (!queue) { - return; - } - - var _queue$shift = queue.shift(); - - const resolve = _queue$shift.resolve, - reject = _queue$shift.reject, - factory = _queue$shift.factory; - - if (!queue.length) { - delete this.queue[key]; - } - - const next = () => { - this.shift(key); - this.shiftConcurrencyQueue(); - }; - - const run = () => { - this.running[key] = true; - this.runningCount++; - - factory().then(function (val) { - resolve(val); - next(); - return null; - }).catch(function (err) { - reject(err); - next(); - }); - }; - - this.maybePushConcurrencyQueue(run); - } - - maybePushConcurrencyQueue(run) { - if (this.runningCount < this.maxConcurrency) { - run(); - } else { - this.concurrencyQueue.push(run); - } - } - - shiftConcurrencyQueue() { - if (this.runningCount < this.maxConcurrency) { - const fn = this.concurrencyQueue.shift(); - if (fn) { - fn(); - } - } - } -} -exports.default = BlockingQueue; - -/***/ }), -/* 85 */ -/***/ (function(module, exports) { - -module.exports = function (exec) { - try { - return !!exec(); - } catch (e) { - return true; - } -}; - - -/***/ }), -/* 86 */, -/* 87 */, -/* 88 */, -/* 89 */, -/* 90 */, -/* 91 */, -/* 92 */, -/* 93 */, -/* 94 */, -/* 95 */, -/* 96 */, -/* 97 */, -/* 98 */, -/* 99 */, -/* 100 */ -/***/ (function(module, exports, __webpack_require__) { - -// getting tag from 19.1.3.6 Object.prototype.toString() -var cof = __webpack_require__(47); -var TAG = __webpack_require__(13)('toStringTag'); -// ES3 wrong here -var ARG = cof(function () { return arguments; }()) == 'Arguments'; - -// fallback for IE11 Script Access Denied error -var tryGet = function (it, key) { - try { - return it[key]; - } catch (e) { /* empty */ } -}; - -module.exports = function (it) { - var O, T, B; - return it === undefined ? 'Undefined' : it === null ? 'Null' - // @@toStringTag case - : typeof (T = tryGet(O = Object(it), TAG)) == 'string' ? T - // builtinTag case - : ARG ? cof(O) - // ES3 arguments fallback - : (B = cof(O)) == 'Object' && typeof O.callee == 'function' ? 'Arguments' : B; -}; - - -/***/ }), -/* 101 */ -/***/ (function(module, exports) { - -// IE 8- don't enum bug keys -module.exports = ( - 'constructor,hasOwnProperty,isPrototypeOf,propertyIsEnumerable,toLocaleString,toString,valueOf' -).split(','); - - -/***/ }), -/* 102 */ -/***/ (function(module, exports, __webpack_require__) { - -var document = __webpack_require__(11).document; -module.exports = document && document.documentElement; - - -/***/ }), -/* 103 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var LIBRARY = __webpack_require__(69); -var $export = __webpack_require__(41); -var redefine = __webpack_require__(197); -var hide = __webpack_require__(31); -var Iterators = __webpack_require__(35); -var $iterCreate = __webpack_require__(188); -var setToStringTag = __webpack_require__(71); -var getPrototypeOf = __webpack_require__(194); -var ITERATOR = __webpack_require__(13)('iterator'); -var BUGGY = !([].keys && 'next' in [].keys()); // Safari has buggy iterators w/o `next` -var FF_ITERATOR = '@@iterator'; -var KEYS = 'keys'; -var VALUES = 'values'; - -var returnThis = function () { return this; }; - -module.exports = function (Base, NAME, Constructor, next, DEFAULT, IS_SET, FORCED) { - $iterCreate(Constructor, NAME, next); - var getMethod = function (kind) { - if (!BUGGY && kind in proto) return proto[kind]; - switch (kind) { - case KEYS: return function keys() { return new Constructor(this, kind); }; - case VALUES: return function values() { return new Constructor(this, kind); }; - } return function entries() { return new Constructor(this, kind); }; - }; - var TAG = NAME + ' Iterator'; - var DEF_VALUES = DEFAULT == VALUES; - var VALUES_BUG = false; - var proto = Base.prototype; - var $native = proto[ITERATOR] || proto[FF_ITERATOR] || DEFAULT && proto[DEFAULT]; - var $default = $native || getMethod(DEFAULT); - var $entries = DEFAULT ? !DEF_VALUES ? $default : getMethod('entries') : undefined; - var $anyNative = NAME == 'Array' ? proto.entries || $native : $native; - var methods, key, IteratorPrototype; - // Fix native - if ($anyNative) { - IteratorPrototype = getPrototypeOf($anyNative.call(new Base())); - if (IteratorPrototype !== Object.prototype && IteratorPrototype.next) { - // Set @@toStringTag to native iterators - setToStringTag(IteratorPrototype, TAG, true); - // fix for some old engines - if (!LIBRARY && typeof IteratorPrototype[ITERATOR] != 'function') hide(IteratorPrototype, ITERATOR, returnThis); - } - } - // fix Array#{values, @@iterator}.name in V8 / FF - if (DEF_VALUES && $native && $native.name !== VALUES) { - VALUES_BUG = true; - $default = function values() { return $native.call(this); }; - } - // Define iterator - if ((!LIBRARY || FORCED) && (BUGGY || VALUES_BUG || !proto[ITERATOR])) { - hide(proto, ITERATOR, $default); - } - // Plug for library - Iterators[NAME] = $default; - Iterators[TAG] = returnThis; - if (DEFAULT) { - methods = { - values: DEF_VALUES ? $default : getMethod(VALUES), - keys: IS_SET ? $default : getMethod(KEYS), - entries: $entries - }; - if (FORCED) for (key in methods) { - if (!(key in proto)) redefine(proto, key, methods[key]); - } else $export($export.P + $export.F * (BUGGY || VALUES_BUG), NAME, methods); - } - return methods; -}; - - -/***/ }), -/* 104 */ -/***/ (function(module, exports) { - -module.exports = function (exec) { - try { - return { e: false, v: exec() }; - } catch (e) { - return { e: true, v: e }; - } -}; - - -/***/ }), -/* 105 */ -/***/ (function(module, exports, __webpack_require__) { - -var anObject = __webpack_require__(27); -var isObject = __webpack_require__(34); -var newPromiseCapability = __webpack_require__(70); - -module.exports = function (C, x) { - anObject(C); - if (isObject(x) && x.constructor === C) return x; - var promiseCapability = newPromiseCapability.f(C); - var resolve = promiseCapability.resolve; - resolve(x); - return promiseCapability.promise; -}; - - -/***/ }), -/* 106 */ -/***/ (function(module, exports) { - -module.exports = function (bitmap, value) { - return { - enumerable: !(bitmap & 1), - configurable: !(bitmap & 2), - writable: !(bitmap & 4), - value: value - }; -}; - - -/***/ }), -/* 107 */ -/***/ (function(module, exports, __webpack_require__) { - -var core = __webpack_require__(23); -var global = __webpack_require__(11); -var SHARED = '__core-js_shared__'; -var store = global[SHARED] || (global[SHARED] = {}); - -(module.exports = function (key, value) { - return store[key] || (store[key] = value !== undefined ? value : {}); -})('versions', []).push({ - version: core.version, - mode: __webpack_require__(69) ? 'pure' : 'global', - copyright: '© 2018 Denis Pushkarev (zloirock.ru)' -}); - - -/***/ }), -/* 108 */ -/***/ (function(module, exports, __webpack_require__) { - -// 7.3.20 SpeciesConstructor(O, defaultConstructor) -var anObject = __webpack_require__(27); -var aFunction = __webpack_require__(46); -var SPECIES = __webpack_require__(13)('species'); -module.exports = function (O, D) { - var C = anObject(O).constructor; - var S; - return C === undefined || (S = anObject(C)[SPECIES]) == undefined ? D : aFunction(S); -}; - - -/***/ }), -/* 109 */ -/***/ (function(module, exports, __webpack_require__) { - -var ctx = __webpack_require__(48); -var invoke = __webpack_require__(185); -var html = __webpack_require__(102); -var cel = __webpack_require__(68); -var global = __webpack_require__(11); -var process = global.process; -var setTask = global.setImmediate; -var clearTask = global.clearImmediate; -var MessageChannel = global.MessageChannel; -var Dispatch = global.Dispatch; -var counter = 0; -var queue = {}; -var ONREADYSTATECHANGE = 'onreadystatechange'; -var defer, channel, port; -var run = function () { - var id = +this; - // eslint-disable-next-line no-prototype-builtins - if (queue.hasOwnProperty(id)) { - var fn = queue[id]; - delete queue[id]; - fn(); - } -}; -var listener = function (event) { - run.call(event.data); -}; -// Node.js 0.9+ & IE10+ has setImmediate, otherwise: -if (!setTask || !clearTask) { - setTask = function setImmediate(fn) { - var args = []; - var i = 1; - while (arguments.length > i) args.push(arguments[i++]); - queue[++counter] = function () { - // eslint-disable-next-line no-new-func - invoke(typeof fn == 'function' ? fn : Function(fn), args); - }; - defer(counter); - return counter; - }; - clearTask = function clearImmediate(id) { - delete queue[id]; - }; - // Node.js 0.8- - if (__webpack_require__(47)(process) == 'process') { - defer = function (id) { - process.nextTick(ctx(run, id, 1)); - }; - // Sphere (JS game engine) Dispatch API - } else if (Dispatch && Dispatch.now) { - defer = function (id) { - Dispatch.now(ctx(run, id, 1)); - }; - // Browsers with MessageChannel, includes WebWorkers - } else if (MessageChannel) { - channel = new MessageChannel(); - port = channel.port2; - channel.port1.onmessage = listener; - defer = ctx(port.postMessage, port, 1); - // Browsers with postMessage, skip WebWorkers - // IE8 has postMessage, but it's sync & typeof its postMessage is 'object' - } else if (global.addEventListener && typeof postMessage == 'function' && !global.importScripts) { - defer = function (id) { - global.postMessage(id + '', '*'); - }; - global.addEventListener('message', listener, false); - // IE8- - } else if (ONREADYSTATECHANGE in cel('script')) { - defer = function (id) { - html.appendChild(cel('script'))[ONREADYSTATECHANGE] = function () { - html.removeChild(this); - run.call(id); - }; - }; - // Rest old browsers - } else { - defer = function (id) { - setTimeout(ctx(run, id, 1), 0); - }; - } -} -module.exports = { - set: setTask, - clear: clearTask -}; - - -/***/ }), -/* 110 */ -/***/ (function(module, exports, __webpack_require__) { - -// 7.1.15 ToLength -var toInteger = __webpack_require__(73); -var min = Math.min; -module.exports = function (it) { - return it > 0 ? min(toInteger(it), 0x1fffffffffffff) : 0; // pow(2, 53) - 1 == 9007199254740991 -}; - - -/***/ }), -/* 111 */ -/***/ (function(module, exports) { - -var id = 0; -var px = Math.random(); -module.exports = function (key) { - return 'Symbol('.concat(key === undefined ? '' : key, ')_', (++id + px).toString(36)); -}; - - -/***/ }), -/* 112 */ -/***/ (function(module, exports, __webpack_require__) { - - -/** - * This is the common logic for both the Node.js and web browser - * implementations of `debug()`. - * - * Expose `debug()` as the module. - */ - -exports = module.exports = createDebug.debug = createDebug['default'] = createDebug; -exports.coerce = coerce; -exports.disable = disable; -exports.enable = enable; -exports.enabled = enabled; -exports.humanize = __webpack_require__(229); - -/** - * Active `debug` instances. - */ -exports.instances = []; - -/** - * The currently active debug mode names, and names to skip. - */ - -exports.names = []; -exports.skips = []; - -/** - * Map of special "%n" handling functions, for the debug "format" argument. - * - * Valid key names are a single, lower or upper-case letter, i.e. "n" and "N". - */ - -exports.formatters = {}; - -/** - * Select a color. - * @param {String} namespace - * @return {Number} - * @api private - */ - -function selectColor(namespace) { - var hash = 0, i; - - for (i in namespace) { - hash = ((hash << 5) - hash) + namespace.charCodeAt(i); - hash |= 0; // Convert to 32bit integer - } - - return exports.colors[Math.abs(hash) % exports.colors.length]; -} - -/** - * Create a debugger with the given `namespace`. - * - * @param {String} namespace - * @return {Function} - * @api public - */ - -function createDebug(namespace) { - - var prevTime; - - function debug() { - // disabled? - if (!debug.enabled) return; - - var self = debug; - - // set `diff` timestamp - var curr = +new Date(); - var ms = curr - (prevTime || curr); - self.diff = ms; - self.prev = prevTime; - self.curr = curr; - prevTime = curr; - - // turn the `arguments` into a proper Array - var args = new Array(arguments.length); - for (var i = 0; i < args.length; i++) { - args[i] = arguments[i]; - } - - args[0] = exports.coerce(args[0]); - - if ('string' !== typeof args[0]) { - // anything else let's inspect with %O - args.unshift('%O'); - } - - // apply any `formatters` transformations - var index = 0; - args[0] = args[0].replace(/%([a-zA-Z%])/g, function(match, format) { - // if we encounter an escaped % then don't increase the array index - if (match === '%%') return match; - index++; - var formatter = exports.formatters[format]; - if ('function' === typeof formatter) { - var val = args[index]; - match = formatter.call(self, val); - - // now we need to remove `args[index]` since it's inlined in the `format` - args.splice(index, 1); - index--; - } - return match; - }); - - // apply env-specific formatting (colors, etc.) - exports.formatArgs.call(self, args); - - var logFn = debug.log || exports.log || console.log.bind(console); - logFn.apply(self, args); - } - - debug.namespace = namespace; - debug.enabled = exports.enabled(namespace); - debug.useColors = exports.useColors(); - debug.color = selectColor(namespace); - debug.destroy = destroy; - - // env-specific initialization logic for debug instances - if ('function' === typeof exports.init) { - exports.init(debug); - } - - exports.instances.push(debug); - - return debug; -} - -function destroy () { - var index = exports.instances.indexOf(this); - if (index !== -1) { - exports.instances.splice(index, 1); - return true; - } else { - return false; - } -} - -/** - * Enables a debug mode by namespaces. This can include modes - * separated by a colon and wildcards. - * - * @param {String} namespaces - * @api public - */ - -function enable(namespaces) { - exports.save(namespaces); - - exports.names = []; - exports.skips = []; - - var i; - var split = (typeof namespaces === 'string' ? namespaces : '').split(/[\s,]+/); - var len = split.length; - - for (i = 0; i < len; i++) { - if (!split[i]) continue; // ignore empty strings - namespaces = split[i].replace(/\*/g, '.*?'); - if (namespaces[0] === '-') { - exports.skips.push(new RegExp('^' + namespaces.substr(1) + '$')); - } else { - exports.names.push(new RegExp('^' + namespaces + '$')); - } - } - - for (i = 0; i < exports.instances.length; i++) { - var instance = exports.instances[i]; - instance.enabled = exports.enabled(instance.namespace); - } -} - -/** - * Disable debug output. - * - * @api public - */ - -function disable() { - exports.enable(''); -} - -/** - * Returns true if the given mode name is enabled, false otherwise. - * - * @param {String} name - * @return {Boolean} - * @api public - */ - -function enabled(name) { - if (name[name.length - 1] === '*') { - return true; - } - var i, len; - for (i = 0, len = exports.skips.length; i < len; i++) { - if (exports.skips[i].test(name)) { - return false; - } - } - for (i = 0, len = exports.names.length; i < len; i++) { - if (exports.names[i].test(name)) { - return true; - } - } - return false; -} - -/** - * Coerce `val`. - * - * @param {Mixed} val - * @return {Mixed} - * @api private - */ - -function coerce(val) { - if (val instanceof Error) return val.stack || val.message; - return val; -} - - -/***/ }), -/* 113 */, -/* 114 */ -/***/ (function(module, exports, __webpack_require__) { - -module.exports = realpath -realpath.realpath = realpath -realpath.sync = realpathSync -realpath.realpathSync = realpathSync -realpath.monkeypatch = monkeypatch -realpath.unmonkeypatch = unmonkeypatch - -var fs = __webpack_require__(3) -var origRealpath = fs.realpath -var origRealpathSync = fs.realpathSync - -var version = process.version -var ok = /^v[0-5]\./.test(version) -var old = __webpack_require__(217) - -function newError (er) { - return er && er.syscall === 'realpath' && ( - er.code === 'ELOOP' || - er.code === 'ENOMEM' || - er.code === 'ENAMETOOLONG' - ) -} - -function realpath (p, cache, cb) { - if (ok) { - return origRealpath(p, cache, cb) - } - - if (typeof cache === 'function') { - cb = cache - cache = null - } - origRealpath(p, cache, function (er, result) { - if (newError(er)) { - old.realpath(p, cache, cb) - } else { - cb(er, result) - } - }) -} - -function realpathSync (p, cache) { - if (ok) { - return origRealpathSync(p, cache) - } - - try { - return origRealpathSync(p, cache) - } catch (er) { - if (newError(er)) { - return old.realpathSync(p, cache) - } else { - throw er - } - } -} - -function monkeypatch () { - fs.realpath = realpath - fs.realpathSync = realpathSync -} - -function unmonkeypatch () { - fs.realpath = origRealpath - fs.realpathSync = origRealpathSync -} - - -/***/ }), -/* 115 */ -/***/ (function(module, exports, __webpack_require__) { - -exports.alphasort = alphasort -exports.alphasorti = alphasorti -exports.setopts = setopts -exports.ownProp = ownProp -exports.makeAbs = makeAbs -exports.finish = finish -exports.mark = mark -exports.isIgnored = isIgnored -exports.childrenIgnored = childrenIgnored - -function ownProp (obj, field) { - return Object.prototype.hasOwnProperty.call(obj, field) -} - -var path = __webpack_require__(0) -var minimatch = __webpack_require__(60) -var isAbsolute = __webpack_require__(76) -var Minimatch = minimatch.Minimatch - -function alphasorti (a, b) { - return a.toLowerCase().localeCompare(b.toLowerCase()) -} - -function alphasort (a, b) { - return a.localeCompare(b) -} - -function setupIgnores (self, options) { - self.ignore = options.ignore || [] - - if (!Array.isArray(self.ignore)) - self.ignore = [self.ignore] - - if (self.ignore.length) { - self.ignore = self.ignore.map(ignoreMap) - } -} - -// ignore patterns are always in dot:true mode. -function ignoreMap (pattern) { - var gmatcher = null - if (pattern.slice(-3) === '/**') { - var gpattern = pattern.replace(/(\/\*\*)+$/, '') - gmatcher = new Minimatch(gpattern, { dot: true }) - } - - return { - matcher: new Minimatch(pattern, { dot: true }), - gmatcher: gmatcher - } -} - -function setopts (self, pattern, options) { - if (!options) - options = {} - - // base-matching: just use globstar for that. - if (options.matchBase && -1 === pattern.indexOf("/")) { - if (options.noglobstar) { - throw new Error("base matching requires globstar") - } - pattern = "**/" + pattern - } - - self.silent = !!options.silent - self.pattern = pattern - self.strict = options.strict !== false - self.realpath = !!options.realpath - self.realpathCache = options.realpathCache || Object.create(null) - self.follow = !!options.follow - self.dot = !!options.dot - self.mark = !!options.mark - self.nodir = !!options.nodir - if (self.nodir) - self.mark = true - self.sync = !!options.sync - self.nounique = !!options.nounique - self.nonull = !!options.nonull - self.nosort = !!options.nosort - self.nocase = !!options.nocase - self.stat = !!options.stat - self.noprocess = !!options.noprocess - self.absolute = !!options.absolute - - self.maxLength = options.maxLength || Infinity - self.cache = options.cache || Object.create(null) - self.statCache = options.statCache || Object.create(null) - self.symlinks = options.symlinks || Object.create(null) - - setupIgnores(self, options) - - self.changedCwd = false - var cwd = process.cwd() - if (!ownProp(options, "cwd")) - self.cwd = cwd - else { - self.cwd = path.resolve(options.cwd) - self.changedCwd = self.cwd !== cwd - } - - self.root = options.root || path.resolve(self.cwd, "/") - self.root = path.resolve(self.root) - if (process.platform === "win32") - self.root = self.root.replace(/\\/g, "/") - - // TODO: is an absolute `cwd` supposed to be resolved against `root`? - // e.g. { cwd: '/test', root: __dirname } === path.join(__dirname, '/test') - self.cwdAbs = isAbsolute(self.cwd) ? self.cwd : makeAbs(self, self.cwd) - if (process.platform === "win32") - self.cwdAbs = self.cwdAbs.replace(/\\/g, "/") - self.nomount = !!options.nomount - - // disable comments and negation in Minimatch. - // Note that they are not supported in Glob itself anyway. - options.nonegate = true - options.nocomment = true - - self.minimatch = new Minimatch(pattern, options) - self.options = self.minimatch.options -} - -function finish (self) { - var nou = self.nounique - var all = nou ? [] : Object.create(null) - - for (var i = 0, l = self.matches.length; i < l; i ++) { - var matches = self.matches[i] - if (!matches || Object.keys(matches).length === 0) { - if (self.nonull) { - // do like the shell, and spit out the literal glob - var literal = self.minimatch.globSet[i] - if (nou) - all.push(literal) - else - all[literal] = true - } - } else { - // had matches - var m = Object.keys(matches) - if (nou) - all.push.apply(all, m) - else - m.forEach(function (m) { - all[m] = true - }) - } - } - - if (!nou) - all = Object.keys(all) - - if (!self.nosort) - all = all.sort(self.nocase ? alphasorti : alphasort) - - // at *some* point we statted all of these - if (self.mark) { - for (var i = 0; i < all.length; i++) { - all[i] = self._mark(all[i]) - } - if (self.nodir) { - all = all.filter(function (e) { - var notDir = !(/\/$/.test(e)) - var c = self.cache[e] || self.cache[makeAbs(self, e)] - if (notDir && c) - notDir = c !== 'DIR' && !Array.isArray(c) - return notDir - }) - } - } - - if (self.ignore.length) - all = all.filter(function(m) { - return !isIgnored(self, m) - }) - - self.found = all -} - -function mark (self, p) { - var abs = makeAbs(self, p) - var c = self.cache[abs] - var m = p - if (c) { - var isDir = c === 'DIR' || Array.isArray(c) - var slash = p.slice(-1) === '/' - - if (isDir && !slash) - m += '/' - else if (!isDir && slash) - m = m.slice(0, -1) - - if (m !== p) { - var mabs = makeAbs(self, m) - self.statCache[mabs] = self.statCache[abs] - self.cache[mabs] = self.cache[abs] - } - } - - return m -} - -// lotta situps... -function makeAbs (self, f) { - var abs = f - if (f.charAt(0) === '/') { - abs = path.join(self.root, f) - } else if (isAbsolute(f) || f === '') { - abs = f - } else if (self.changedCwd) { - abs = path.resolve(self.cwd, f) - } else { - abs = path.resolve(f) - } - - if (process.platform === 'win32') - abs = abs.replace(/\\/g, '/') - - return abs -} - - -// Return true, if pattern ends with globstar '**', for the accompanying parent directory. -// Ex:- If node_modules/** is the pattern, add 'node_modules' to ignore list along with it's contents -function isIgnored (self, path) { - if (!self.ignore.length) - return false - - return self.ignore.some(function(item) { - return item.matcher.match(path) || !!(item.gmatcher && item.gmatcher.match(path)) - }) -} - -function childrenIgnored (self, path) { - if (!self.ignore.length) - return false - - return self.ignore.some(function(item) { - return !!(item.gmatcher && item.gmatcher.match(path)) - }) -} - - -/***/ }), -/* 116 */ -/***/ (function(module, exports, __webpack_require__) { - -var path = __webpack_require__(0); -var fs = __webpack_require__(3); -var _0777 = parseInt('0777', 8); - -module.exports = mkdirP.mkdirp = mkdirP.mkdirP = mkdirP; - -function mkdirP (p, opts, f, made) { - if (typeof opts === 'function') { - f = opts; - opts = {}; - } - else if (!opts || typeof opts !== 'object') { - opts = { mode: opts }; - } - - var mode = opts.mode; - var xfs = opts.fs || fs; - - if (mode === undefined) { - mode = _0777 & (~process.umask()); - } - if (!made) made = null; - - var cb = f || function () {}; - p = path.resolve(p); - - xfs.mkdir(p, mode, function (er) { - if (!er) { - made = made || p; - return cb(null, made); - } - switch (er.code) { - case 'ENOENT': - mkdirP(path.dirname(p), opts, function (er, made) { - if (er) cb(er, made); - else mkdirP(p, opts, cb, made); - }); - break; - - // In the case of any other error, just see if there's a dir - // there already. If so, then hooray! If not, then something - // is borked. - default: - xfs.stat(p, function (er2, stat) { - // if the stat fails, then that's super weird. - // let the original error be the failure reason. - if (er2 || !stat.isDirectory()) cb(er, made) - else cb(null, made); - }); - break; - } - }); -} - -mkdirP.sync = function sync (p, opts, made) { - if (!opts || typeof opts !== 'object') { - opts = { mode: opts }; - } - - var mode = opts.mode; - var xfs = opts.fs || fs; - - if (mode === undefined) { - mode = _0777 & (~process.umask()); - } - if (!made) made = null; - - p = path.resolve(p); - - try { - xfs.mkdirSync(p, mode); - made = made || p; - } - catch (err0) { - switch (err0.code) { - case 'ENOENT' : - made = sync(path.dirname(p), opts, made); - sync(p, opts, made); - break; - - // In the case of any other error, just see if there's a dir - // there already. If so, then hooray! If not, then something - // is borked. - default: - var stat; - try { - stat = xfs.statSync(p); - } - catch (err1) { - throw err0; - } - if (!stat.isDirectory()) throw err0; - break; - } - } - - return made; -}; - - -/***/ }), -/* 117 */, -/* 118 */, -/* 119 */, -/* 120 */, -/* 121 */, -/* 122 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = x => { - if (typeof x !== 'string') { - throw new TypeError('Expected a string, got ' + typeof x); - } - - // Catches EFBBBF (UTF-8 BOM) because the buffer-to-string - // conversion translates it to FEFF (UTF-16 BOM) - if (x.charCodeAt(0) === 0xFEFF) { - return x.slice(1); - } - - return x; -}; - - -/***/ }), -/* 123 */ -/***/ (function(module, exports) { - -// Returns a wrapper function that returns a wrapped callback -// The wrapper function should do some stuff, and return a -// presumably different callback function. -// This makes sure that own properties are retained, so that -// decorations and such are not lost along the way. -module.exports = wrappy -function wrappy (fn, cb) { - if (fn && cb) return wrappy(fn)(cb) - - if (typeof fn !== 'function') - throw new TypeError('need wrapper function') - - Object.keys(fn).forEach(function (k) { - wrapper[k] = fn[k] - }) - - return wrapper - - function wrapper() { - var args = new Array(arguments.length) - for (var i = 0; i < args.length; i++) { - args[i] = arguments[i] - } - var ret = fn.apply(this, args) - var cb = args[args.length-1] - if (typeof ret === 'function' && ret !== cb) { - Object.keys(cb).forEach(function (k) { - ret[k] = cb[k] - }) - } - return ret - } -} - - -/***/ }), -/* 124 */, -/* 125 */, -/* 126 */, -/* 127 */, -/* 128 */, -/* 129 */, -/* 130 */, -/* 131 */ -/***/ (function(module, exports, __webpack_require__) { - -// fallback for non-array-like ES3 and non-enumerable old V8 strings -var cof = __webpack_require__(47); -// eslint-disable-next-line no-prototype-builtins -module.exports = Object('z').propertyIsEnumerable(0) ? Object : function (it) { - return cof(it) == 'String' ? it.split('') : Object(it); -}; - - -/***/ }), -/* 132 */ -/***/ (function(module, exports, __webpack_require__) { - -// 19.1.2.14 / 15.2.3.14 Object.keys(O) -var $keys = __webpack_require__(195); -var enumBugKeys = __webpack_require__(101); - -module.exports = Object.keys || function keys(O) { - return $keys(O, enumBugKeys); -}; - - -/***/ }), -/* 133 */ -/***/ (function(module, exports, __webpack_require__) { - -// 7.1.13 ToObject(argument) -var defined = __webpack_require__(67); -module.exports = function (it) { - return Object(defined(it)); -}; - - -/***/ }), -/* 134 */, -/* 135 */, -/* 136 */, -/* 137 */, -/* 138 */, -/* 139 */, -/* 140 */, -/* 141 */, -/* 142 */, -/* 143 */, -/* 144 */, -/* 145 */ -/***/ (function(module, exports) { - -module.exports = {"name":"yarn","installationMethod":"unknown","version":"1.10.0-0","license":"BSD-2-Clause","preferGlobal":true,"description":"📦🐈 Fast, reliable, and secure dependency management.","dependencies":{"@zkochan/cmd-shim":"^2.2.4","babel-runtime":"^6.26.0","bytes":"^3.0.0","camelcase":"^4.0.0","chalk":"^2.1.0","commander":"^2.9.0","death":"^1.0.0","debug":"^3.0.0","deep-equal":"^1.0.1","detect-indent":"^5.0.0","dnscache":"^1.0.1","glob":"^7.1.1","gunzip-maybe":"^1.4.0","hash-for-dep":"^1.2.3","imports-loader":"^0.8.0","ini":"^1.3.4","inquirer":"^3.0.1","invariant":"^2.2.0","is-builtin-module":"^2.0.0","is-ci":"^1.0.10","is-webpack-bundle":"^1.0.0","leven":"^2.0.0","loud-rejection":"^1.2.0","micromatch":"^2.3.11","mkdirp":"^0.5.1","node-emoji":"^1.6.1","normalize-url":"^2.0.0","npm-logical-tree":"^1.2.1","object-path":"^0.11.2","proper-lockfile":"^2.0.0","puka":"^1.0.0","read":"^1.0.7","request":"^2.87.0","request-capture-har":"^1.2.2","rimraf":"^2.5.0","semver":"^5.1.0","ssri":"^5.3.0","strip-ansi":"^4.0.0","strip-bom":"^3.0.0","tar-fs":"^1.16.0","tar-stream":"^1.6.1","uuid":"^3.0.1","v8-compile-cache":"^2.0.0","validate-npm-package-license":"^3.0.3","yn":"^2.0.0"},"devDependencies":{"babel-core":"^6.26.0","babel-eslint":"^7.2.3","babel-loader":"^6.2.5","babel-plugin-array-includes":"^2.0.3","babel-plugin-transform-builtin-extend":"^1.1.2","babel-plugin-transform-inline-imports-commonjs":"^1.0.0","babel-plugin-transform-runtime":"^6.4.3","babel-preset-env":"^1.6.0","babel-preset-flow":"^6.23.0","babel-preset-stage-0":"^6.0.0","babylon":"^6.5.0","commitizen":"^2.9.6","cz-conventional-changelog":"^2.0.0","eslint":"^4.3.0","eslint-config-fb-strict":"^22.0.0","eslint-plugin-babel":"^5.0.0","eslint-plugin-flowtype":"^2.35.0","eslint-plugin-jasmine":"^2.6.2","eslint-plugin-jest":"^21.0.0","eslint-plugin-jsx-a11y":"^6.0.2","eslint-plugin-prefer-object-spread":"^1.2.1","eslint-plugin-prettier":"^2.1.2","eslint-plugin-react":"^7.1.0","eslint-plugin-relay":"^0.0.24","eslint-plugin-yarn-internal":"file:scripts/eslint-rules","execa":"^0.10.0","flow-bin":"^0.66.0","git-release-notes":"^3.0.0","gulp":"^3.9.0","gulp-babel":"^7.0.0","gulp-if":"^2.0.1","gulp-newer":"^1.0.0","gulp-plumber":"^1.0.1","gulp-sourcemaps":"^2.2.0","gulp-util":"^3.0.7","gulp-watch":"^5.0.0","jest":"^22.4.4","jsinspect":"^0.12.6","minimatch":"^3.0.4","mock-stdin":"^0.3.0","prettier":"^1.5.2","temp":"^0.8.3","webpack":"^2.1.0-beta.25","yargs":"^6.3.0"},"resolutions":{"sshpk":"^1.14.2"},"engines":{"node":">=4.0.0"},"repository":"yarnpkg/yarn","bin":{"yarn":"./bin/yarn.js","yarnpkg":"./bin/yarn.js"},"scripts":{"build":"gulp build","build-bundle":"node ./scripts/build-webpack.js","build-chocolatey":"powershell ./scripts/build-chocolatey.ps1","build-deb":"./scripts/build-deb.sh","build-dist":"bash ./scripts/build-dist.sh","build-win-installer":"scripts\\build-windows-installer.bat","changelog":"git-release-notes $(git describe --tags --abbrev=0 $(git describe --tags --abbrev=0)^)..$(git describe --tags --abbrev=0) scripts/changelog.md","dupe-check":"yarn jsinspect ./src","lint":"eslint . && flow check","pkg-tests":"yarn --cwd packages/pkg-tests jest yarn.test.js","prettier":"eslint src __tests__ --fix","release-branch":"./scripts/release-branch.sh","test":"yarn lint && yarn test-only","test-only":"node --max_old_space_size=4096 node_modules/jest/bin/jest.js --verbose","test-only-debug":"node --inspect-brk --max_old_space_size=4096 node_modules/jest/bin/jest.js --runInBand --verbose","test-coverage":"node --max_old_space_size=4096 node_modules/jest/bin/jest.js --coverage --verbose","watch":"gulp watch","commit":"git-cz"},"jest":{"collectCoverageFrom":["src/**/*.js"],"testEnvironment":"node","modulePathIgnorePatterns":["__tests__/fixtures/","packages/pkg-tests/pkg-tests-fixtures","dist/"],"testPathIgnorePatterns":["__tests__/(fixtures|__mocks__)/","updates/","_(temp|mock|install|init|helpers).js$","packages/pkg-tests"]},"config":{"commitizen":{"path":"./node_modules/cz-conventional-changelog"}}} - -/***/ }), -/* 146 */, -/* 147 */, -/* 148 */, -/* 149 */, -/* 150 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.default = stringify; - -var _misc; - -function _load_misc() { - return _misc = __webpack_require__(12); -} - -var _constants; - -function _load_constants() { - return _constants = __webpack_require__(6); -} - -var _package; - -function _load_package() { - return _package = __webpack_require__(145); -} - -const NODE_VERSION = process.version; - -function shouldWrapKey(str) { - return str.indexOf('true') === 0 || str.indexOf('false') === 0 || /[:\s\n\\",\[\]]/g.test(str) || /^[0-9]/g.test(str) || !/^[a-zA-Z]/g.test(str); -} - -function maybeWrap(str) { - if (typeof str === 'boolean' || typeof str === 'number' || shouldWrapKey(str)) { - return JSON.stringify(str); - } else { - return str; - } -} - -const priorities = { - name: 1, - version: 2, - uid: 3, - resolved: 4, - integrity: 5, - registry: 6, - dependencies: 7 -}; - -function priorityThenAlphaSort(a, b) { - if (priorities[a] || priorities[b]) { - return (priorities[a] || 100) > (priorities[b] || 100) ? 1 : -1; - } else { - return (0, (_misc || _load_misc()).sortAlpha)(a, b); - } -} - -function _stringify(obj, options) { - if (typeof obj !== 'object') { - throw new TypeError(); - } - - const indent = options.indent; - const lines = []; - - // Sorting order needs to be consistent between runs, we run native sort by name because there are no - // problems with it being unstable because there are no to keys the same - // However priorities can be duplicated and native sort can shuffle things from run to run - const keys = Object.keys(obj).sort(priorityThenAlphaSort); - - let addedKeys = []; - - for (let i = 0; i < keys.length; i++) { - const key = keys[i]; - const val = obj[key]; - if (val == null || addedKeys.indexOf(key) >= 0) { - continue; - } - - const valKeys = [key]; - - // get all keys that have the same value equality, we only want this for objects - if (typeof val === 'object') { - for (let j = i + 1; j < keys.length; j++) { - const key = keys[j]; - if (val === obj[key]) { - valKeys.push(key); - } - } - } - - const keyLine = valKeys.sort((_misc || _load_misc()).sortAlpha).map(maybeWrap).join(', '); - - if (typeof val === 'string' || typeof val === 'boolean' || typeof val === 'number') { - lines.push(`${keyLine} ${maybeWrap(val)}`); - } else if (typeof val === 'object') { - lines.push(`${keyLine}:\n${_stringify(val, { indent: indent + ' ' })}` + (options.topLevel ? '\n' : '')); - } else { - throw new TypeError(); - } - - addedKeys = addedKeys.concat(valKeys); - } - - return indent + lines.join(`\n${indent}`); -} - -function stringify(obj, noHeader, enableVersions) { - const val = _stringify(obj, { - indent: '', - topLevel: true - }); - if (noHeader) { - return val; - } - - const lines = []; - lines.push('# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.'); - lines.push(`# yarn lockfile v${(_constants || _load_constants()).LOCKFILE_VERSION}`); - if (enableVersions) { - lines.push(`# yarn v${(_package || _load_package()).version}`); - lines.push(`# node ${NODE_VERSION}`); - } - lines.push('\n'); - lines.push(val); - - return lines.join('\n'); -} - -/***/ }), -/* 151 */, -/* 152 */, -/* 153 */, -/* 154 */, -/* 155 */, -/* 156 */, -/* 157 */, -/* 158 */, -/* 159 */, -/* 160 */, -/* 161 */, -/* 162 */, -/* 163 */, -/* 164 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.fileDatesEqual = exports.copyFile = exports.unlink = undefined; - -var _asyncToGenerator2; - -function _load_asyncToGenerator() { - return _asyncToGenerator2 = _interopRequireDefault(__webpack_require__(1)); -} - -// We want to preserve file timestamps when copying a file, since yarn uses them to decide if a file has -// changed compared to the cache. -// There are some OS specific cases here: -// * On linux, fs.copyFile does not preserve timestamps, but does on OSX and Win. -// * On windows, you must open a file with write permissions to call `fs.futimes`. -// * On OSX you can open with read permissions and still call `fs.futimes`. -let fixTimes = (() => { - var _ref3 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (fd, dest, data) { - const doOpen = fd === undefined; - let openfd = fd ? fd : -1; - - if (disableTimestampCorrection === undefined) { - // if timestamps match already, no correction is needed. - // the need to correct timestamps varies based on OS and node versions. - const destStat = yield lstat(dest); - disableTimestampCorrection = fileDatesEqual(destStat.mtime, data.mtime); - } - - if (disableTimestampCorrection) { - return; - } - - if (doOpen) { - try { - openfd = yield open(dest, 'a', data.mode); - } catch (er) { - // file is likely read-only - try { - openfd = yield open(dest, 'r', data.mode); - } catch (err) { - // We can't even open this file for reading. - return; - } - } - } - - try { - if (openfd) { - yield futimes(openfd, data.atime, data.mtime); - } - } catch (er) { - // If `futimes` throws an exception, we probably have a case of a read-only file on Windows. - // In this case we can just return. The incorrect timestamp will just cause that file to be recopied - // on subsequent installs, which will effect yarn performance but not break anything. - } finally { - if (doOpen && openfd) { - yield close(openfd); - } - } - }); - - return function fixTimes(_x7, _x8, _x9) { - return _ref3.apply(this, arguments); - }; -})(); - -// Compare file timestamps. -// Some versions of Node on windows zero the milliseconds when utime is used. - - -var _fs; - -function _load_fs() { - return _fs = _interopRequireDefault(__webpack_require__(3)); -} - -var _promise; - -function _load_promise() { - return _promise = __webpack_require__(40); -} - -function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } - -// This module serves as a wrapper for file operations that are inconsistant across node and OS versions. - -let disableTimestampCorrection = undefined; // OS dependent. will be detected on first file copy. - -const readFileBuffer = (0, (_promise || _load_promise()).promisify)((_fs || _load_fs()).default.readFile); -const close = (0, (_promise || _load_promise()).promisify)((_fs || _load_fs()).default.close); -const lstat = (0, (_promise || _load_promise()).promisify)((_fs || _load_fs()).default.lstat); -const open = (0, (_promise || _load_promise()).promisify)((_fs || _load_fs()).default.open); -const futimes = (0, (_promise || _load_promise()).promisify)((_fs || _load_fs()).default.futimes); - -const write = (0, (_promise || _load_promise()).promisify)((_fs || _load_fs()).default.write); - -const unlink = exports.unlink = (0, (_promise || _load_promise()).promisify)(__webpack_require__(233)); - -/** - * Unlinks the destination to force a recreation. This is needed on case-insensitive file systems - * to force the correct naming when the filename has changed only in character-casing. (Jest -> jest). - */ -const copyFile = exports.copyFile = (() => { - var _ref = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (data, cleanup) { - try { - yield unlink(data.dest); - yield copyFilePoly(data.src, data.dest, 0, data); - } finally { - if (cleanup) { - cleanup(); - } - } - }); - - return function copyFile(_x, _x2) { - return _ref.apply(this, arguments); - }; -})(); - -// Node 8.5.0 introduced `fs.copyFile` which is much faster, so use that when available. -// Otherwise we fall back to reading and writing files as buffers. -const copyFilePoly = (src, dest, flags, data) => { - if ((_fs || _load_fs()).default.copyFile) { - return new Promise((resolve, reject) => (_fs || _load_fs()).default.copyFile(src, dest, flags, err => { - if (err) { - reject(err); - } else { - fixTimes(undefined, dest, data).then(() => resolve()).catch(ex => reject(ex)); - } - })); - } else { - return copyWithBuffer(src, dest, flags, data); - } -}; - -const copyWithBuffer = (() => { - var _ref2 = (0, (_asyncToGenerator2 || _load_asyncToGenerator()).default)(function* (src, dest, flags, data) { - // Use open -> write -> futimes -> close sequence to avoid opening the file twice: - // one with writeFile and one with utimes - const fd = yield open(dest, 'w', data.mode); - try { - const buffer = yield readFileBuffer(src); - yield write(fd, buffer, 0, buffer.length); - yield fixTimes(fd, dest, data); - } finally { - yield close(fd); - } - }); - - return function copyWithBuffer(_x3, _x4, _x5, _x6) { - return _ref2.apply(this, arguments); - }; -})();const fileDatesEqual = exports.fileDatesEqual = (a, b) => { - const aTime = a.getTime(); - const bTime = b.getTime(); - - if (process.platform !== 'win32') { - return aTime === bTime; - } - - // See https://github.com/nodejs/node/pull/12607 - // Submillisecond times from stat and utimes are truncated on Windows, - // causing a file with mtime 8.0079998 and 8.0081144 to become 8.007 and 8.008 - // and making it impossible to update these files to their correct timestamps. - if (Math.abs(aTime - bTime) <= 1) { - return true; - } - - const aTimeSec = Math.floor(aTime / 1000); - const bTimeSec = Math.floor(bTime / 1000); - - // See https://github.com/nodejs/node/issues/2069 - // Some versions of Node on windows zero the milliseconds when utime is used - // So if any of the time has a milliseconds part of zero we suspect that the - // bug is present and compare only seconds. - if (aTime - aTimeSec * 1000 === 0 || bTime - bTimeSec * 1000 === 0) { - return aTimeSec === bTimeSec; - } - - return aTime === bTime; -}; - -/***/ }), -/* 165 */, -/* 166 */, -/* 167 */, -/* 168 */, -/* 169 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.isFakeRoot = isFakeRoot; -exports.isRootUser = isRootUser; -function getUid() { - if (process.platform !== 'win32' && process.getuid) { - return process.getuid(); - } - return null; -} - -exports.default = isRootUser(getUid()) && !isFakeRoot(); -function isFakeRoot() { - return Boolean(process.env.FAKEROOTKEY); -} - -function isRootUser(uid) { - return uid === 0; -} - -/***/ }), -/* 170 */, -/* 171 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", { - value: true -}); -exports.getDataDir = getDataDir; -exports.getCacheDir = getCacheDir; -exports.getConfigDir = getConfigDir; -const path = __webpack_require__(0); -const userHome = __webpack_require__(45).default; - -const FALLBACK_CONFIG_DIR = path.join(userHome, '.config', 'yarn'); -const FALLBACK_CACHE_DIR = path.join(userHome, '.cache', 'yarn'); - -function getDataDir() { - if (process.platform === 'win32') { - const WIN32_APPDATA_DIR = getLocalAppDataDir(); - return WIN32_APPDATA_DIR == null ? FALLBACK_CONFIG_DIR : path.join(WIN32_APPDATA_DIR, 'Data'); - } else if (process.env.XDG_DATA_HOME) { - return path.join(process.env.XDG_DATA_HOME, 'yarn'); - } else { - // This could arguably be ~/Library/Application Support/Yarn on Macs, - // but that feels unintuitive for a cli tool - - // Instead, use our prior fallback. Some day this could be - // path.join(userHome, '.local', 'share', 'yarn') - // or return path.join(WIN32_APPDATA_DIR, 'Data') on win32 - return FALLBACK_CONFIG_DIR; - } -} - -function getCacheDir() { - if (process.platform === 'win32') { - // process.env.TEMP also exists, but most apps put caches here - return path.join(getLocalAppDataDir() || path.join(userHome, 'AppData', 'Local', 'Yarn'), 'Cache'); - } else if (process.env.XDG_CACHE_HOME) { - return path.join(process.env.XDG_CACHE_HOME, 'yarn'); - } else if (process.platform === 'darwin') { - return path.join(userHome, 'Library', 'Caches', 'Yarn'); - } else { - return FALLBACK_CACHE_DIR; - } -} - -function getConfigDir() { - if (process.platform === 'win32') { - // Use our prior fallback. Some day this could be - // return path.join(WIN32_APPDATA_DIR, 'Config') - const WIN32_APPDATA_DIR = getLocalAppDataDir(); - return WIN32_APPDATA_DIR == null ? FALLBACK_CONFIG_DIR : path.join(WIN32_APPDATA_DIR, 'Config'); - } else if (process.env.XDG_CONFIG_HOME) { - return path.join(process.env.XDG_CONFIG_HOME, 'yarn'); - } else { - return FALLBACK_CONFIG_DIR; - } -} - -function getLocalAppDataDir() { - return process.env.LOCALAPPDATA ? path.join(process.env.LOCALAPPDATA, 'Yarn') : null; -} - -/***/ }), -/* 172 */, -/* 173 */ -/***/ (function(module, exports, __webpack_require__) { - -module.exports = { "default": __webpack_require__(179), __esModule: true }; - -/***/ }), -/* 174 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = balanced; -function balanced(a, b, str) { - if (a instanceof RegExp) a = maybeMatch(a, str); - if (b instanceof RegExp) b = maybeMatch(b, str); - - var r = range(a, b, str); - - return r && { - start: r[0], - end: r[1], - pre: str.slice(0, r[0]), - body: str.slice(r[0] + a.length, r[1]), - post: str.slice(r[1] + b.length) - }; -} - -function maybeMatch(reg, str) { - var m = str.match(reg); - return m ? m[0] : null; -} - -balanced.range = range; -function range(a, b, str) { - var begs, beg, left, right, result; - var ai = str.indexOf(a); - var bi = str.indexOf(b, ai + 1); - var i = ai; - - if (ai >= 0 && bi > 0) { - begs = []; - left = str.length; - - while (i >= 0 && !result) { - if (i == ai) { - begs.push(i); - ai = str.indexOf(a, i + 1); - } else if (begs.length == 1) { - result = [ begs.pop(), bi ]; - } else { - beg = begs.pop(); - if (beg < left) { - left = beg; - right = bi; - } - - bi = str.indexOf(b, i + 1); - } - - i = ai < bi && ai >= 0 ? ai : bi; - } - - if (begs.length) { - result = [ left, right ]; - } - } - - return result; -} - - -/***/ }), -/* 175 */ -/***/ (function(module, exports, __webpack_require__) { - -var concatMap = __webpack_require__(178); -var balanced = __webpack_require__(174); - -module.exports = expandTop; - -var escSlash = '\0SLASH'+Math.random()+'\0'; -var escOpen = '\0OPEN'+Math.random()+'\0'; -var escClose = '\0CLOSE'+Math.random()+'\0'; -var escComma = '\0COMMA'+Math.random()+'\0'; -var escPeriod = '\0PERIOD'+Math.random()+'\0'; - -function numeric(str) { - return parseInt(str, 10) == str - ? parseInt(str, 10) - : str.charCodeAt(0); -} - -function escapeBraces(str) { - return str.split('\\\\').join(escSlash) - .split('\\{').join(escOpen) - .split('\\}').join(escClose) - .split('\\,').join(escComma) - .split('\\.').join(escPeriod); -} - -function unescapeBraces(str) { - return str.split(escSlash).join('\\') - .split(escOpen).join('{') - .split(escClose).join('}') - .split(escComma).join(',') - .split(escPeriod).join('.'); -} - - -// Basically just str.split(","), but handling cases -// where we have nested braced sections, which should be -// treated as individual members, like {a,{b,c},d} -function parseCommaParts(str) { - if (!str) - return ['']; - - var parts = []; - var m = balanced('{', '}', str); - - if (!m) - return str.split(','); - - var pre = m.pre; - var body = m.body; - var post = m.post; - var p = pre.split(','); - - p[p.length-1] += '{' + body + '}'; - var postParts = parseCommaParts(post); - if (post.length) { - p[p.length-1] += postParts.shift(); - p.push.apply(p, postParts); - } - - parts.push.apply(parts, p); - - return parts; -} - -function expandTop(str) { - if (!str) - return []; - - // I don't know why Bash 4.3 does this, but it does. - // Anything starting with {} will have the first two bytes preserved - // but *only* at the top level, so {},a}b will not expand to anything, - // but a{},b}c will be expanded to [a}c,abc]. - // One could argue that this is a bug in Bash, but since the goal of - // this module is to match Bash's rules, we escape a leading {} - if (str.substr(0, 2) === '{}') { - str = '\\{\\}' + str.substr(2); - } - - return expand(escapeBraces(str), true).map(unescapeBraces); -} - -function identity(e) { - return e; -} - -function embrace(str) { - return '{' + str + '}'; -} -function isPadded(el) { - return /^-?0\d/.test(el); -} - -function lte(i, y) { - return i <= y; -} -function gte(i, y) { - return i >= y; -} - -function expand(str, isTop) { - var expansions = []; - - var m = balanced('{', '}', str); - if (!m || /\$$/.test(m.pre)) return [str]; - - var isNumericSequence = /^-?\d+\.\.-?\d+(?:\.\.-?\d+)?$/.test(m.body); - var isAlphaSequence = /^[a-zA-Z]\.\.[a-zA-Z](?:\.\.-?\d+)?$/.test(m.body); - var isSequence = isNumericSequence || isAlphaSequence; - var isOptions = m.body.indexOf(',') >= 0; - if (!isSequence && !isOptions) { - // {a},b} - if (m.post.match(/,.*\}/)) { - str = m.pre + '{' + m.body + escClose + m.post; - return expand(str); - } - return [str]; - } - - var n; - if (isSequence) { - n = m.body.split(/\.\./); - } else { - n = parseCommaParts(m.body); - if (n.length === 1) { - // x{{a,b}}y ==> x{a}y x{b}y - n = expand(n[0], false).map(embrace); - if (n.length === 1) { - var post = m.post.length - ? expand(m.post, false) - : ['']; - return post.map(function(p) { - return m.pre + n[0] + p; - }); - } - } - } - - // at this point, n is the parts, and we know it's not a comma set - // with a single entry. - - // no need to expand pre, since it is guaranteed to be free of brace-sets - var pre = m.pre; - var post = m.post.length - ? expand(m.post, false) - : ['']; - - var N; - - if (isSequence) { - var x = numeric(n[0]); - var y = numeric(n[1]); - var width = Math.max(n[0].length, n[1].length) - var incr = n.length == 3 - ? Math.abs(numeric(n[2])) - : 1; - var test = lte; - var reverse = y < x; - if (reverse) { - incr *= -1; - test = gte; - } - var pad = n.some(isPadded); - - N = []; - - for (var i = x; test(i, y); i += incr) { - var c; - if (isAlphaSequence) { - c = String.fromCharCode(i); - if (c === '\\') - c = ''; - } else { - c = String(i); - if (pad) { - var need = width - c.length; - if (need > 0) { - var z = new Array(need + 1).join('0'); - if (i < 0) - c = '-' + z + c.slice(1); - else - c = z + c; - } - } - } - N.push(c); - } - } else { - N = concatMap(n, function(el) { return expand(el, false) }); - } - - for (var j = 0; j < N.length; j++) { - for (var k = 0; k < post.length; k++) { - var expansion = pre + N[j] + post[k]; - if (!isTop || isSequence || expansion) - expansions.push(expansion); - } - } - - return expansions; -} - - - -/***/ }), -/* 176 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -function preserveCamelCase(str) { - let isLastCharLower = false; - let isLastCharUpper = false; - let isLastLastCharUpper = false; - - for (let i = 0; i < str.length; i++) { - const c = str[i]; - - if (isLastCharLower && /[a-zA-Z]/.test(c) && c.toUpperCase() === c) { - str = str.substr(0, i) + '-' + str.substr(i); - isLastCharLower = false; - isLastLastCharUpper = isLastCharUpper; - isLastCharUpper = true; - i++; - } else if (isLastCharUpper && isLastLastCharUpper && /[a-zA-Z]/.test(c) && c.toLowerCase() === c) { - str = str.substr(0, i - 1) + '-' + str.substr(i - 1); - isLastLastCharUpper = isLastCharUpper; - isLastCharUpper = false; - isLastCharLower = true; - } else { - isLastCharLower = c.toLowerCase() === c; - isLastLastCharUpper = isLastCharUpper; - isLastCharUpper = c.toUpperCase() === c; - } - } - - return str; -} - -module.exports = function (str) { - if (arguments.length > 1) { - str = Array.from(arguments) - .map(x => x.trim()) - .filter(x => x.length) - .join('-'); - } else { - str = str.trim(); - } - - if (str.length === 0) { - return ''; - } - - if (str.length === 1) { - return str.toLowerCase(); - } - - if (/^[a-z0-9]+$/.test(str)) { - return str; - } - - const hasUpperCase = str !== str.toLowerCase(); - - if (hasUpperCase) { - str = preserveCamelCase(str); - } - - return str - .replace(/^[_.\- ]+/, '') - .toLowerCase() - .replace(/[_.\- ]+(\w|$)/g, (m, p1) => p1.toUpperCase()); -}; - - -/***/ }), -/* 177 */, -/* 178 */ -/***/ (function(module, exports) { - -module.exports = function (xs, fn) { - var res = []; - for (var i = 0; i < xs.length; i++) { - var x = fn(xs[i], i); - if (isArray(x)) res.push.apply(res, x); - else res.push(x); - } - return res; -}; - -var isArray = Array.isArray || function (xs) { - return Object.prototype.toString.call(xs) === '[object Array]'; -}; - - -/***/ }), -/* 179 */ -/***/ (function(module, exports, __webpack_require__) { - -__webpack_require__(205); -__webpack_require__(207); -__webpack_require__(210); -__webpack_require__(206); -__webpack_require__(208); -__webpack_require__(209); -module.exports = __webpack_require__(23).Promise; - - -/***/ }), -/* 180 */ -/***/ (function(module, exports) { - -module.exports = function () { /* empty */ }; - - -/***/ }), -/* 181 */ -/***/ (function(module, exports) { - -module.exports = function (it, Constructor, name, forbiddenField) { - if (!(it instanceof Constructor) || (forbiddenField !== undefined && forbiddenField in it)) { - throw TypeError(name + ': incorrect invocation!'); - } return it; -}; - - -/***/ }), -/* 182 */ -/***/ (function(module, exports, __webpack_require__) { - -// false -> Array#indexOf -// true -> Array#includes -var toIObject = __webpack_require__(74); -var toLength = __webpack_require__(110); -var toAbsoluteIndex = __webpack_require__(200); -module.exports = function (IS_INCLUDES) { - return function ($this, el, fromIndex) { - var O = toIObject($this); - var length = toLength(O.length); - var index = toAbsoluteIndex(fromIndex, length); - var value; - // Array#includes uses SameValueZero equality algorithm - // eslint-disable-next-line no-self-compare - if (IS_INCLUDES && el != el) while (length > index) { - value = O[index++]; - // eslint-disable-next-line no-self-compare - if (value != value) return true; - // Array#indexOf ignores holes, Array#includes - not - } else for (;length > index; index++) if (IS_INCLUDES || index in O) { - if (O[index] === el) return IS_INCLUDES || index || 0; - } return !IS_INCLUDES && -1; - }; -}; - - -/***/ }), -/* 183 */ -/***/ (function(module, exports, __webpack_require__) { - -var ctx = __webpack_require__(48); -var call = __webpack_require__(187); -var isArrayIter = __webpack_require__(186); -var anObject = __webpack_require__(27); -var toLength = __webpack_require__(110); -var getIterFn = __webpack_require__(203); -var BREAK = {}; -var RETURN = {}; -var exports = module.exports = function (iterable, entries, fn, that, ITERATOR) { - var iterFn = ITERATOR ? function () { return iterable; } : getIterFn(iterable); - var f = ctx(fn, that, entries ? 2 : 1); - var index = 0; - var length, step, iterator, result; - if (typeof iterFn != 'function') throw TypeError(iterable + ' is not iterable!'); - // fast case for arrays with default iterator - if (isArrayIter(iterFn)) for (length = toLength(iterable.length); length > index; index++) { - result = entries ? f(anObject(step = iterable[index])[0], step[1]) : f(iterable[index]); - if (result === BREAK || result === RETURN) return result; - } else for (iterator = iterFn.call(iterable); !(step = iterator.next()).done;) { - result = call(iterator, f, step.value, entries); - if (result === BREAK || result === RETURN) return result; - } -}; -exports.BREAK = BREAK; -exports.RETURN = RETURN; - - -/***/ }), -/* 184 */ -/***/ (function(module, exports, __webpack_require__) { - -module.exports = !__webpack_require__(33) && !__webpack_require__(85)(function () { - return Object.defineProperty(__webpack_require__(68)('div'), 'a', { get: function () { return 7; } }).a != 7; -}); - - -/***/ }), -/* 185 */ -/***/ (function(module, exports) { - -// fast apply, http://jsperf.lnkit.com/fast-apply/5 -module.exports = function (fn, args, that) { - var un = that === undefined; - switch (args.length) { - case 0: return un ? fn() - : fn.call(that); - case 1: return un ? fn(args[0]) - : fn.call(that, args[0]); - case 2: return un ? fn(args[0], args[1]) - : fn.call(that, args[0], args[1]); - case 3: return un ? fn(args[0], args[1], args[2]) - : fn.call(that, args[0], args[1], args[2]); - case 4: return un ? fn(args[0], args[1], args[2], args[3]) - : fn.call(that, args[0], args[1], args[2], args[3]); - } return fn.apply(that, args); -}; - - -/***/ }), -/* 186 */ -/***/ (function(module, exports, __webpack_require__) { - -// check on default Array iterator -var Iterators = __webpack_require__(35); -var ITERATOR = __webpack_require__(13)('iterator'); -var ArrayProto = Array.prototype; - -module.exports = function (it) { - return it !== undefined && (Iterators.Array === it || ArrayProto[ITERATOR] === it); -}; - - -/***/ }), -/* 187 */ -/***/ (function(module, exports, __webpack_require__) { - -// call something on iterator step with safe closing on error -var anObject = __webpack_require__(27); -module.exports = function (iterator, fn, value, entries) { - try { - return entries ? fn(anObject(value)[0], value[1]) : fn(value); - // 7.4.6 IteratorClose(iterator, completion) - } catch (e) { - var ret = iterator['return']; - if (ret !== undefined) anObject(ret.call(iterator)); - throw e; - } -}; - - -/***/ }), -/* 188 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var create = __webpack_require__(192); -var descriptor = __webpack_require__(106); -var setToStringTag = __webpack_require__(71); -var IteratorPrototype = {}; - -// 25.1.2.1.1 %IteratorPrototype%[@@iterator]() -__webpack_require__(31)(IteratorPrototype, __webpack_require__(13)('iterator'), function () { return this; }); - -module.exports = function (Constructor, NAME, next) { - Constructor.prototype = create(IteratorPrototype, { next: descriptor(1, next) }); - setToStringTag(Constructor, NAME + ' Iterator'); -}; - - -/***/ }), -/* 189 */ -/***/ (function(module, exports, __webpack_require__) { - -var ITERATOR = __webpack_require__(13)('iterator'); -var SAFE_CLOSING = false; - -try { - var riter = [7][ITERATOR](); - riter['return'] = function () { SAFE_CLOSING = true; }; - // eslint-disable-next-line no-throw-literal - Array.from(riter, function () { throw 2; }); -} catch (e) { /* empty */ } - -module.exports = function (exec, skipClosing) { - if (!skipClosing && !SAFE_CLOSING) return false; - var safe = false; - try { - var arr = [7]; - var iter = arr[ITERATOR](); - iter.next = function () { return { done: safe = true }; }; - arr[ITERATOR] = function () { return iter; }; - exec(arr); - } catch (e) { /* empty */ } - return safe; -}; - - -/***/ }), -/* 190 */ -/***/ (function(module, exports) { - -module.exports = function (done, value) { - return { value: value, done: !!done }; -}; - - -/***/ }), -/* 191 */ -/***/ (function(module, exports, __webpack_require__) { - -var global = __webpack_require__(11); -var macrotask = __webpack_require__(109).set; -var Observer = global.MutationObserver || global.WebKitMutationObserver; -var process = global.process; -var Promise = global.Promise; -var isNode = __webpack_require__(47)(process) == 'process'; - -module.exports = function () { - var head, last, notify; - - var flush = function () { - var parent, fn; - if (isNode && (parent = process.domain)) parent.exit(); - while (head) { - fn = head.fn; - head = head.next; - try { - fn(); - } catch (e) { - if (head) notify(); - else last = undefined; - throw e; - } - } last = undefined; - if (parent) parent.enter(); - }; - - // Node.js - if (isNode) { - notify = function () { - process.nextTick(flush); - }; - // browsers with MutationObserver, except iOS Safari - https://github.com/zloirock/core-js/issues/339 - } else if (Observer && !(global.navigator && global.navigator.standalone)) { - var toggle = true; - var node = document.createTextNode(''); - new Observer(flush).observe(node, { characterData: true }); // eslint-disable-line no-new - notify = function () { - node.data = toggle = !toggle; - }; - // environments with maybe non-completely correct, but existent Promise - } else if (Promise && Promise.resolve) { - // Promise.resolve without an argument throws an error in LG WebOS 2 - var promise = Promise.resolve(undefined); - notify = function () { - promise.then(flush); - }; - // for other environments - macrotask based on: - // - setImmediate - // - MessageChannel - // - window.postMessag - // - onreadystatechange - // - setTimeout - } else { - notify = function () { - // strange IE + webpack dev server bug - use .call(global) - macrotask.call(global, flush); - }; - } - - return function (fn) { - var task = { fn: fn, next: undefined }; - if (last) last.next = task; - if (!head) { - head = task; - notify(); - } last = task; - }; -}; - - -/***/ }), -/* 192 */ -/***/ (function(module, exports, __webpack_require__) { - -// 19.1.2.2 / 15.2.3.5 Object.create(O [, Properties]) -var anObject = __webpack_require__(27); -var dPs = __webpack_require__(193); -var enumBugKeys = __webpack_require__(101); -var IE_PROTO = __webpack_require__(72)('IE_PROTO'); -var Empty = function () { /* empty */ }; -var PROTOTYPE = 'prototype'; - -// Create object with fake `null` prototype: use iframe Object with cleared prototype -var createDict = function () { - // Thrash, waste and sodomy: IE GC bug - var iframe = __webpack_require__(68)('iframe'); - var i = enumBugKeys.length; - var lt = '<'; - var gt = '>'; - var iframeDocument; - iframe.style.display = 'none'; - __webpack_require__(102).appendChild(iframe); - iframe.src = 'javascript:'; // eslint-disable-line no-script-url - // createDict = iframe.contentWindow.Object; - // html.removeChild(iframe); - iframeDocument = iframe.contentWindow.document; - iframeDocument.open(); - iframeDocument.write(lt + 'script' + gt + 'document.F=Object' + lt + '/script' + gt); - iframeDocument.close(); - createDict = iframeDocument.F; - while (i--) delete createDict[PROTOTYPE][enumBugKeys[i]]; - return createDict(); -}; - -module.exports = Object.create || function create(O, Properties) { - var result; - if (O !== null) { - Empty[PROTOTYPE] = anObject(O); - result = new Empty(); - Empty[PROTOTYPE] = null; - // add "__proto__" for Object.getPrototypeOf polyfill - result[IE_PROTO] = O; - } else result = createDict(); - return Properties === undefined ? result : dPs(result, Properties); -}; - - -/***/ }), -/* 193 */ -/***/ (function(module, exports, __webpack_require__) { - -var dP = __webpack_require__(50); -var anObject = __webpack_require__(27); -var getKeys = __webpack_require__(132); - -module.exports = __webpack_require__(33) ? Object.defineProperties : function defineProperties(O, Properties) { - anObject(O); - var keys = getKeys(Properties); - var length = keys.length; - var i = 0; - var P; - while (length > i) dP.f(O, P = keys[i++], Properties[P]); - return O; -}; - - -/***/ }), -/* 194 */ -/***/ (function(module, exports, __webpack_require__) { - -// 19.1.2.9 / 15.2.3.2 Object.getPrototypeOf(O) -var has = __webpack_require__(49); -var toObject = __webpack_require__(133); -var IE_PROTO = __webpack_require__(72)('IE_PROTO'); -var ObjectProto = Object.prototype; - -module.exports = Object.getPrototypeOf || function (O) { - O = toObject(O); - if (has(O, IE_PROTO)) return O[IE_PROTO]; - if (typeof O.constructor == 'function' && O instanceof O.constructor) { - return O.constructor.prototype; - } return O instanceof Object ? ObjectProto : null; -}; - - -/***/ }), -/* 195 */ -/***/ (function(module, exports, __webpack_require__) { - -var has = __webpack_require__(49); -var toIObject = __webpack_require__(74); -var arrayIndexOf = __webpack_require__(182)(false); -var IE_PROTO = __webpack_require__(72)('IE_PROTO'); - -module.exports = function (object, names) { - var O = toIObject(object); - var i = 0; - var result = []; - var key; - for (key in O) if (key != IE_PROTO) has(O, key) && result.push(key); - // Don't enum bug & hidden keys - while (names.length > i) if (has(O, key = names[i++])) { - ~arrayIndexOf(result, key) || result.push(key); - } - return result; -}; - - -/***/ }), -/* 196 */ -/***/ (function(module, exports, __webpack_require__) { - -var hide = __webpack_require__(31); -module.exports = function (target, src, safe) { - for (var key in src) { - if (safe && target[key]) target[key] = src[key]; - else hide(target, key, src[key]); - } return target; -}; - - -/***/ }), -/* 197 */ -/***/ (function(module, exports, __webpack_require__) { - -module.exports = __webpack_require__(31); - - -/***/ }), -/* 198 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var global = __webpack_require__(11); -var core = __webpack_require__(23); -var dP = __webpack_require__(50); -var DESCRIPTORS = __webpack_require__(33); -var SPECIES = __webpack_require__(13)('species'); - -module.exports = function (KEY) { - var C = typeof core[KEY] == 'function' ? core[KEY] : global[KEY]; - if (DESCRIPTORS && C && !C[SPECIES]) dP.f(C, SPECIES, { - configurable: true, - get: function () { return this; } - }); -}; - - -/***/ }), -/* 199 */ -/***/ (function(module, exports, __webpack_require__) { - -var toInteger = __webpack_require__(73); -var defined = __webpack_require__(67); -// true -> String#at -// false -> String#codePointAt -module.exports = function (TO_STRING) { - return function (that, pos) { - var s = String(defined(that)); - var i = toInteger(pos); - var l = s.length; - var a, b; - if (i < 0 || i >= l) return TO_STRING ? '' : undefined; - a = s.charCodeAt(i); - return a < 0xd800 || a > 0xdbff || i + 1 === l || (b = s.charCodeAt(i + 1)) < 0xdc00 || b > 0xdfff - ? TO_STRING ? s.charAt(i) : a - : TO_STRING ? s.slice(i, i + 2) : (a - 0xd800 << 10) + (b - 0xdc00) + 0x10000; - }; -}; - - -/***/ }), -/* 200 */ -/***/ (function(module, exports, __webpack_require__) { - -var toInteger = __webpack_require__(73); -var max = Math.max; -var min = Math.min; -module.exports = function (index, length) { - index = toInteger(index); - return index < 0 ? max(index + length, 0) : min(index, length); -}; - - -/***/ }), -/* 201 */ -/***/ (function(module, exports, __webpack_require__) { - -// 7.1.1 ToPrimitive(input [, PreferredType]) -var isObject = __webpack_require__(34); -// instead of the ES6 spec version, we didn't implement @@toPrimitive case -// and the second argument - flag - preferred type is a string -module.exports = function (it, S) { - if (!isObject(it)) return it; - var fn, val; - if (S && typeof (fn = it.toString) == 'function' && !isObject(val = fn.call(it))) return val; - if (typeof (fn = it.valueOf) == 'function' && !isObject(val = fn.call(it))) return val; - if (!S && typeof (fn = it.toString) == 'function' && !isObject(val = fn.call(it))) return val; - throw TypeError("Can't convert object to primitive value"); -}; - - -/***/ }), -/* 202 */ -/***/ (function(module, exports, __webpack_require__) { - -var global = __webpack_require__(11); -var navigator = global.navigator; - -module.exports = navigator && navigator.userAgent || ''; - - -/***/ }), -/* 203 */ -/***/ (function(module, exports, __webpack_require__) { - -var classof = __webpack_require__(100); -var ITERATOR = __webpack_require__(13)('iterator'); -var Iterators = __webpack_require__(35); -module.exports = __webpack_require__(23).getIteratorMethod = function (it) { - if (it != undefined) return it[ITERATOR] - || it['@@iterator'] - || Iterators[classof(it)]; -}; - - -/***/ }), -/* 204 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var addToUnscopables = __webpack_require__(180); -var step = __webpack_require__(190); -var Iterators = __webpack_require__(35); -var toIObject = __webpack_require__(74); - -// 22.1.3.4 Array.prototype.entries() -// 22.1.3.13 Array.prototype.keys() -// 22.1.3.29 Array.prototype.values() -// 22.1.3.30 Array.prototype[@@iterator]() -module.exports = __webpack_require__(103)(Array, 'Array', function (iterated, kind) { - this._t = toIObject(iterated); // target - this._i = 0; // next index - this._k = kind; // kind -// 22.1.5.2.1 %ArrayIteratorPrototype%.next() -}, function () { - var O = this._t; - var kind = this._k; - var index = this._i++; - if (!O || index >= O.length) { - this._t = undefined; - return step(1); - } - if (kind == 'keys') return step(0, index); - if (kind == 'values') return step(0, O[index]); - return step(0, [index, O[index]]); -}, 'values'); - -// argumentsList[@@iterator] is %ArrayProto_values% (9.4.4.6, 9.4.4.7) -Iterators.Arguments = Iterators.Array; - -addToUnscopables('keys'); -addToUnscopables('values'); -addToUnscopables('entries'); - - -/***/ }), -/* 205 */ -/***/ (function(module, exports) { - - - -/***/ }), -/* 206 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var LIBRARY = __webpack_require__(69); -var global = __webpack_require__(11); -var ctx = __webpack_require__(48); -var classof = __webpack_require__(100); -var $export = __webpack_require__(41); -var isObject = __webpack_require__(34); -var aFunction = __webpack_require__(46); -var anInstance = __webpack_require__(181); -var forOf = __webpack_require__(183); -var speciesConstructor = __webpack_require__(108); -var task = __webpack_require__(109).set; -var microtask = __webpack_require__(191)(); -var newPromiseCapabilityModule = __webpack_require__(70); -var perform = __webpack_require__(104); -var userAgent = __webpack_require__(202); -var promiseResolve = __webpack_require__(105); -var PROMISE = 'Promise'; -var TypeError = global.TypeError; -var process = global.process; -var versions = process && process.versions; -var v8 = versions && versions.v8 || ''; -var $Promise = global[PROMISE]; -var isNode = classof(process) == 'process'; -var empty = function () { /* empty */ }; -var Internal, newGenericPromiseCapability, OwnPromiseCapability, Wrapper; -var newPromiseCapability = newGenericPromiseCapability = newPromiseCapabilityModule.f; - -var USE_NATIVE = !!function () { - try { - // correct subclassing with @@species support - var promise = $Promise.resolve(1); - var FakePromise = (promise.constructor = {})[__webpack_require__(13)('species')] = function (exec) { - exec(empty, empty); - }; - // unhandled rejections tracking support, NodeJS Promise without it fails @@species test - return (isNode || typeof PromiseRejectionEvent == 'function') - && promise.then(empty) instanceof FakePromise - // v8 6.6 (Node 10 and Chrome 66) have a bug with resolving custom thenables - // https://bugs.chromium.org/p/chromium/issues/detail?id=830565 - // we can't detect it synchronously, so just check versions - && v8.indexOf('6.6') !== 0 - && userAgent.indexOf('Chrome/66') === -1; - } catch (e) { /* empty */ } -}(); - -// helpers -var isThenable = function (it) { - var then; - return isObject(it) && typeof (then = it.then) == 'function' ? then : false; -}; -var notify = function (promise, isReject) { - if (promise._n) return; - promise._n = true; - var chain = promise._c; - microtask(function () { - var value = promise._v; - var ok = promise._s == 1; - var i = 0; - var run = function (reaction) { - var handler = ok ? reaction.ok : reaction.fail; - var resolve = reaction.resolve; - var reject = reaction.reject; - var domain = reaction.domain; - var result, then, exited; - try { - if (handler) { - if (!ok) { - if (promise._h == 2) onHandleUnhandled(promise); - promise._h = 1; - } - if (handler === true) result = value; - else { - if (domain) domain.enter(); - result = handler(value); // may throw - if (domain) { - domain.exit(); - exited = true; - } - } - if (result === reaction.promise) { - reject(TypeError('Promise-chain cycle')); - } else if (then = isThenable(result)) { - then.call(result, resolve, reject); - } else resolve(result); - } else reject(value); - } catch (e) { - if (domain && !exited) domain.exit(); - reject(e); - } - }; - while (chain.length > i) run(chain[i++]); // variable length - can't use forEach - promise._c = []; - promise._n = false; - if (isReject && !promise._h) onUnhandled(promise); - }); -}; -var onUnhandled = function (promise) { - task.call(global, function () { - var value = promise._v; - var unhandled = isUnhandled(promise); - var result, handler, console; - if (unhandled) { - result = perform(function () { - if (isNode) { - process.emit('unhandledRejection', value, promise); - } else if (handler = global.onunhandledrejection) { - handler({ promise: promise, reason: value }); - } else if ((console = global.console) && console.error) { - console.error('Unhandled promise rejection', value); - } - }); - // Browsers should not trigger `rejectionHandled` event if it was handled here, NodeJS - should - promise._h = isNode || isUnhandled(promise) ? 2 : 1; - } promise._a = undefined; - if (unhandled && result.e) throw result.v; - }); -}; -var isUnhandled = function (promise) { - return promise._h !== 1 && (promise._a || promise._c).length === 0; -}; -var onHandleUnhandled = function (promise) { - task.call(global, function () { - var handler; - if (isNode) { - process.emit('rejectionHandled', promise); - } else if (handler = global.onrejectionhandled) { - handler({ promise: promise, reason: promise._v }); - } - }); -}; -var $reject = function (value) { - var promise = this; - if (promise._d) return; - promise._d = true; - promise = promise._w || promise; // unwrap - promise._v = value; - promise._s = 2; - if (!promise._a) promise._a = promise._c.slice(); - notify(promise, true); -}; -var $resolve = function (value) { - var promise = this; - var then; - if (promise._d) return; - promise._d = true; - promise = promise._w || promise; // unwrap - try { - if (promise === value) throw TypeError("Promise can't be resolved itself"); - if (then = isThenable(value)) { - microtask(function () { - var wrapper = { _w: promise, _d: false }; // wrap - try { - then.call(value, ctx($resolve, wrapper, 1), ctx($reject, wrapper, 1)); - } catch (e) { - $reject.call(wrapper, e); - } - }); - } else { - promise._v = value; - promise._s = 1; - notify(promise, false); - } - } catch (e) { - $reject.call({ _w: promise, _d: false }, e); // wrap - } -}; - -// constructor polyfill -if (!USE_NATIVE) { - // 25.4.3.1 Promise(executor) - $Promise = function Promise(executor) { - anInstance(this, $Promise, PROMISE, '_h'); - aFunction(executor); - Internal.call(this); - try { - executor(ctx($resolve, this, 1), ctx($reject, this, 1)); - } catch (err) { - $reject.call(this, err); - } - }; - // eslint-disable-next-line no-unused-vars - Internal = function Promise(executor) { - this._c = []; // <- awaiting reactions - this._a = undefined; // <- checked in isUnhandled reactions - this._s = 0; // <- state - this._d = false; // <- done - this._v = undefined; // <- value - this._h = 0; // <- rejection state, 0 - default, 1 - handled, 2 - unhandled - this._n = false; // <- notify - }; - Internal.prototype = __webpack_require__(196)($Promise.prototype, { - // 25.4.5.3 Promise.prototype.then(onFulfilled, onRejected) - then: function then(onFulfilled, onRejected) { - var reaction = newPromiseCapability(speciesConstructor(this, $Promise)); - reaction.ok = typeof onFulfilled == 'function' ? onFulfilled : true; - reaction.fail = typeof onRejected == 'function' && onRejected; - reaction.domain = isNode ? process.domain : undefined; - this._c.push(reaction); - if (this._a) this._a.push(reaction); - if (this._s) notify(this, false); - return reaction.promise; - }, - // 25.4.5.1 Promise.prototype.catch(onRejected) - 'catch': function (onRejected) { - return this.then(undefined, onRejected); - } - }); - OwnPromiseCapability = function () { - var promise = new Internal(); - this.promise = promise; - this.resolve = ctx($resolve, promise, 1); - this.reject = ctx($reject, promise, 1); - }; - newPromiseCapabilityModule.f = newPromiseCapability = function (C) { - return C === $Promise || C === Wrapper - ? new OwnPromiseCapability(C) - : newGenericPromiseCapability(C); - }; -} - -$export($export.G + $export.W + $export.F * !USE_NATIVE, { Promise: $Promise }); -__webpack_require__(71)($Promise, PROMISE); -__webpack_require__(198)(PROMISE); -Wrapper = __webpack_require__(23)[PROMISE]; - -// statics -$export($export.S + $export.F * !USE_NATIVE, PROMISE, { - // 25.4.4.5 Promise.reject(r) - reject: function reject(r) { - var capability = newPromiseCapability(this); - var $$reject = capability.reject; - $$reject(r); - return capability.promise; - } -}); -$export($export.S + $export.F * (LIBRARY || !USE_NATIVE), PROMISE, { - // 25.4.4.6 Promise.resolve(x) - resolve: function resolve(x) { - return promiseResolve(LIBRARY && this === Wrapper ? $Promise : this, x); - } -}); -$export($export.S + $export.F * !(USE_NATIVE && __webpack_require__(189)(function (iter) { - $Promise.all(iter)['catch'](empty); -})), PROMISE, { - // 25.4.4.1 Promise.all(iterable) - all: function all(iterable) { - var C = this; - var capability = newPromiseCapability(C); - var resolve = capability.resolve; - var reject = capability.reject; - var result = perform(function () { - var values = []; - var index = 0; - var remaining = 1; - forOf(iterable, false, function (promise) { - var $index = index++; - var alreadyCalled = false; - values.push(undefined); - remaining++; - C.resolve(promise).then(function (value) { - if (alreadyCalled) return; - alreadyCalled = true; - values[$index] = value; - --remaining || resolve(values); - }, reject); - }); - --remaining || resolve(values); - }); - if (result.e) reject(result.v); - return capability.promise; - }, - // 25.4.4.4 Promise.race(iterable) - race: function race(iterable) { - var C = this; - var capability = newPromiseCapability(C); - var reject = capability.reject; - var result = perform(function () { - forOf(iterable, false, function (promise) { - C.resolve(promise).then(capability.resolve, reject); - }); - }); - if (result.e) reject(result.v); - return capability.promise; - } -}); - - -/***/ }), -/* 207 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var $at = __webpack_require__(199)(true); - -// 21.1.3.27 String.prototype[@@iterator]() -__webpack_require__(103)(String, 'String', function (iterated) { - this._t = String(iterated); // target - this._i = 0; // next index -// 21.1.5.2.1 %StringIteratorPrototype%.next() -}, function () { - var O = this._t; - var index = this._i; - var point; - if (index >= O.length) return { value: undefined, done: true }; - point = $at(O, index); - this._i += point.length; - return { value: point, done: false }; -}); - - -/***/ }), -/* 208 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -// https://github.com/tc39/proposal-promise-finally - -var $export = __webpack_require__(41); -var core = __webpack_require__(23); -var global = __webpack_require__(11); -var speciesConstructor = __webpack_require__(108); -var promiseResolve = __webpack_require__(105); - -$export($export.P + $export.R, 'Promise', { 'finally': function (onFinally) { - var C = speciesConstructor(this, core.Promise || global.Promise); - var isFunction = typeof onFinally == 'function'; - return this.then( - isFunction ? function (x) { - return promiseResolve(C, onFinally()).then(function () { return x; }); - } : onFinally, - isFunction ? function (e) { - return promiseResolve(C, onFinally()).then(function () { throw e; }); - } : onFinally - ); -} }); - - -/***/ }), -/* 209 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -// https://github.com/tc39/proposal-promise-try -var $export = __webpack_require__(41); -var newPromiseCapability = __webpack_require__(70); -var perform = __webpack_require__(104); - -$export($export.S, 'Promise', { 'try': function (callbackfn) { - var promiseCapability = newPromiseCapability.f(this); - var result = perform(callbackfn); - (result.e ? promiseCapability.reject : promiseCapability.resolve)(result.v); - return promiseCapability.promise; -} }); - - -/***/ }), -/* 210 */ -/***/ (function(module, exports, __webpack_require__) { - -__webpack_require__(204); -var global = __webpack_require__(11); -var hide = __webpack_require__(31); -var Iterators = __webpack_require__(35); -var TO_STRING_TAG = __webpack_require__(13)('toStringTag'); - -var DOMIterables = ('CSSRuleList,CSSStyleDeclaration,CSSValueList,ClientRectList,DOMRectList,DOMStringList,' + - 'DOMTokenList,DataTransferItemList,FileList,HTMLAllCollection,HTMLCollection,HTMLFormElement,HTMLSelectElement,' + - 'MediaList,MimeTypeArray,NamedNodeMap,NodeList,PaintRequestList,Plugin,PluginArray,SVGLengthList,SVGNumberList,' + - 'SVGPathSegList,SVGPointList,SVGStringList,SVGTransformList,SourceBufferList,StyleSheetList,TextTrackCueList,' + - 'TextTrackList,TouchList').split(','); - -for (var i = 0; i < DOMIterables.length; i++) { - var NAME = DOMIterables[i]; - var Collection = global[NAME]; - var proto = Collection && Collection.prototype; - if (proto && !proto[TO_STRING_TAG]) hide(proto, TO_STRING_TAG, NAME); - Iterators[NAME] = Iterators.Array; -} - - -/***/ }), -/* 211 */ -/***/ (function(module, exports, __webpack_require__) { - -/** - * This is the web browser implementation of `debug()`. - * - * Expose `debug()` as the module. - */ - -exports = module.exports = __webpack_require__(112); -exports.log = log; -exports.formatArgs = formatArgs; -exports.save = save; -exports.load = load; -exports.useColors = useColors; -exports.storage = 'undefined' != typeof chrome - && 'undefined' != typeof chrome.storage - ? chrome.storage.local - : localstorage(); - -/** - * Colors. - */ - -exports.colors = [ - '#0000CC', '#0000FF', '#0033CC', '#0033FF', '#0066CC', '#0066FF', '#0099CC', - '#0099FF', '#00CC00', '#00CC33', '#00CC66', '#00CC99', '#00CCCC', '#00CCFF', - '#3300CC', '#3300FF', '#3333CC', '#3333FF', '#3366CC', '#3366FF', '#3399CC', - '#3399FF', '#33CC00', '#33CC33', '#33CC66', '#33CC99', '#33CCCC', '#33CCFF', - '#6600CC', '#6600FF', '#6633CC', '#6633FF', '#66CC00', '#66CC33', '#9900CC', - '#9900FF', '#9933CC', '#9933FF', '#99CC00', '#99CC33', '#CC0000', '#CC0033', - '#CC0066', '#CC0099', '#CC00CC', '#CC00FF', '#CC3300', '#CC3333', '#CC3366', - '#CC3399', '#CC33CC', '#CC33FF', '#CC6600', '#CC6633', '#CC9900', '#CC9933', - '#CCCC00', '#CCCC33', '#FF0000', '#FF0033', '#FF0066', '#FF0099', '#FF00CC', - '#FF00FF', '#FF3300', '#FF3333', '#FF3366', '#FF3399', '#FF33CC', '#FF33FF', - '#FF6600', '#FF6633', '#FF9900', '#FF9933', '#FFCC00', '#FFCC33' -]; - -/** - * Currently only WebKit-based Web Inspectors, Firefox >= v31, - * and the Firebug extension (any Firefox version) are known - * to support "%c" CSS customizations. - * - * TODO: add a `localStorage` variable to explicitly enable/disable colors - */ - -function useColors() { - // NB: In an Electron preload script, document will be defined but not fully - // initialized. Since we know we're in Chrome, we'll just detect this case - // explicitly - if (typeof window !== 'undefined' && window.process && window.process.type === 'renderer') { - return true; - } - - // Internet Explorer and Edge do not support colors. - if (typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/(edge|trident)\/(\d+)/)) { - return false; - } - - // is webkit? http://stackoverflow.com/a/16459606/376773 - // document is undefined in react-native: https://github.com/facebook/react-native/pull/1632 - return (typeof document !== 'undefined' && document.documentElement && document.documentElement.style && document.documentElement.style.WebkitAppearance) || - // is firebug? http://stackoverflow.com/a/398120/376773 - (typeof window !== 'undefined' && window.console && (window.console.firebug || (window.console.exception && window.console.table))) || - // is firefox >= v31? - // https://developer.mozilla.org/en-US/docs/Tools/Web_Console#Styling_messages - (typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/firefox\/(\d+)/) && parseInt(RegExp.$1, 10) >= 31) || - // double check webkit in userAgent just in case we are in a worker - (typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/applewebkit\/(\d+)/)); -} - -/** - * Map %j to `JSON.stringify()`, since no Web Inspectors do that by default. - */ - -exports.formatters.j = function(v) { - try { - return JSON.stringify(v); - } catch (err) { - return '[UnexpectedJSONParseError]: ' + err.message; - } -}; - - -/** - * Colorize log arguments if enabled. - * - * @api public - */ - -function formatArgs(args) { - var useColors = this.useColors; - - args[0] = (useColors ? '%c' : '') - + this.namespace - + (useColors ? ' %c' : ' ') - + args[0] - + (useColors ? '%c ' : ' ') - + '+' + exports.humanize(this.diff); - - if (!useColors) return; - - var c = 'color: ' + this.color; - args.splice(1, 0, c, 'color: inherit') - - // the final "%c" is somewhat tricky, because there could be other - // arguments passed either before or after the %c, so we need to - // figure out the correct index to insert the CSS into - var index = 0; - var lastC = 0; - args[0].replace(/%[a-zA-Z%]/g, function(match) { - if ('%%' === match) return; - index++; - if ('%c' === match) { - // we only are interested in the *last* %c - // (the user may have provided their own) - lastC = index; - } - }); - - args.splice(lastC, 0, c); -} - -/** - * Invokes `console.log()` when available. - * No-op when `console.log` is not a "function". - * - * @api public - */ - -function log() { - // this hackery is required for IE8/9, where - // the `console.log` function doesn't have 'apply' - return 'object' === typeof console - && console.log - && Function.prototype.apply.call(console.log, console, arguments); -} - -/** - * Save `namespaces`. - * - * @param {String} namespaces - * @api private - */ - -function save(namespaces) { - try { - if (null == namespaces) { - exports.storage.removeItem('debug'); - } else { - exports.storage.debug = namespaces; - } - } catch(e) {} -} - -/** - * Load `namespaces`. - * - * @return {String} returns the previously persisted debug modes - * @api private - */ - -function load() { - var r; - try { - r = exports.storage.debug; - } catch(e) {} - - // If debug isn't set in LS, and we're in Electron, try to load $DEBUG - if (!r && typeof process !== 'undefined' && 'env' in process) { - r = process.env.DEBUG; - } - - return r; -} - -/** - * Enable namespaces listed in `localStorage.debug` initially. - */ - -exports.enable(load()); - -/** - * Localstorage attempts to return the localstorage. - * - * This is necessary because safari throws - * when a user disables cookies/localstorage - * and you attempt to access it. - * - * @return {LocalStorage} - * @api private - */ - -function localstorage() { - try { - return window.localStorage; - } catch (e) {} -} - - -/***/ }), -/* 212 */ -/***/ (function(module, exports, __webpack_require__) { - -/** - * Detect Electron renderer process, which is node, but we should - * treat as a browser. - */ - -if (typeof process === 'undefined' || process.type === 'renderer') { - module.exports = __webpack_require__(211); -} else { - module.exports = __webpack_require__(213); -} - - -/***/ }), -/* 213 */ -/***/ (function(module, exports, __webpack_require__) { - -/** - * Module dependencies. - */ - -var tty = __webpack_require__(79); -var util = __webpack_require__(2); - -/** - * This is the Node.js implementation of `debug()`. - * - * Expose `debug()` as the module. - */ - -exports = module.exports = __webpack_require__(112); -exports.init = init; -exports.log = log; -exports.formatArgs = formatArgs; -exports.save = save; -exports.load = load; -exports.useColors = useColors; - -/** - * Colors. - */ - -exports.colors = [ 6, 2, 3, 4, 5, 1 ]; - -try { - var supportsColor = __webpack_require__(239); - if (supportsColor && supportsColor.level >= 2) { - exports.colors = [ - 20, 21, 26, 27, 32, 33, 38, 39, 40, 41, 42, 43, 44, 45, 56, 57, 62, 63, 68, - 69, 74, 75, 76, 77, 78, 79, 80, 81, 92, 93, 98, 99, 112, 113, 128, 129, 134, - 135, 148, 149, 160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, - 172, 173, 178, 179, 184, 185, 196, 197, 198, 199, 200, 201, 202, 203, 204, - 205, 206, 207, 208, 209, 214, 215, 220, 221 - ]; - } -} catch (err) { - // swallow - we only care if `supports-color` is available; it doesn't have to be. -} - -/** - * Build up the default `inspectOpts` object from the environment variables. - * - * $ DEBUG_COLORS=no DEBUG_DEPTH=10 DEBUG_SHOW_HIDDEN=enabled node script.js - */ - -exports.inspectOpts = Object.keys(process.env).filter(function (key) { - return /^debug_/i.test(key); -}).reduce(function (obj, key) { - // camel-case - var prop = key - .substring(6) - .toLowerCase() - .replace(/_([a-z])/g, function (_, k) { return k.toUpperCase() }); - - // coerce string value into JS value - var val = process.env[key]; - if (/^(yes|on|true|enabled)$/i.test(val)) val = true; - else if (/^(no|off|false|disabled)$/i.test(val)) val = false; - else if (val === 'null') val = null; - else val = Number(val); - - obj[prop] = val; - return obj; -}, {}); - -/** - * Is stdout a TTY? Colored output is enabled when `true`. - */ - -function useColors() { - return 'colors' in exports.inspectOpts - ? Boolean(exports.inspectOpts.colors) - : tty.isatty(process.stderr.fd); -} - -/** - * Map %o to `util.inspect()`, all on a single line. - */ - -exports.formatters.o = function(v) { - this.inspectOpts.colors = this.useColors; - return util.inspect(v, this.inspectOpts) - .split('\n').map(function(str) { - return str.trim() - }).join(' '); -}; - -/** - * Map %o to `util.inspect()`, allowing multiple lines if needed. - */ - -exports.formatters.O = function(v) { - this.inspectOpts.colors = this.useColors; - return util.inspect(v, this.inspectOpts); -}; - -/** - * Adds ANSI color escape codes if enabled. - * - * @api public - */ - -function formatArgs(args) { - var name = this.namespace; - var useColors = this.useColors; - - if (useColors) { - var c = this.color; - var colorCode = '\u001b[3' + (c < 8 ? c : '8;5;' + c); - var prefix = ' ' + colorCode + ';1m' + name + ' ' + '\u001b[0m'; - - args[0] = prefix + args[0].split('\n').join('\n' + prefix); - args.push(colorCode + 'm+' + exports.humanize(this.diff) + '\u001b[0m'); - } else { - args[0] = getDate() + name + ' ' + args[0]; - } -} - -function getDate() { - if (exports.inspectOpts.hideDate) { - return ''; - } else { - return new Date().toISOString() + ' '; - } -} - -/** - * Invokes `util.format()` with the specified arguments and writes to stderr. - */ - -function log() { - return process.stderr.write(util.format.apply(util, arguments) + '\n'); -} - -/** - * Save `namespaces`. - * - * @param {String} namespaces - * @api private - */ - -function save(namespaces) { - if (null == namespaces) { - // If you set a process.env field to null or undefined, it gets cast to the - // string 'null' or 'undefined'. Just delete instead. - delete process.env.DEBUG; - } else { - process.env.DEBUG = namespaces; - } -} - -/** - * Load `namespaces`. - * - * @return {String} returns the previously persisted debug modes - * @api private - */ - -function load() { - return process.env.DEBUG; -} - -/** - * Init logic for `debug` instances. - * - * Create a new `inspectOpts` object in case `useColors` is set - * differently for a particular `debug` instance. - */ - -function init (debug) { - debug.inspectOpts = {}; - - var keys = Object.keys(exports.inspectOpts); - for (var i = 0; i < keys.length; i++) { - debug.inspectOpts[keys[i]] = exports.inspectOpts[keys[i]]; - } -} - -/** - * Enable namespaces listed in `process.env.DEBUG` initially. - */ - -exports.enable(load()); - - -/***/ }), -/* 214 */, -/* 215 */, -/* 216 */, -/* 217 */ -/***/ (function(module, exports, __webpack_require__) { - -// Copyright Joyent, Inc. and other Node contributors. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. - -var pathModule = __webpack_require__(0); -var isWindows = process.platform === 'win32'; -var fs = __webpack_require__(3); - -// JavaScript implementation of realpath, ported from node pre-v6 - -var DEBUG = process.env.NODE_DEBUG && /fs/.test(process.env.NODE_DEBUG); - -function rethrow() { - // Only enable in debug mode. A backtrace uses ~1000 bytes of heap space and - // is fairly slow to generate. - var callback; - if (DEBUG) { - var backtrace = new Error; - callback = debugCallback; - } else - callback = missingCallback; - - return callback; - - function debugCallback(err) { - if (err) { - backtrace.message = err.message; - err = backtrace; - missingCallback(err); - } - } - - function missingCallback(err) { - if (err) { - if (process.throwDeprecation) - throw err; // Forgot a callback but don't know where? Use NODE_DEBUG=fs - else if (!process.noDeprecation) { - var msg = 'fs: missing callback ' + (err.stack || err.message); - if (process.traceDeprecation) - console.trace(msg); - else - console.error(msg); - } - } - } -} - -function maybeCallback(cb) { - return typeof cb === 'function' ? cb : rethrow(); -} - -var normalize = pathModule.normalize; - -// Regexp that finds the next partion of a (partial) path -// result is [base_with_slash, base], e.g. ['somedir/', 'somedir'] -if (isWindows) { - var nextPartRe = /(.*?)(?:[\/\\]+|$)/g; -} else { - var nextPartRe = /(.*?)(?:[\/]+|$)/g; -} - -// Regex to find the device root, including trailing slash. E.g. 'c:\\'. -if (isWindows) { - var splitRootRe = /^(?:[a-zA-Z]:|[\\\/]{2}[^\\\/]+[\\\/][^\\\/]+)?[\\\/]*/; -} else { - var splitRootRe = /^[\/]*/; -} - -exports.realpathSync = function realpathSync(p, cache) { - // make p is absolute - p = pathModule.resolve(p); - - if (cache && Object.prototype.hasOwnProperty.call(cache, p)) { - return cache[p]; - } - - var original = p, - seenLinks = {}, - knownHard = {}; - - // current character position in p - var pos; - // the partial path so far, including a trailing slash if any - var current; - // the partial path without a trailing slash (except when pointing at a root) - var base; - // the partial path scanned in the previous round, with slash - var previous; - - start(); - - function start() { - // Skip over roots - var m = splitRootRe.exec(p); - pos = m[0].length; - current = m[0]; - base = m[0]; - previous = ''; - - // On windows, check that the root exists. On unix there is no need. - if (isWindows && !knownHard[base]) { - fs.lstatSync(base); - knownHard[base] = true; - } - } - - // walk down the path, swapping out linked pathparts for their real - // values - // NB: p.length changes. - while (pos < p.length) { - // find the next part - nextPartRe.lastIndex = pos; - var result = nextPartRe.exec(p); - previous = current; - current += result[0]; - base = previous + result[1]; - pos = nextPartRe.lastIndex; - - // continue if not a symlink - if (knownHard[base] || (cache && cache[base] === base)) { - continue; - } - - var resolvedLink; - if (cache && Object.prototype.hasOwnProperty.call(cache, base)) { - // some known symbolic link. no need to stat again. - resolvedLink = cache[base]; - } else { - var stat = fs.lstatSync(base); - if (!stat.isSymbolicLink()) { - knownHard[base] = true; - if (cache) cache[base] = base; - continue; - } - - // read the link if it wasn't read before - // dev/ino always return 0 on windows, so skip the check. - var linkTarget = null; - if (!isWindows) { - var id = stat.dev.toString(32) + ':' + stat.ino.toString(32); - if (seenLinks.hasOwnProperty(id)) { - linkTarget = seenLinks[id]; - } - } - if (linkTarget === null) { - fs.statSync(base); - linkTarget = fs.readlinkSync(base); - } - resolvedLink = pathModule.resolve(previous, linkTarget); - // track this, if given a cache. - if (cache) cache[base] = resolvedLink; - if (!isWindows) seenLinks[id] = linkTarget; - } - - // resolve the link, then start over - p = pathModule.resolve(resolvedLink, p.slice(pos)); - start(); - } - - if (cache) cache[original] = p; - - return p; -}; - - -exports.realpath = function realpath(p, cache, cb) { - if (typeof cb !== 'function') { - cb = maybeCallback(cache); - cache = null; - } - - // make p is absolute - p = pathModule.resolve(p); - - if (cache && Object.prototype.hasOwnProperty.call(cache, p)) { - return process.nextTick(cb.bind(null, null, cache[p])); - } - - var original = p, - seenLinks = {}, - knownHard = {}; - - // current character position in p - var pos; - // the partial path so far, including a trailing slash if any - var current; - // the partial path without a trailing slash (except when pointing at a root) - var base; - // the partial path scanned in the previous round, with slash - var previous; - - start(); - - function start() { - // Skip over roots - var m = splitRootRe.exec(p); - pos = m[0].length; - current = m[0]; - base = m[0]; - previous = ''; - - // On windows, check that the root exists. On unix there is no need. - if (isWindows && !knownHard[base]) { - fs.lstat(base, function(err) { - if (err) return cb(err); - knownHard[base] = true; - LOOP(); - }); - } else { - process.nextTick(LOOP); - } - } - - // walk down the path, swapping out linked pathparts for their real - // values - function LOOP() { - // stop if scanned past end of path - if (pos >= p.length) { - if (cache) cache[original] = p; - return cb(null, p); - } - - // find the next part - nextPartRe.lastIndex = pos; - var result = nextPartRe.exec(p); - previous = current; - current += result[0]; - base = previous + result[1]; - pos = nextPartRe.lastIndex; - - // continue if not a symlink - if (knownHard[base] || (cache && cache[base] === base)) { - return process.nextTick(LOOP); - } - - if (cache && Object.prototype.hasOwnProperty.call(cache, base)) { - // known symbolic link. no need to stat again. - return gotResolvedLink(cache[base]); - } - - return fs.lstat(base, gotStat); - } - - function gotStat(err, stat) { - if (err) return cb(err); - - // if not a symlink, skip to the next path part - if (!stat.isSymbolicLink()) { - knownHard[base] = true; - if (cache) cache[base] = base; - return process.nextTick(LOOP); - } - - // stat & read the link if not read before - // call gotTarget as soon as the link target is known - // dev/ino always return 0 on windows, so skip the check. - if (!isWindows) { - var id = stat.dev.toString(32) + ':' + stat.ino.toString(32); - if (seenLinks.hasOwnProperty(id)) { - return gotTarget(null, seenLinks[id], base); - } - } - fs.stat(base, function(err) { - if (err) return cb(err); - - fs.readlink(base, function(err, target) { - if (!isWindows) seenLinks[id] = target; - gotTarget(err, target); - }); - }); - } - - function gotTarget(err, target, base) { - if (err) return cb(err); - - var resolvedLink = pathModule.resolve(previous, target); - if (cache) cache[base] = resolvedLink; - gotResolvedLink(resolvedLink); - } - - function gotResolvedLink(resolvedLink) { - // resolve the link, then start over - p = pathModule.resolve(resolvedLink, p.slice(pos)); - start(); - } -}; - - -/***/ }), -/* 218 */ -/***/ (function(module, exports, __webpack_require__) { - -module.exports = globSync -globSync.GlobSync = GlobSync - -var fs = __webpack_require__(3) -var rp = __webpack_require__(114) -var minimatch = __webpack_require__(60) -var Minimatch = minimatch.Minimatch -var Glob = __webpack_require__(75).Glob -var util = __webpack_require__(2) -var path = __webpack_require__(0) -var assert = __webpack_require__(22) -var isAbsolute = __webpack_require__(76) -var common = __webpack_require__(115) -var alphasort = common.alphasort -var alphasorti = common.alphasorti -var setopts = common.setopts -var ownProp = common.ownProp -var childrenIgnored = common.childrenIgnored -var isIgnored = common.isIgnored - -function globSync (pattern, options) { - if (typeof options === 'function' || arguments.length === 3) - throw new TypeError('callback provided to sync glob\n'+ - 'See: https://github.com/isaacs/node-glob/issues/167') - - return new GlobSync(pattern, options).found -} - -function GlobSync (pattern, options) { - if (!pattern) - throw new Error('must provide pattern') - - if (typeof options === 'function' || arguments.length === 3) - throw new TypeError('callback provided to sync glob\n'+ - 'See: https://github.com/isaacs/node-glob/issues/167') - - if (!(this instanceof GlobSync)) - return new GlobSync(pattern, options) - - setopts(this, pattern, options) - - if (this.noprocess) - return this - - var n = this.minimatch.set.length - this.matches = new Array(n) - for (var i = 0; i < n; i ++) { - this._process(this.minimatch.set[i], i, false) - } - this._finish() -} - -GlobSync.prototype._finish = function () { - assert(this instanceof GlobSync) - if (this.realpath) { - var self = this - this.matches.forEach(function (matchset, index) { - var set = self.matches[index] = Object.create(null) - for (var p in matchset) { - try { - p = self._makeAbs(p) - var real = rp.realpathSync(p, self.realpathCache) - set[real] = true - } catch (er) { - if (er.syscall === 'stat') - set[self._makeAbs(p)] = true - else - throw er - } - } - }) - } - common.finish(this) -} - - -GlobSync.prototype._process = function (pattern, index, inGlobStar) { - assert(this instanceof GlobSync) - - // Get the first [n] parts of pattern that are all strings. - var n = 0 - while (typeof pattern[n] === 'string') { - n ++ - } - // now n is the index of the first one that is *not* a string. - - // See if there's anything else - var prefix - switch (n) { - // if not, then this is rather simple - case pattern.length: - this._processSimple(pattern.join('/'), index) - return - - case 0: - // pattern *starts* with some non-trivial item. - // going to readdir(cwd), but not include the prefix in matches. - prefix = null - break - - default: - // pattern has some string bits in the front. - // whatever it starts with, whether that's 'absolute' like /foo/bar, - // or 'relative' like '../baz' - prefix = pattern.slice(0, n).join('/') - break - } - - var remain = pattern.slice(n) - - // get the list of entries. - var read - if (prefix === null) - read = '.' - else if (isAbsolute(prefix) || isAbsolute(pattern.join('/'))) { - if (!prefix || !isAbsolute(prefix)) - prefix = '/' + prefix - read = prefix - } else - read = prefix - - var abs = this._makeAbs(read) - - //if ignored, skip processing - if (childrenIgnored(this, read)) - return - - var isGlobStar = remain[0] === minimatch.GLOBSTAR - if (isGlobStar) - this._processGlobStar(prefix, read, abs, remain, index, inGlobStar) - else - this._processReaddir(prefix, read, abs, remain, index, inGlobStar) -} - - -GlobSync.prototype._processReaddir = function (prefix, read, abs, remain, index, inGlobStar) { - var entries = this._readdir(abs, inGlobStar) - - // if the abs isn't a dir, then nothing can match! - if (!entries) - return - - // It will only match dot entries if it starts with a dot, or if - // dot is set. Stuff like @(.foo|.bar) isn't allowed. - var pn = remain[0] - var negate = !!this.minimatch.negate - var rawGlob = pn._glob - var dotOk = this.dot || rawGlob.charAt(0) === '.' - - var matchedEntries = [] - for (var i = 0; i < entries.length; i++) { - var e = entries[i] - if (e.charAt(0) !== '.' || dotOk) { - var m - if (negate && !prefix) { - m = !e.match(pn) - } else { - m = e.match(pn) - } - if (m) - matchedEntries.push(e) - } - } - - var len = matchedEntries.length - // If there are no matched entries, then nothing matches. - if (len === 0) - return - - // if this is the last remaining pattern bit, then no need for - // an additional stat *unless* the user has specified mark or - // stat explicitly. We know they exist, since readdir returned - // them. - - if (remain.length === 1 && !this.mark && !this.stat) { - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - if (prefix) { - if (prefix.slice(-1) !== '/') - e = prefix + '/' + e - else - e = prefix + e - } - - if (e.charAt(0) === '/' && !this.nomount) { - e = path.join(this.root, e) - } - this._emitMatch(index, e) - } - // This was the last one, and no stats were needed - return - } - - // now test all matched entries as stand-ins for that part - // of the pattern. - remain.shift() - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - var newPattern - if (prefix) - newPattern = [prefix, e] - else - newPattern = [e] - this._process(newPattern.concat(remain), index, inGlobStar) - } -} - - -GlobSync.prototype._emitMatch = function (index, e) { - if (isIgnored(this, e)) - return - - var abs = this._makeAbs(e) - - if (this.mark) - e = this._mark(e) - - if (this.absolute) { - e = abs - } - - if (this.matches[index][e]) - return - - if (this.nodir) { - var c = this.cache[abs] - if (c === 'DIR' || Array.isArray(c)) - return - } - - this.matches[index][e] = true - - if (this.stat) - this._stat(e) -} - - -GlobSync.prototype._readdirInGlobStar = function (abs) { - // follow all symlinked directories forever - // just proceed as if this is a non-globstar situation - if (this.follow) - return this._readdir(abs, false) - - var entries - var lstat - var stat - try { - lstat = fs.lstatSync(abs) - } catch (er) { - if (er.code === 'ENOENT') { - // lstat failed, doesn't exist - return null - } - } - - var isSym = lstat && lstat.isSymbolicLink() - this.symlinks[abs] = isSym - - // If it's not a symlink or a dir, then it's definitely a regular file. - // don't bother doing a readdir in that case. - if (!isSym && lstat && !lstat.isDirectory()) - this.cache[abs] = 'FILE' - else - entries = this._readdir(abs, false) - - return entries -} - -GlobSync.prototype._readdir = function (abs, inGlobStar) { - var entries - - if (inGlobStar && !ownProp(this.symlinks, abs)) - return this._readdirInGlobStar(abs) - - if (ownProp(this.cache, abs)) { - var c = this.cache[abs] - if (!c || c === 'FILE') - return null - - if (Array.isArray(c)) - return c - } - - try { - return this._readdirEntries(abs, fs.readdirSync(abs)) - } catch (er) { - this._readdirError(abs, er) - return null - } -} - -GlobSync.prototype._readdirEntries = function (abs, entries) { - // if we haven't asked to stat everything, then just - // assume that everything in there exists, so we can avoid - // having to stat it a second time. - if (!this.mark && !this.stat) { - for (var i = 0; i < entries.length; i ++) { - var e = entries[i] - if (abs === '/') - e = abs + e - else - e = abs + '/' + e - this.cache[e] = true - } - } - - this.cache[abs] = entries - - // mark and cache dir-ness - return entries -} - -GlobSync.prototype._readdirError = function (f, er) { - // handle errors, and cache the information - switch (er.code) { - case 'ENOTSUP': // https://github.com/isaacs/node-glob/issues/205 - case 'ENOTDIR': // totally normal. means it *does* exist. - var abs = this._makeAbs(f) - this.cache[abs] = 'FILE' - if (abs === this.cwdAbs) { - var error = new Error(er.code + ' invalid cwd ' + this.cwd) - error.path = this.cwd - error.code = er.code - throw error - } - break - - case 'ENOENT': // not terribly unusual - case 'ELOOP': - case 'ENAMETOOLONG': - case 'UNKNOWN': - this.cache[this._makeAbs(f)] = false - break - - default: // some unusual error. Treat as failure. - this.cache[this._makeAbs(f)] = false - if (this.strict) - throw er - if (!this.silent) - console.error('glob error', er) - break - } -} - -GlobSync.prototype._processGlobStar = function (prefix, read, abs, remain, index, inGlobStar) { - - var entries = this._readdir(abs, inGlobStar) - - // no entries means not a dir, so it can never have matches - // foo.txt/** doesn't match foo.txt - if (!entries) - return - - // test without the globstar, and with every child both below - // and replacing the globstar. - var remainWithoutGlobStar = remain.slice(1) - var gspref = prefix ? [ prefix ] : [] - var noGlobStar = gspref.concat(remainWithoutGlobStar) - - // the noGlobStar pattern exits the inGlobStar state - this._process(noGlobStar, index, false) - - var len = entries.length - var isSym = this.symlinks[abs] - - // If it's a symlink, and we're in a globstar, then stop - if (isSym && inGlobStar) - return - - for (var i = 0; i < len; i++) { - var e = entries[i] - if (e.charAt(0) === '.' && !this.dot) - continue - - // these two cases enter the inGlobStar state - var instead = gspref.concat(entries[i], remainWithoutGlobStar) - this._process(instead, index, true) - - var below = gspref.concat(entries[i], remain) - this._process(below, index, true) - } -} - -GlobSync.prototype._processSimple = function (prefix, index) { - // XXX review this. Shouldn't it be doing the mounting etc - // before doing stat? kinda weird? - var exists = this._stat(prefix) - - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - // If it doesn't exist, then just mark the lack of results - if (!exists) - return - - if (prefix && isAbsolute(prefix) && !this.nomount) { - var trail = /[\/\\]$/.test(prefix) - if (prefix.charAt(0) === '/') { - prefix = path.join(this.root, prefix) - } else { - prefix = path.resolve(this.root, prefix) - if (trail) - prefix += '/' - } - } - - if (process.platform === 'win32') - prefix = prefix.replace(/\\/g, '/') - - // Mark this as a match - this._emitMatch(index, prefix) -} - -// Returns either 'DIR', 'FILE', or false -GlobSync.prototype._stat = function (f) { - var abs = this._makeAbs(f) - var needDir = f.slice(-1) === '/' - - if (f.length > this.maxLength) - return false - - if (!this.stat && ownProp(this.cache, abs)) { - var c = this.cache[abs] - - if (Array.isArray(c)) - c = 'DIR' - - // It exists, but maybe not how we need it - if (!needDir || c === 'DIR') - return c - - if (needDir && c === 'FILE') - return false - - // otherwise we have to stat, because maybe c=true - // if we know it exists, but not what it is. - } - - var exists - var stat = this.statCache[abs] - if (!stat) { - var lstat - try { - lstat = fs.lstatSync(abs) - } catch (er) { - if (er && (er.code === 'ENOENT' || er.code === 'ENOTDIR')) { - this.statCache[abs] = false - return false - } - } - - if (lstat && lstat.isSymbolicLink()) { - try { - stat = fs.statSync(abs) - } catch (er) { - stat = lstat - } - } else { - stat = lstat - } - } - - this.statCache[abs] = stat - - var c = true - if (stat) - c = stat.isDirectory() ? 'DIR' : 'FILE' - - this.cache[abs] = this.cache[abs] || c - - if (needDir && c === 'FILE') - return false - - return c -} - -GlobSync.prototype._mark = function (p) { - return common.mark(this, p) -} - -GlobSync.prototype._makeAbs = function (f) { - return common.makeAbs(this, f) -} - - -/***/ }), -/* 219 */, -/* 220 */, -/* 221 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = function (flag, argv) { - argv = argv || process.argv; - - var terminatorPos = argv.indexOf('--'); - var prefix = /^--/.test(flag) ? '' : '--'; - var pos = argv.indexOf(prefix + flag); - - return pos !== -1 && (terminatorPos !== -1 ? pos < terminatorPos : true); -}; - - -/***/ }), -/* 222 */, -/* 223 */ -/***/ (function(module, exports, __webpack_require__) { - -var wrappy = __webpack_require__(123) -var reqs = Object.create(null) -var once = __webpack_require__(61) - -module.exports = wrappy(inflight) - -function inflight (key, cb) { - if (reqs[key]) { - reqs[key].push(cb) - return null - } else { - reqs[key] = [cb] - return makeres(key) - } -} - -function makeres (key) { - return once(function RES () { - var cbs = reqs[key] - var len = cbs.length - var args = slice(arguments) - - // XXX It's somewhat ambiguous whether a new callback added in this - // pass should be queued for later execution if something in the - // list of callbacks throws, or if it should just be discarded. - // However, it's such an edge case that it hardly matters, and either - // choice is likely as surprising as the other. - // As it happens, we do go ahead and schedule it for later execution. - try { - for (var i = 0; i < len; i++) { - cbs[i].apply(null, args) - } - } finally { - if (cbs.length > len) { - // added more in the interim. - // de-zalgo, just in case, but don't call again. - cbs.splice(0, len) - process.nextTick(function () { - RES.apply(null, args) - }) - } else { - delete reqs[key] - } - } - }) -} - -function slice (args) { - var length = args.length - var array = [] - - for (var i = 0; i < length; i++) array[i] = args[i] - return array -} - - -/***/ }), -/* 224 */ -/***/ (function(module, exports) { - -if (typeof Object.create === 'function') { - // implementation from standard node.js 'util' module - module.exports = function inherits(ctor, superCtor) { - ctor.super_ = superCtor - ctor.prototype = Object.create(superCtor.prototype, { - constructor: { - value: ctor, - enumerable: false, - writable: true, - configurable: true - } - }); - }; -} else { - // old school shim for old browsers - module.exports = function inherits(ctor, superCtor) { - ctor.super_ = superCtor - var TempCtor = function () {} - TempCtor.prototype = superCtor.prototype - ctor.prototype = new TempCtor() - ctor.prototype.constructor = ctor - } -} - - -/***/ }), -/* 225 */, -/* 226 */, -/* 227 */ -/***/ (function(module, exports, __webpack_require__) { - -// @flow - -/*:: -declare var __webpack_require__: mixed; -*/ - -module.exports = typeof __webpack_require__ !== "undefined"; - - -/***/ }), -/* 228 */, -/* 229 */ -/***/ (function(module, exports) { - -/** - * Helpers. - */ - -var s = 1000; -var m = s * 60; -var h = m * 60; -var d = h * 24; -var y = d * 365.25; - -/** - * Parse or format the given `val`. - * - * Options: - * - * - `long` verbose formatting [false] - * - * @param {String|Number} val - * @param {Object} [options] - * @throws {Error} throw an error if val is not a non-empty string or a number - * @return {String|Number} - * @api public - */ - -module.exports = function(val, options) { - options = options || {}; - var type = typeof val; - if (type === 'string' && val.length > 0) { - return parse(val); - } else if (type === 'number' && isNaN(val) === false) { - return options.long ? fmtLong(val) : fmtShort(val); - } - throw new Error( - 'val is not a non-empty string or a valid number. val=' + - JSON.stringify(val) - ); -}; - -/** - * Parse the given `str` and return milliseconds. - * - * @param {String} str - * @return {Number} - * @api private - */ - -function parse(str) { - str = String(str); - if (str.length > 100) { - return; - } - var match = /^((?:\d+)?\.?\d+) *(milliseconds?|msecs?|ms|seconds?|secs?|s|minutes?|mins?|m|hours?|hrs?|h|days?|d|years?|yrs?|y)?$/i.exec( - str - ); - if (!match) { - return; - } - var n = parseFloat(match[1]); - var type = (match[2] || 'ms').toLowerCase(); - switch (type) { - case 'years': - case 'year': - case 'yrs': - case 'yr': - case 'y': - return n * y; - case 'days': - case 'day': - case 'd': - return n * d; - case 'hours': - case 'hour': - case 'hrs': - case 'hr': - case 'h': - return n * h; - case 'minutes': - case 'minute': - case 'mins': - case 'min': - case 'm': - return n * m; - case 'seconds': - case 'second': - case 'secs': - case 'sec': - case 's': - return n * s; - case 'milliseconds': - case 'millisecond': - case 'msecs': - case 'msec': - case 'ms': - return n; - default: - return undefined; - } -} - -/** - * Short format for `ms`. - * - * @param {Number} ms - * @return {String} - * @api private - */ - -function fmtShort(ms) { - if (ms >= d) { - return Math.round(ms / d) + 'd'; - } - if (ms >= h) { - return Math.round(ms / h) + 'h'; - } - if (ms >= m) { - return Math.round(ms / m) + 'm'; - } - if (ms >= s) { - return Math.round(ms / s) + 's'; - } - return ms + 'ms'; -} - -/** - * Long format for `ms`. - * - * @param {Number} ms - * @return {String} - * @api private - */ - -function fmtLong(ms) { - return plural(ms, d, 'day') || - plural(ms, h, 'hour') || - plural(ms, m, 'minute') || - plural(ms, s, 'second') || - ms + ' ms'; -} - -/** - * Pluralization helper. - */ - -function plural(ms, n, name) { - if (ms < n) { - return; - } - if (ms < n * 1.5) { - return Math.floor(ms / n) + ' ' + name; - } - return Math.ceil(ms / n) + ' ' + name + 's'; -} - - -/***/ }), -/* 230 */, -/* 231 */, -/* 232 */, -/* 233 */ -/***/ (function(module, exports, __webpack_require__) { - -module.exports = rimraf -rimraf.sync = rimrafSync - -var assert = __webpack_require__(22) -var path = __webpack_require__(0) -var fs = __webpack_require__(3) -var glob = __webpack_require__(75) -var _0666 = parseInt('666', 8) - -var defaultGlobOpts = { - nosort: true, - silent: true -} - -// for EMFILE handling -var timeout = 0 - -var isWindows = (process.platform === "win32") - -function defaults (options) { - var methods = [ - 'unlink', - 'chmod', - 'stat', - 'lstat', - 'rmdir', - 'readdir' - ] - methods.forEach(function(m) { - options[m] = options[m] || fs[m] - m = m + 'Sync' - options[m] = options[m] || fs[m] - }) - - options.maxBusyTries = options.maxBusyTries || 3 - options.emfileWait = options.emfileWait || 1000 - if (options.glob === false) { - options.disableGlob = true - } - options.disableGlob = options.disableGlob || false - options.glob = options.glob || defaultGlobOpts -} - -function rimraf (p, options, cb) { - if (typeof options === 'function') { - cb = options - options = {} - } - - assert(p, 'rimraf: missing path') - assert.equal(typeof p, 'string', 'rimraf: path should be a string') - assert.equal(typeof cb, 'function', 'rimraf: callback function required') - assert(options, 'rimraf: invalid options argument provided') - assert.equal(typeof options, 'object', 'rimraf: options should be object') - - defaults(options) - - var busyTries = 0 - var errState = null - var n = 0 - - if (options.disableGlob || !glob.hasMagic(p)) - return afterGlob(null, [p]) - - options.lstat(p, function (er, stat) { - if (!er) - return afterGlob(null, [p]) - - glob(p, options.glob, afterGlob) - }) - - function next (er) { - errState = errState || er - if (--n === 0) - cb(errState) - } - - function afterGlob (er, results) { - if (er) - return cb(er) - - n = results.length - if (n === 0) - return cb() - - results.forEach(function (p) { - rimraf_(p, options, function CB (er) { - if (er) { - if ((er.code === "EBUSY" || er.code === "ENOTEMPTY" || er.code === "EPERM") && - busyTries < options.maxBusyTries) { - busyTries ++ - var time = busyTries * 100 - // try again, with the same exact callback as this one. - return setTimeout(function () { - rimraf_(p, options, CB) - }, time) - } - - // this one won't happen if graceful-fs is used. - if (er.code === "EMFILE" && timeout < options.emfileWait) { - return setTimeout(function () { - rimraf_(p, options, CB) - }, timeout ++) - } - - // already gone - if (er.code === "ENOENT") er = null - } - - timeout = 0 - next(er) - }) - }) - } -} - -// Two possible strategies. -// 1. Assume it's a file. unlink it, then do the dir stuff on EPERM or EISDIR -// 2. Assume it's a directory. readdir, then do the file stuff on ENOTDIR -// -// Both result in an extra syscall when you guess wrong. However, there -// are likely far more normal files in the world than directories. This -// is based on the assumption that a the average number of files per -// directory is >= 1. -// -// If anyone ever complains about this, then I guess the strategy could -// be made configurable somehow. But until then, YAGNI. -function rimraf_ (p, options, cb) { - assert(p) - assert(options) - assert(typeof cb === 'function') - - // sunos lets the root user unlink directories, which is... weird. - // so we have to lstat here and make sure it's not a dir. - options.lstat(p, function (er, st) { - if (er && er.code === "ENOENT") - return cb(null) - - // Windows can EPERM on stat. Life is suffering. - if (er && er.code === "EPERM" && isWindows) - fixWinEPERM(p, options, er, cb) - - if (st && st.isDirectory()) - return rmdir(p, options, er, cb) - - options.unlink(p, function (er) { - if (er) { - if (er.code === "ENOENT") - return cb(null) - if (er.code === "EPERM") - return (isWindows) - ? fixWinEPERM(p, options, er, cb) - : rmdir(p, options, er, cb) - if (er.code === "EISDIR") - return rmdir(p, options, er, cb) - } - return cb(er) - }) - }) -} - -function fixWinEPERM (p, options, er, cb) { - assert(p) - assert(options) - assert(typeof cb === 'function') - if (er) - assert(er instanceof Error) - - options.chmod(p, _0666, function (er2) { - if (er2) - cb(er2.code === "ENOENT" ? null : er) - else - options.stat(p, function(er3, stats) { - if (er3) - cb(er3.code === "ENOENT" ? null : er) - else if (stats.isDirectory()) - rmdir(p, options, er, cb) - else - options.unlink(p, cb) - }) - }) -} - -function fixWinEPERMSync (p, options, er) { - assert(p) - assert(options) - if (er) - assert(er instanceof Error) - - try { - options.chmodSync(p, _0666) - } catch (er2) { - if (er2.code === "ENOENT") - return - else - throw er - } - - try { - var stats = options.statSync(p) - } catch (er3) { - if (er3.code === "ENOENT") - return - else - throw er - } - - if (stats.isDirectory()) - rmdirSync(p, options, er) - else - options.unlinkSync(p) -} - -function rmdir (p, options, originalEr, cb) { - assert(p) - assert(options) - if (originalEr) - assert(originalEr instanceof Error) - assert(typeof cb === 'function') - - // try to rmdir first, and only readdir on ENOTEMPTY or EEXIST (SunOS) - // if we guessed wrong, and it's not a directory, then - // raise the original error. - options.rmdir(p, function (er) { - if (er && (er.code === "ENOTEMPTY" || er.code === "EEXIST" || er.code === "EPERM")) - rmkids(p, options, cb) - else if (er && er.code === "ENOTDIR") - cb(originalEr) - else - cb(er) - }) -} - -function rmkids(p, options, cb) { - assert(p) - assert(options) - assert(typeof cb === 'function') - - options.readdir(p, function (er, files) { - if (er) - return cb(er) - var n = files.length - if (n === 0) - return options.rmdir(p, cb) - var errState - files.forEach(function (f) { - rimraf(path.join(p, f), options, function (er) { - if (errState) - return - if (er) - return cb(errState = er) - if (--n === 0) - options.rmdir(p, cb) - }) - }) - }) -} - -// this looks simpler, and is strictly *faster*, but will -// tie up the JavaScript thread and fail on excessively -// deep directory trees. -function rimrafSync (p, options) { - options = options || {} - defaults(options) - - assert(p, 'rimraf: missing path') - assert.equal(typeof p, 'string', 'rimraf: path should be a string') - assert(options, 'rimraf: missing options') - assert.equal(typeof options, 'object', 'rimraf: options should be object') - - var results - - if (options.disableGlob || !glob.hasMagic(p)) { - results = [p] - } else { - try { - options.lstatSync(p) - results = [p] - } catch (er) { - results = glob.sync(p, options.glob) - } - } - - if (!results.length) - return - - for (var i = 0; i < results.length; i++) { - var p = results[i] - - try { - var st = options.lstatSync(p) - } catch (er) { - if (er.code === "ENOENT") - return - - // Windows can EPERM on stat. Life is suffering. - if (er.code === "EPERM" && isWindows) - fixWinEPERMSync(p, options, er) - } - - try { - // sunos lets the root user unlink directories, which is... weird. - if (st && st.isDirectory()) - rmdirSync(p, options, null) - else - options.unlinkSync(p) - } catch (er) { - if (er.code === "ENOENT") - return - if (er.code === "EPERM") - return isWindows ? fixWinEPERMSync(p, options, er) : rmdirSync(p, options, er) - if (er.code !== "EISDIR") - throw er - - rmdirSync(p, options, er) - } - } -} - -function rmdirSync (p, options, originalEr) { - assert(p) - assert(options) - if (originalEr) - assert(originalEr instanceof Error) - - try { - options.rmdirSync(p) - } catch (er) { - if (er.code === "ENOENT") - return - if (er.code === "ENOTDIR") - throw originalEr - if (er.code === "ENOTEMPTY" || er.code === "EEXIST" || er.code === "EPERM") - rmkidsSync(p, options) - } -} - -function rmkidsSync (p, options) { - assert(p) - assert(options) - options.readdirSync(p).forEach(function (f) { - rimrafSync(path.join(p, f), options) - }) - - // We only end up here once we got ENOTEMPTY at least once, and - // at this point, we are guaranteed to have removed all the kids. - // So, we know that it won't be ENOENT or ENOTDIR or anything else. - // try really hard to delete stuff on windows, because it has a - // PROFOUNDLY annoying habit of not closing handles promptly when - // files are deleted, resulting in spurious ENOTEMPTY errors. - var retries = isWindows ? 100 : 1 - var i = 0 - do { - var threw = true - try { - var ret = options.rmdirSync(p, options) - threw = false - return ret - } finally { - if (++i < retries && threw) - continue - } - } while (true) -} - - -/***/ }), -/* 234 */, -/* 235 */, -/* 236 */, -/* 237 */, -/* 238 */, -/* 239 */ -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var hasFlag = __webpack_require__(221); - -var support = function (level) { - if (level === 0) { - return false; - } - - return { - level: level, - hasBasic: true, - has256: level >= 2, - has16m: level >= 3 - }; -}; - -var supportLevel = (function () { - if (hasFlag('no-color') || - hasFlag('no-colors') || - hasFlag('color=false')) { - return 0; - } - - if (hasFlag('color=16m') || - hasFlag('color=full') || - hasFlag('color=truecolor')) { - return 3; - } - - if (hasFlag('color=256')) { - return 2; - } - - if (hasFlag('color') || - hasFlag('colors') || - hasFlag('color=true') || - hasFlag('color=always')) { - return 1; - } - - if (process.stdout && !process.stdout.isTTY) { - return 0; - } - - if (process.platform === 'win32') { - return 1; - } - - if ('CI' in process.env) { - if ('TRAVIS' in process.env || process.env.CI === 'Travis') { - return 1; - } - - return 0; - } - - if ('TEAMCITY_VERSION' in process.env) { - return process.env.TEAMCITY_VERSION.match(/^(9\.(0*[1-9]\d*)\.|\d{2,}\.)/) === null ? 0 : 1; - } - - if (/^(screen|xterm)-256(?:color)?/.test(process.env.TERM)) { - return 2; - } - - if (/^screen|^xterm|^vt100|color|ansi|cygwin|linux/i.test(process.env.TERM)) { - return 1; - } - - if ('COLORTERM' in process.env) { - return 1; - } - - if (process.env.TERM === 'dumb') { - return 0; - } - - return 0; -})(); - -if (supportLevel === 0 && 'FORCE_COLOR' in process.env) { - supportLevel = 1; -} - -module.exports = process && support(supportLevel); - - -/***/ }) -/******/ ]); - -/***/ }), - -/***/ "../../node_modules/ansi-regex/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = ({onlyFirst = false} = {}) => { - const pattern = [ - '[\\u001B\\u009B][[\\]()#;?]*(?:(?:(?:(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]+)*|[a-zA-Z\\d]+(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]*)*)?\\u0007)', - '(?:(?:\\d{1,4}(?:;\\d{0,4})*)?[\\dA-PR-TZcf-ntqry=><~]))' - ].join('|'); - - return new RegExp(pattern, onlyFirst ? undefined : 'g'); -}; - - -/***/ }), - -/***/ "../../node_modules/ansi-styles/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/* WEBPACK VAR INJECTION */(function(module) { - -const wrapAnsi16 = (fn, offset) => (...args) => { - const code = fn(...args); - return `\u001B[${code + offset}m`; -}; - -const wrapAnsi256 = (fn, offset) => (...args) => { - const code = fn(...args); - return `\u001B[${38 + offset};5;${code}m`; -}; - -const wrapAnsi16m = (fn, offset) => (...args) => { - const rgb = fn(...args); - return `\u001B[${38 + offset};2;${rgb[0]};${rgb[1]};${rgb[2]}m`; -}; - -const ansi2ansi = n => n; -const rgb2rgb = (r, g, b) => [r, g, b]; - -const setLazyProperty = (object, property, get) => { - Object.defineProperty(object, property, { - get: () => { - const value = get(); - - Object.defineProperty(object, property, { - value, - enumerable: true, - configurable: true - }); - - return value; - }, - enumerable: true, - configurable: true - }); -}; - -/** @type {typeof import('color-convert')} */ -let colorConvert; -const makeDynamicStyles = (wrap, targetSpace, identity, isBackground) => { - if (colorConvert === undefined) { - colorConvert = __webpack_require__("../../node_modules/ansi-styles/node_modules/color-convert/index.js"); - } - - const offset = isBackground ? 10 : 0; - const styles = {}; - - for (const [sourceSpace, suite] of Object.entries(colorConvert)) { - const name = sourceSpace === 'ansi16' ? 'ansi' : sourceSpace; - if (sourceSpace === targetSpace) { - styles[name] = wrap(identity, offset); - } else if (typeof suite === 'object') { - styles[name] = wrap(suite[targetSpace], offset); - } - } - - return styles; -}; - -function assembleStyles() { - const codes = new Map(); - const styles = { - modifier: { - reset: [0, 0], - // 21 isn't widely supported and 22 does the same thing - bold: [1, 22], - dim: [2, 22], - italic: [3, 23], - underline: [4, 24], - inverse: [7, 27], - hidden: [8, 28], - strikethrough: [9, 29] - }, - color: { - black: [30, 39], - red: [31, 39], - green: [32, 39], - yellow: [33, 39], - blue: [34, 39], - magenta: [35, 39], - cyan: [36, 39], - white: [37, 39], - - // Bright color - blackBright: [90, 39], - redBright: [91, 39], - greenBright: [92, 39], - yellowBright: [93, 39], - blueBright: [94, 39], - magentaBright: [95, 39], - cyanBright: [96, 39], - whiteBright: [97, 39] - }, - bgColor: { - bgBlack: [40, 49], - bgRed: [41, 49], - bgGreen: [42, 49], - bgYellow: [43, 49], - bgBlue: [44, 49], - bgMagenta: [45, 49], - bgCyan: [46, 49], - bgWhite: [47, 49], - - // Bright color - bgBlackBright: [100, 49], - bgRedBright: [101, 49], - bgGreenBright: [102, 49], - bgYellowBright: [103, 49], - bgBlueBright: [104, 49], - bgMagentaBright: [105, 49], - bgCyanBright: [106, 49], - bgWhiteBright: [107, 49] - } - }; - - // Alias bright black as gray (and grey) - styles.color.gray = styles.color.blackBright; - styles.bgColor.bgGray = styles.bgColor.bgBlackBright; - styles.color.grey = styles.color.blackBright; - styles.bgColor.bgGrey = styles.bgColor.bgBlackBright; - - for (const [groupName, group] of Object.entries(styles)) { - for (const [styleName, style] of Object.entries(group)) { - styles[styleName] = { - open: `\u001B[${style[0]}m`, - close: `\u001B[${style[1]}m` - }; - - group[styleName] = styles[styleName]; - - codes.set(style[0], style[1]); - } - - Object.defineProperty(styles, groupName, { - value: group, - enumerable: false - }); - } - - Object.defineProperty(styles, 'codes', { - value: codes, - enumerable: false - }); - - styles.color.close = '\u001B[39m'; - styles.bgColor.close = '\u001B[49m'; - - setLazyProperty(styles.color, 'ansi', () => makeDynamicStyles(wrapAnsi16, 'ansi16', ansi2ansi, false)); - setLazyProperty(styles.color, 'ansi256', () => makeDynamicStyles(wrapAnsi256, 'ansi256', ansi2ansi, false)); - setLazyProperty(styles.color, 'ansi16m', () => makeDynamicStyles(wrapAnsi16m, 'rgb', rgb2rgb, false)); - setLazyProperty(styles.bgColor, 'ansi', () => makeDynamicStyles(wrapAnsi16, 'ansi16', ansi2ansi, true)); - setLazyProperty(styles.bgColor, 'ansi256', () => makeDynamicStyles(wrapAnsi256, 'ansi256', ansi2ansi, true)); - setLazyProperty(styles.bgColor, 'ansi16m', () => makeDynamicStyles(wrapAnsi16m, 'rgb', rgb2rgb, true)); - - return styles; -} - -// Make the export immutable -Object.defineProperty(module, 'exports', { - enumerable: true, - get: assembleStyles -}); - -/* WEBPACK VAR INJECTION */}.call(this, __webpack_require__("../../node_modules/webpack/buildin/module.js")(module))) - -/***/ }), - -/***/ "../../node_modules/ansi-styles/node_modules/color-convert/conversions.js": -/***/ (function(module, exports, __webpack_require__) { - -/* MIT license */ -/* eslint-disable no-mixed-operators */ -const cssKeywords = __webpack_require__("../../node_modules/color-name/index.js"); - -// NOTE: conversions should only return primitive values (i.e. arrays, or -// values that give correct `typeof` results). -// do not use box values types (i.e. Number(), String(), etc.) - -const reverseKeywords = {}; -for (const key of Object.keys(cssKeywords)) { - reverseKeywords[cssKeywords[key]] = key; -} - -const convert = { - rgb: {channels: 3, labels: 'rgb'}, - hsl: {channels: 3, labels: 'hsl'}, - hsv: {channels: 3, labels: 'hsv'}, - hwb: {channels: 3, labels: 'hwb'}, - cmyk: {channels: 4, labels: 'cmyk'}, - xyz: {channels: 3, labels: 'xyz'}, - lab: {channels: 3, labels: 'lab'}, - lch: {channels: 3, labels: 'lch'}, - hex: {channels: 1, labels: ['hex']}, - keyword: {channels: 1, labels: ['keyword']}, - ansi16: {channels: 1, labels: ['ansi16']}, - ansi256: {channels: 1, labels: ['ansi256']}, - hcg: {channels: 3, labels: ['h', 'c', 'g']}, - apple: {channels: 3, labels: ['r16', 'g16', 'b16']}, - gray: {channels: 1, labels: ['gray']} -}; - -module.exports = convert; - -// Hide .channels and .labels properties -for (const model of Object.keys(convert)) { - if (!('channels' in convert[model])) { - throw new Error('missing channels property: ' + model); - } - - if (!('labels' in convert[model])) { - throw new Error('missing channel labels property: ' + model); - } - - if (convert[model].labels.length !== convert[model].channels) { - throw new Error('channel and label counts mismatch: ' + model); - } - - const {channels, labels} = convert[model]; - delete convert[model].channels; - delete convert[model].labels; - Object.defineProperty(convert[model], 'channels', {value: channels}); - Object.defineProperty(convert[model], 'labels', {value: labels}); -} - -convert.rgb.hsl = function (rgb) { - const r = rgb[0] / 255; - const g = rgb[1] / 255; - const b = rgb[2] / 255; - const min = Math.min(r, g, b); - const max = Math.max(r, g, b); - const delta = max - min; - let h; - let s; - - if (max === min) { - h = 0; - } else if (r === max) { - h = (g - b) / delta; - } else if (g === max) { - h = 2 + (b - r) / delta; - } else if (b === max) { - h = 4 + (r - g) / delta; - } - - h = Math.min(h * 60, 360); - - if (h < 0) { - h += 360; - } - - const l = (min + max) / 2; - - if (max === min) { - s = 0; - } else if (l <= 0.5) { - s = delta / (max + min); - } else { - s = delta / (2 - max - min); - } - - return [h, s * 100, l * 100]; -}; - -convert.rgb.hsv = function (rgb) { - let rdif; - let gdif; - let bdif; - let h; - let s; - - const r = rgb[0] / 255; - const g = rgb[1] / 255; - const b = rgb[2] / 255; - const v = Math.max(r, g, b); - const diff = v - Math.min(r, g, b); - const diffc = function (c) { - return (v - c) / 6 / diff + 1 / 2; - }; - - if (diff === 0) { - h = 0; - s = 0; - } else { - s = diff / v; - rdif = diffc(r); - gdif = diffc(g); - bdif = diffc(b); - - if (r === v) { - h = bdif - gdif; - } else if (g === v) { - h = (1 / 3) + rdif - bdif; - } else if (b === v) { - h = (2 / 3) + gdif - rdif; - } - - if (h < 0) { - h += 1; - } else if (h > 1) { - h -= 1; - } - } - - return [ - h * 360, - s * 100, - v * 100 - ]; -}; - -convert.rgb.hwb = function (rgb) { - const r = rgb[0]; - const g = rgb[1]; - let b = rgb[2]; - const h = convert.rgb.hsl(rgb)[0]; - const w = 1 / 255 * Math.min(r, Math.min(g, b)); - - b = 1 - 1 / 255 * Math.max(r, Math.max(g, b)); - - return [h, w * 100, b * 100]; -}; - -convert.rgb.cmyk = function (rgb) { - const r = rgb[0] / 255; - const g = rgb[1] / 255; - const b = rgb[2] / 255; - - const k = Math.min(1 - r, 1 - g, 1 - b); - const c = (1 - r - k) / (1 - k) || 0; - const m = (1 - g - k) / (1 - k) || 0; - const y = (1 - b - k) / (1 - k) || 0; - - return [c * 100, m * 100, y * 100, k * 100]; -}; - -function comparativeDistance(x, y) { - /* - See https://en.m.wikipedia.org/wiki/Euclidean_distance#Squared_Euclidean_distance - */ - return ( - ((x[0] - y[0]) ** 2) + - ((x[1] - y[1]) ** 2) + - ((x[2] - y[2]) ** 2) - ); -} - -convert.rgb.keyword = function (rgb) { - const reversed = reverseKeywords[rgb]; - if (reversed) { - return reversed; - } - - let currentClosestDistance = Infinity; - let currentClosestKeyword; - - for (const keyword of Object.keys(cssKeywords)) { - const value = cssKeywords[keyword]; - - // Compute comparative distance - const distance = comparativeDistance(rgb, value); - - // Check if its less, if so set as closest - if (distance < currentClosestDistance) { - currentClosestDistance = distance; - currentClosestKeyword = keyword; - } - } - - return currentClosestKeyword; -}; - -convert.keyword.rgb = function (keyword) { - return cssKeywords[keyword]; -}; - -convert.rgb.xyz = function (rgb) { - let r = rgb[0] / 255; - let g = rgb[1] / 255; - let b = rgb[2] / 255; - - // Assume sRGB - r = r > 0.04045 ? (((r + 0.055) / 1.055) ** 2.4) : (r / 12.92); - g = g > 0.04045 ? (((g + 0.055) / 1.055) ** 2.4) : (g / 12.92); - b = b > 0.04045 ? (((b + 0.055) / 1.055) ** 2.4) : (b / 12.92); - - const x = (r * 0.4124) + (g * 0.3576) + (b * 0.1805); - const y = (r * 0.2126) + (g * 0.7152) + (b * 0.0722); - const z = (r * 0.0193) + (g * 0.1192) + (b * 0.9505); - - return [x * 100, y * 100, z * 100]; -}; - -convert.rgb.lab = function (rgb) { - const xyz = convert.rgb.xyz(rgb); - let x = xyz[0]; - let y = xyz[1]; - let z = xyz[2]; - - x /= 95.047; - y /= 100; - z /= 108.883; - - x = x > 0.008856 ? (x ** (1 / 3)) : (7.787 * x) + (16 / 116); - y = y > 0.008856 ? (y ** (1 / 3)) : (7.787 * y) + (16 / 116); - z = z > 0.008856 ? (z ** (1 / 3)) : (7.787 * z) + (16 / 116); - - const l = (116 * y) - 16; - const a = 500 * (x - y); - const b = 200 * (y - z); - - return [l, a, b]; -}; - -convert.hsl.rgb = function (hsl) { - const h = hsl[0] / 360; - const s = hsl[1] / 100; - const l = hsl[2] / 100; - let t2; - let t3; - let val; - - if (s === 0) { - val = l * 255; - return [val, val, val]; - } - - if (l < 0.5) { - t2 = l * (1 + s); - } else { - t2 = l + s - l * s; - } - - const t1 = 2 * l - t2; - - const rgb = [0, 0, 0]; - for (let i = 0; i < 3; i++) { - t3 = h + 1 / 3 * -(i - 1); - if (t3 < 0) { - t3++; - } - - if (t3 > 1) { - t3--; - } - - if (6 * t3 < 1) { - val = t1 + (t2 - t1) * 6 * t3; - } else if (2 * t3 < 1) { - val = t2; - } else if (3 * t3 < 2) { - val = t1 + (t2 - t1) * (2 / 3 - t3) * 6; - } else { - val = t1; - } - - rgb[i] = val * 255; - } - - return rgb; -}; - -convert.hsl.hsv = function (hsl) { - const h = hsl[0]; - let s = hsl[1] / 100; - let l = hsl[2] / 100; - let smin = s; - const lmin = Math.max(l, 0.01); - - l *= 2; - s *= (l <= 1) ? l : 2 - l; - smin *= lmin <= 1 ? lmin : 2 - lmin; - const v = (l + s) / 2; - const sv = l === 0 ? (2 * smin) / (lmin + smin) : (2 * s) / (l + s); - - return [h, sv * 100, v * 100]; -}; - -convert.hsv.rgb = function (hsv) { - const h = hsv[0] / 60; - const s = hsv[1] / 100; - let v = hsv[2] / 100; - const hi = Math.floor(h) % 6; - - const f = h - Math.floor(h); - const p = 255 * v * (1 - s); - const q = 255 * v * (1 - (s * f)); - const t = 255 * v * (1 - (s * (1 - f))); - v *= 255; - - switch (hi) { - case 0: - return [v, t, p]; - case 1: - return [q, v, p]; - case 2: - return [p, v, t]; - case 3: - return [p, q, v]; - case 4: - return [t, p, v]; - case 5: - return [v, p, q]; - } -}; - -convert.hsv.hsl = function (hsv) { - const h = hsv[0]; - const s = hsv[1] / 100; - const v = hsv[2] / 100; - const vmin = Math.max(v, 0.01); - let sl; - let l; - - l = (2 - s) * v; - const lmin = (2 - s) * vmin; - sl = s * vmin; - sl /= (lmin <= 1) ? lmin : 2 - lmin; - sl = sl || 0; - l /= 2; - - return [h, sl * 100, l * 100]; -}; - -// http://dev.w3.org/csswg/css-color/#hwb-to-rgb -convert.hwb.rgb = function (hwb) { - const h = hwb[0] / 360; - let wh = hwb[1] / 100; - let bl = hwb[2] / 100; - const ratio = wh + bl; - let f; - - // Wh + bl cant be > 1 - if (ratio > 1) { - wh /= ratio; - bl /= ratio; - } - - const i = Math.floor(6 * h); - const v = 1 - bl; - f = 6 * h - i; - - if ((i & 0x01) !== 0) { - f = 1 - f; - } - - const n = wh + f * (v - wh); // Linear interpolation - - let r; - let g; - let b; - /* eslint-disable max-statements-per-line,no-multi-spaces */ - switch (i) { - default: - case 6: - case 0: r = v; g = n; b = wh; break; - case 1: r = n; g = v; b = wh; break; - case 2: r = wh; g = v; b = n; break; - case 3: r = wh; g = n; b = v; break; - case 4: r = n; g = wh; b = v; break; - case 5: r = v; g = wh; b = n; break; - } - /* eslint-enable max-statements-per-line,no-multi-spaces */ - - return [r * 255, g * 255, b * 255]; -}; - -convert.cmyk.rgb = function (cmyk) { - const c = cmyk[0] / 100; - const m = cmyk[1] / 100; - const y = cmyk[2] / 100; - const k = cmyk[3] / 100; - - const r = 1 - Math.min(1, c * (1 - k) + k); - const g = 1 - Math.min(1, m * (1 - k) + k); - const b = 1 - Math.min(1, y * (1 - k) + k); - - return [r * 255, g * 255, b * 255]; -}; - -convert.xyz.rgb = function (xyz) { - const x = xyz[0] / 100; - const y = xyz[1] / 100; - const z = xyz[2] / 100; - let r; - let g; - let b; - - r = (x * 3.2406) + (y * -1.5372) + (z * -0.4986); - g = (x * -0.9689) + (y * 1.8758) + (z * 0.0415); - b = (x * 0.0557) + (y * -0.2040) + (z * 1.0570); - - // Assume sRGB - r = r > 0.0031308 - ? ((1.055 * (r ** (1.0 / 2.4))) - 0.055) - : r * 12.92; - - g = g > 0.0031308 - ? ((1.055 * (g ** (1.0 / 2.4))) - 0.055) - : g * 12.92; - - b = b > 0.0031308 - ? ((1.055 * (b ** (1.0 / 2.4))) - 0.055) - : b * 12.92; - - r = Math.min(Math.max(0, r), 1); - g = Math.min(Math.max(0, g), 1); - b = Math.min(Math.max(0, b), 1); - - return [r * 255, g * 255, b * 255]; -}; - -convert.xyz.lab = function (xyz) { - let x = xyz[0]; - let y = xyz[1]; - let z = xyz[2]; - - x /= 95.047; - y /= 100; - z /= 108.883; - - x = x > 0.008856 ? (x ** (1 / 3)) : (7.787 * x) + (16 / 116); - y = y > 0.008856 ? (y ** (1 / 3)) : (7.787 * y) + (16 / 116); - z = z > 0.008856 ? (z ** (1 / 3)) : (7.787 * z) + (16 / 116); - - const l = (116 * y) - 16; - const a = 500 * (x - y); - const b = 200 * (y - z); - - return [l, a, b]; -}; - -convert.lab.xyz = function (lab) { - const l = lab[0]; - const a = lab[1]; - const b = lab[2]; - let x; - let y; - let z; - - y = (l + 16) / 116; - x = a / 500 + y; - z = y - b / 200; - - const y2 = y ** 3; - const x2 = x ** 3; - const z2 = z ** 3; - y = y2 > 0.008856 ? y2 : (y - 16 / 116) / 7.787; - x = x2 > 0.008856 ? x2 : (x - 16 / 116) / 7.787; - z = z2 > 0.008856 ? z2 : (z - 16 / 116) / 7.787; - - x *= 95.047; - y *= 100; - z *= 108.883; - - return [x, y, z]; -}; - -convert.lab.lch = function (lab) { - const l = lab[0]; - const a = lab[1]; - const b = lab[2]; - let h; - - const hr = Math.atan2(b, a); - h = hr * 360 / 2 / Math.PI; - - if (h < 0) { - h += 360; - } - - const c = Math.sqrt(a * a + b * b); - - return [l, c, h]; -}; - -convert.lch.lab = function (lch) { - const l = lch[0]; - const c = lch[1]; - const h = lch[2]; - - const hr = h / 360 * 2 * Math.PI; - const a = c * Math.cos(hr); - const b = c * Math.sin(hr); - - return [l, a, b]; -}; - -convert.rgb.ansi16 = function (args, saturation = null) { - const [r, g, b] = args; - let value = saturation === null ? convert.rgb.hsv(args)[2] : saturation; // Hsv -> ansi16 optimization - - value = Math.round(value / 50); - - if (value === 0) { - return 30; - } - - let ansi = 30 - + ((Math.round(b / 255) << 2) - | (Math.round(g / 255) << 1) - | Math.round(r / 255)); - - if (value === 2) { - ansi += 60; - } - - return ansi; -}; - -convert.hsv.ansi16 = function (args) { - // Optimization here; we already know the value and don't need to get - // it converted for us. - return convert.rgb.ansi16(convert.hsv.rgb(args), args[2]); -}; - -convert.rgb.ansi256 = function (args) { - const r = args[0]; - const g = args[1]; - const b = args[2]; - - // We use the extended greyscale palette here, with the exception of - // black and white. normal palette only has 4 greyscale shades. - if (r === g && g === b) { - if (r < 8) { - return 16; - } - - if (r > 248) { - return 231; - } - - return Math.round(((r - 8) / 247) * 24) + 232; - } - - const ansi = 16 - + (36 * Math.round(r / 255 * 5)) - + (6 * Math.round(g / 255 * 5)) - + Math.round(b / 255 * 5); - - return ansi; -}; - -convert.ansi16.rgb = function (args) { - let color = args % 10; - - // Handle greyscale - if (color === 0 || color === 7) { - if (args > 50) { - color += 3.5; - } - - color = color / 10.5 * 255; - - return [color, color, color]; - } - - const mult = (~~(args > 50) + 1) * 0.5; - const r = ((color & 1) * mult) * 255; - const g = (((color >> 1) & 1) * mult) * 255; - const b = (((color >> 2) & 1) * mult) * 255; - - return [r, g, b]; -}; - -convert.ansi256.rgb = function (args) { - // Handle greyscale - if (args >= 232) { - const c = (args - 232) * 10 + 8; - return [c, c, c]; - } - - args -= 16; - - let rem; - const r = Math.floor(args / 36) / 5 * 255; - const g = Math.floor((rem = args % 36) / 6) / 5 * 255; - const b = (rem % 6) / 5 * 255; - - return [r, g, b]; -}; - -convert.rgb.hex = function (args) { - const integer = ((Math.round(args[0]) & 0xFF) << 16) - + ((Math.round(args[1]) & 0xFF) << 8) - + (Math.round(args[2]) & 0xFF); - - const string = integer.toString(16).toUpperCase(); - return '000000'.substring(string.length) + string; -}; - -convert.hex.rgb = function (args) { - const match = args.toString(16).match(/[a-f0-9]{6}|[a-f0-9]{3}/i); - if (!match) { - return [0, 0, 0]; - } - - let colorString = match[0]; - - if (match[0].length === 3) { - colorString = colorString.split('').map(char => { - return char + char; - }).join(''); - } - - const integer = parseInt(colorString, 16); - const r = (integer >> 16) & 0xFF; - const g = (integer >> 8) & 0xFF; - const b = integer & 0xFF; - - return [r, g, b]; -}; - -convert.rgb.hcg = function (rgb) { - const r = rgb[0] / 255; - const g = rgb[1] / 255; - const b = rgb[2] / 255; - const max = Math.max(Math.max(r, g), b); - const min = Math.min(Math.min(r, g), b); - const chroma = (max - min); - let grayscale; - let hue; - - if (chroma < 1) { - grayscale = min / (1 - chroma); - } else { - grayscale = 0; - } - - if (chroma <= 0) { - hue = 0; - } else - if (max === r) { - hue = ((g - b) / chroma) % 6; - } else - if (max === g) { - hue = 2 + (b - r) / chroma; - } else { - hue = 4 + (r - g) / chroma; - } - - hue /= 6; - hue %= 1; - - return [hue * 360, chroma * 100, grayscale * 100]; -}; - -convert.hsl.hcg = function (hsl) { - const s = hsl[1] / 100; - const l = hsl[2] / 100; - - const c = l < 0.5 ? (2.0 * s * l) : (2.0 * s * (1.0 - l)); - - let f = 0; - if (c < 1.0) { - f = (l - 0.5 * c) / (1.0 - c); - } - - return [hsl[0], c * 100, f * 100]; -}; - -convert.hsv.hcg = function (hsv) { - const s = hsv[1] / 100; - const v = hsv[2] / 100; - - const c = s * v; - let f = 0; - - if (c < 1.0) { - f = (v - c) / (1 - c); - } - - return [hsv[0], c * 100, f * 100]; -}; - -convert.hcg.rgb = function (hcg) { - const h = hcg[0] / 360; - const c = hcg[1] / 100; - const g = hcg[2] / 100; - - if (c === 0.0) { - return [g * 255, g * 255, g * 255]; - } - - const pure = [0, 0, 0]; - const hi = (h % 1) * 6; - const v = hi % 1; - const w = 1 - v; - let mg = 0; - - /* eslint-disable max-statements-per-line */ - switch (Math.floor(hi)) { - case 0: - pure[0] = 1; pure[1] = v; pure[2] = 0; break; - case 1: - pure[0] = w; pure[1] = 1; pure[2] = 0; break; - case 2: - pure[0] = 0; pure[1] = 1; pure[2] = v; break; - case 3: - pure[0] = 0; pure[1] = w; pure[2] = 1; break; - case 4: - pure[0] = v; pure[1] = 0; pure[2] = 1; break; - default: - pure[0] = 1; pure[1] = 0; pure[2] = w; - } - /* eslint-enable max-statements-per-line */ - - mg = (1.0 - c) * g; - - return [ - (c * pure[0] + mg) * 255, - (c * pure[1] + mg) * 255, - (c * pure[2] + mg) * 255 - ]; -}; - -convert.hcg.hsv = function (hcg) { - const c = hcg[1] / 100; - const g = hcg[2] / 100; - - const v = c + g * (1.0 - c); - let f = 0; - - if (v > 0.0) { - f = c / v; - } - - return [hcg[0], f * 100, v * 100]; -}; - -convert.hcg.hsl = function (hcg) { - const c = hcg[1] / 100; - const g = hcg[2] / 100; - - const l = g * (1.0 - c) + 0.5 * c; - let s = 0; - - if (l > 0.0 && l < 0.5) { - s = c / (2 * l); - } else - if (l >= 0.5 && l < 1.0) { - s = c / (2 * (1 - l)); - } - - return [hcg[0], s * 100, l * 100]; -}; - -convert.hcg.hwb = function (hcg) { - const c = hcg[1] / 100; - const g = hcg[2] / 100; - const v = c + g * (1.0 - c); - return [hcg[0], (v - c) * 100, (1 - v) * 100]; -}; - -convert.hwb.hcg = function (hwb) { - const w = hwb[1] / 100; - const b = hwb[2] / 100; - const v = 1 - b; - const c = v - w; - let g = 0; - - if (c < 1) { - g = (v - c) / (1 - c); - } - - return [hwb[0], c * 100, g * 100]; -}; - -convert.apple.rgb = function (apple) { - return [(apple[0] / 65535) * 255, (apple[1] / 65535) * 255, (apple[2] / 65535) * 255]; -}; - -convert.rgb.apple = function (rgb) { - return [(rgb[0] / 255) * 65535, (rgb[1] / 255) * 65535, (rgb[2] / 255) * 65535]; -}; - -convert.gray.rgb = function (args) { - return [args[0] / 100 * 255, args[0] / 100 * 255, args[0] / 100 * 255]; -}; - -convert.gray.hsl = function (args) { - return [0, 0, args[0]]; -}; - -convert.gray.hsv = convert.gray.hsl; - -convert.gray.hwb = function (gray) { - return [0, 100, gray[0]]; -}; - -convert.gray.cmyk = function (gray) { - return [0, 0, 0, gray[0]]; -}; - -convert.gray.lab = function (gray) { - return [gray[0], 0, 0]; -}; - -convert.gray.hex = function (gray) { - const val = Math.round(gray[0] / 100 * 255) & 0xFF; - const integer = (val << 16) + (val << 8) + val; - - const string = integer.toString(16).toUpperCase(); - return '000000'.substring(string.length) + string; -}; - -convert.rgb.gray = function (rgb) { - const val = (rgb[0] + rgb[1] + rgb[2]) / 3; - return [val / 255 * 100]; -}; - - -/***/ }), - -/***/ "../../node_modules/ansi-styles/node_modules/color-convert/index.js": -/***/ (function(module, exports, __webpack_require__) { - -const conversions = __webpack_require__("../../node_modules/ansi-styles/node_modules/color-convert/conversions.js"); -const route = __webpack_require__("../../node_modules/ansi-styles/node_modules/color-convert/route.js"); - -const convert = {}; - -const models = Object.keys(conversions); - -function wrapRaw(fn) { - const wrappedFn = function (...args) { - const arg0 = args[0]; - if (arg0 === undefined || arg0 === null) { - return arg0; - } - - if (arg0.length > 1) { - args = arg0; - } - - return fn(args); - }; - - // Preserve .conversion property if there is one - if ('conversion' in fn) { - wrappedFn.conversion = fn.conversion; - } - - return wrappedFn; -} - -function wrapRounded(fn) { - const wrappedFn = function (...args) { - const arg0 = args[0]; - - if (arg0 === undefined || arg0 === null) { - return arg0; - } - - if (arg0.length > 1) { - args = arg0; - } - - const result = fn(args); - - // We're assuming the result is an array here. - // see notice in conversions.js; don't use box types - // in conversion functions. - if (typeof result === 'object') { - for (let len = result.length, i = 0; i < len; i++) { - result[i] = Math.round(result[i]); - } - } - - return result; - }; - - // Preserve .conversion property if there is one - if ('conversion' in fn) { - wrappedFn.conversion = fn.conversion; - } - - return wrappedFn; -} - -models.forEach(fromModel => { - convert[fromModel] = {}; - - Object.defineProperty(convert[fromModel], 'channels', {value: conversions[fromModel].channels}); - Object.defineProperty(convert[fromModel], 'labels', {value: conversions[fromModel].labels}); - - const routes = route(fromModel); - const routeModels = Object.keys(routes); - - routeModels.forEach(toModel => { - const fn = routes[toModel]; - - convert[fromModel][toModel] = wrapRounded(fn); - convert[fromModel][toModel].raw = wrapRaw(fn); - }); -}); - -module.exports = convert; - - -/***/ }), - -/***/ "../../node_modules/ansi-styles/node_modules/color-convert/route.js": -/***/ (function(module, exports, __webpack_require__) { - -const conversions = __webpack_require__("../../node_modules/ansi-styles/node_modules/color-convert/conversions.js"); - -/* - This function routes a model to all other models. - - all functions that are routed have a property `.conversion` attached - to the returned synthetic function. This property is an array - of strings, each with the steps in between the 'from' and 'to' - color models (inclusive). - - conversions that are not possible simply are not included. -*/ - -function buildGraph() { - const graph = {}; - // https://jsperf.com/object-keys-vs-for-in-with-closure/3 - const models = Object.keys(conversions); - - for (let len = models.length, i = 0; i < len; i++) { - graph[models[i]] = { - // http://jsperf.com/1-vs-infinity - // micro-opt, but this is simple. - distance: -1, - parent: null - }; - } - - return graph; -} - -// https://en.wikipedia.org/wiki/Breadth-first_search -function deriveBFS(fromModel) { - const graph = buildGraph(); - const queue = [fromModel]; // Unshift -> queue -> pop - - graph[fromModel].distance = 0; - - while (queue.length) { - const current = queue.pop(); - const adjacents = Object.keys(conversions[current]); - - for (let len = adjacents.length, i = 0; i < len; i++) { - const adjacent = adjacents[i]; - const node = graph[adjacent]; - - if (node.distance === -1) { - node.distance = graph[current].distance + 1; - node.parent = current; - queue.unshift(adjacent); - } - } - } - - return graph; -} - -function link(from, to) { - return function (args) { - return to(from(args)); - }; -} - -function wrapConversion(toModel, graph) { - const path = [graph[toModel].parent, toModel]; - let fn = conversions[graph[toModel].parent][toModel]; - - let cur = graph[toModel].parent; - while (graph[cur].parent) { - path.unshift(graph[cur].parent); - fn = link(conversions[graph[cur].parent][cur], fn); - cur = graph[cur].parent; - } - - fn.conversion = path; - return fn; -} - -module.exports = function (fromModel) { - const graph = deriveBFS(fromModel); - const conversion = {}; - - const models = Object.keys(graph); - for (let len = models.length, i = 0; i < len; i++) { - const toModel = models[i]; - const node = graph[toModel]; - - if (node.parent === null) { - // No possible conversion, or this node is the source model. - continue; - } - - conversion[toModel] = wrapConversion(toModel, graph); - } - - return conversion; -}; - - - -/***/ }), - -/***/ "../../node_modules/array-differ/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const arrayDiffer = (array, ...values) => { - const rest = new Set([].concat(...values)); - return array.filter(element => !rest.has(element)); -}; - -module.exports = arrayDiffer; - - -/***/ }), - -/***/ "../../node_modules/array-union/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = (...arguments_) => { - return [...new Set([].concat(...arguments_))]; -}; - - -/***/ }), - -/***/ "../../node_modules/arrify/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const arrify = value => { - if (value === null || value === undefined) { - return []; - } - - if (Array.isArray(value)) { - return value; - } - - if (typeof value === 'string') { - return [value]; - } - - if (typeof value[Symbol.iterator] === 'function') { - return [...value]; - } - - return [value]; -}; - -module.exports = arrify; - - -/***/ }), - -/***/ "../../node_modules/asynckit/index.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = -{ - parallel : __webpack_require__("../../node_modules/asynckit/parallel.js"), - serial : __webpack_require__("../../node_modules/asynckit/serial.js"), - serialOrdered : __webpack_require__("../../node_modules/asynckit/serialOrdered.js") -}; - - -/***/ }), - -/***/ "../../node_modules/asynckit/lib/abort.js": -/***/ (function(module, exports) { - -// API -module.exports = abort; - -/** - * Aborts leftover active jobs - * - * @param {object} state - current state object - */ -function abort(state) -{ - Object.keys(state.jobs).forEach(clean.bind(state)); - - // reset leftover jobs - state.jobs = {}; -} - -/** - * Cleans up leftover job by invoking abort function for the provided job id - * - * @this state - * @param {string|number} key - job id to abort - */ -function clean(key) -{ - if (typeof this.jobs[key] == 'function') - { - this.jobs[key](); - } -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/lib/async.js": -/***/ (function(module, exports, __webpack_require__) { - -var defer = __webpack_require__("../../node_modules/asynckit/lib/defer.js"); - -// API -module.exports = async; - -/** - * Runs provided callback asynchronously - * even if callback itself is not - * - * @param {function} callback - callback to invoke - * @returns {function} - augmented callback - */ -function async(callback) -{ - var isAsync = false; - - // check if async happened - defer(function() { isAsync = true; }); - - return function async_callback(err, result) - { - if (isAsync) - { - callback(err, result); - } - else - { - defer(function nextTick_callback() - { - callback(err, result); - }); - } - }; -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/lib/defer.js": -/***/ (function(module, exports) { - -module.exports = defer; - -/** - * Runs provided function on next iteration of the event loop - * - * @param {function} fn - function to run - */ -function defer(fn) -{ - var nextTick = typeof setImmediate == 'function' - ? setImmediate - : ( - typeof process == 'object' && typeof process.nextTick == 'function' - ? process.nextTick - : null - ); - - if (nextTick) - { - nextTick(fn); - } - else - { - setTimeout(fn, 0); - } -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/lib/iterate.js": -/***/ (function(module, exports, __webpack_require__) { - -var async = __webpack_require__("../../node_modules/asynckit/lib/async.js") - , abort = __webpack_require__("../../node_modules/asynckit/lib/abort.js") - ; - -// API -module.exports = iterate; - -/** - * Iterates over each job object - * - * @param {array|object} list - array or object (named list) to iterate over - * @param {function} iterator - iterator to run - * @param {object} state - current job status - * @param {function} callback - invoked when all elements processed - */ -function iterate(list, iterator, state, callback) -{ - // store current index - var key = state['keyedList'] ? state['keyedList'][state.index] : state.index; - - state.jobs[key] = runJob(iterator, key, list[key], function(error, output) - { - // don't repeat yourself - // skip secondary callbacks - if (!(key in state.jobs)) - { - return; - } - - // clean up jobs - delete state.jobs[key]; - - if (error) - { - // don't process rest of the results - // stop still active jobs - // and reset the list - abort(state); - } - else - { - state.results[key] = output; - } - - // return salvaged results - callback(error, state.results); - }); -} - -/** - * Runs iterator over provided job element - * - * @param {function} iterator - iterator to invoke - * @param {string|number} key - key/index of the element in the list of jobs - * @param {mixed} item - job description - * @param {function} callback - invoked after iterator is done with the job - * @returns {function|mixed} - job abort function or something else - */ -function runJob(iterator, key, item, callback) -{ - var aborter; - - // allow shortcut if iterator expects only two arguments - if (iterator.length == 2) - { - aborter = iterator(item, async(callback)); - } - // otherwise go with full three arguments - else - { - aborter = iterator(item, key, async(callback)); - } - - return aborter; -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/lib/state.js": -/***/ (function(module, exports) { - -// API -module.exports = state; - -/** - * Creates initial state object - * for iteration over list - * - * @param {array|object} list - list to iterate over - * @param {function|null} sortMethod - function to use for keys sort, - * or `null` to keep them as is - * @returns {object} - initial state object - */ -function state(list, sortMethod) -{ - var isNamedList = !Array.isArray(list) - , initState = - { - index : 0, - keyedList: isNamedList || sortMethod ? Object.keys(list) : null, - jobs : {}, - results : isNamedList ? {} : [], - size : isNamedList ? Object.keys(list).length : list.length - } - ; - - if (sortMethod) - { - // sort array keys based on it's values - // sort object's keys just on own merit - initState.keyedList.sort(isNamedList ? sortMethod : function(a, b) - { - return sortMethod(list[a], list[b]); - }); - } - - return initState; -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/lib/terminator.js": -/***/ (function(module, exports, __webpack_require__) { - -var abort = __webpack_require__("../../node_modules/asynckit/lib/abort.js") - , async = __webpack_require__("../../node_modules/asynckit/lib/async.js") - ; - -// API -module.exports = terminator; - -/** - * Terminates jobs in the attached state context - * - * @this AsyncKitState# - * @param {function} callback - final callback to invoke after termination - */ -function terminator(callback) -{ - if (!Object.keys(this.jobs).length) - { - return; - } - - // fast forward iteration index - this.index = this.size; - - // abort jobs - abort(this); - - // send back results we have so far - async(callback)(null, this.results); -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/parallel.js": -/***/ (function(module, exports, __webpack_require__) { - -var iterate = __webpack_require__("../../node_modules/asynckit/lib/iterate.js") - , initState = __webpack_require__("../../node_modules/asynckit/lib/state.js") - , terminator = __webpack_require__("../../node_modules/asynckit/lib/terminator.js") - ; - -// Public API -module.exports = parallel; - -/** - * Runs iterator over provided array elements in parallel - * - * @param {array|object} list - array or object (named list) to iterate over - * @param {function} iterator - iterator to run - * @param {function} callback - invoked when all elements processed - * @returns {function} - jobs terminator - */ -function parallel(list, iterator, callback) -{ - var state = initState(list); - - while (state.index < (state['keyedList'] || list).length) - { - iterate(list, iterator, state, function(error, result) - { - if (error) - { - callback(error, result); - return; - } - - // looks like it's the last one - if (Object.keys(state.jobs).length === 0) - { - callback(null, state.results); - return; - } - }); - - state.index++; - } - - return terminator.bind(state, callback); -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/serial.js": -/***/ (function(module, exports, __webpack_require__) { - -var serialOrdered = __webpack_require__("../../node_modules/asynckit/serialOrdered.js"); - -// Public API -module.exports = serial; - -/** - * Runs iterator over provided array elements in series - * - * @param {array|object} list - array or object (named list) to iterate over - * @param {function} iterator - iterator to run - * @param {function} callback - invoked when all elements processed - * @returns {function} - jobs terminator - */ -function serial(list, iterator, callback) -{ - return serialOrdered(list, iterator, null, callback); -} - - -/***/ }), - -/***/ "../../node_modules/asynckit/serialOrdered.js": -/***/ (function(module, exports, __webpack_require__) { - -var iterate = __webpack_require__("../../node_modules/asynckit/lib/iterate.js") - , initState = __webpack_require__("../../node_modules/asynckit/lib/state.js") - , terminator = __webpack_require__("../../node_modules/asynckit/lib/terminator.js") - ; - -// Public API -module.exports = serialOrdered; -// sorting helpers -module.exports.ascending = ascending; -module.exports.descending = descending; - -/** - * Runs iterator over provided sorted array elements in series - * - * @param {array|object} list - array or object (named list) to iterate over - * @param {function} iterator - iterator to run - * @param {function} sortMethod - custom sort function - * @param {function} callback - invoked when all elements processed - * @returns {function} - jobs terminator - */ -function serialOrdered(list, iterator, sortMethod, callback) -{ - var state = initState(list, sortMethod); - - iterate(list, iterator, state, function iteratorHandler(error, result) - { - if (error) - { - callback(error, result); - return; - } - - state.index++; - - // are we there yet? - if (state.index < (state['keyedList'] || list).length) - { - iterate(list, iterator, state, iteratorHandler); - return; - } - - // done here - callback(null, state.results); - }); - - return terminator.bind(state, callback); -} - -/* - * -- Sort methods - */ - -/** - * sort helper to sort array elements in ascending order - * - * @param {mixed} a - an item to compare - * @param {mixed} b - an item to compare - * @returns {number} - comparison result - */ -function ascending(a, b) -{ - return a < b ? -1 : a > b ? 1 : 0; -} - -/** - * sort helper to sort array elements in descending order - * - * @param {mixed} a - an item to compare - * @param {mixed} b - an item to compare - * @returns {number} - comparison result - */ -function descending(a, b) -{ - return -1 * ascending(a, b); -} - - -/***/ }), - -/***/ "../../node_modules/axios/index.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = __webpack_require__("../../node_modules/axios/lib/axios.js"); - -/***/ }), - -/***/ "../../node_modules/axios/lib/adapters/http.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); -var settle = __webpack_require__("../../node_modules/axios/lib/core/settle.js"); -var buildFullPath = __webpack_require__("../../node_modules/axios/lib/core/buildFullPath.js"); -var buildURL = __webpack_require__("../../node_modules/axios/lib/helpers/buildURL.js"); -var http = __webpack_require__("http"); -var https = __webpack_require__("https"); -var httpFollow = __webpack_require__("../../node_modules/follow-redirects/index.js").http; -var httpsFollow = __webpack_require__("../../node_modules/follow-redirects/index.js").https; -var url = __webpack_require__("url"); -var zlib = __webpack_require__("zlib"); -var VERSION = __webpack_require__("../../node_modules/axios/lib/env/data.js").version; -var transitionalDefaults = __webpack_require__("../../node_modules/axios/lib/defaults/transitional.js"); -var AxiosError = __webpack_require__("../../node_modules/axios/lib/core/AxiosError.js"); -var CanceledError = __webpack_require__("../../node_modules/axios/lib/cancel/CanceledError.js"); - -var isHttps = /https:?/; - -var supportedProtocols = [ 'http:', 'https:', 'file:' ]; - -/** - * - * @param {http.ClientRequestArgs} options - * @param {AxiosProxyConfig} proxy - * @param {string} location - */ -function setProxy(options, proxy, location) { - options.hostname = proxy.host; - options.host = proxy.host; - options.port = proxy.port; - options.path = location; - - // Basic proxy authorization - if (proxy.auth) { - var base64 = Buffer.from(proxy.auth.username + ':' + proxy.auth.password, 'utf8').toString('base64'); - options.headers['Proxy-Authorization'] = 'Basic ' + base64; - } - - // If a proxy is used, any redirects must also pass through the proxy - options.beforeRedirect = function beforeRedirect(redirection) { - redirection.headers.host = redirection.host; - setProxy(redirection, proxy, redirection.href); - }; -} - -/*eslint consistent-return:0*/ -module.exports = function httpAdapter(config) { - return new Promise(function dispatchHttpRequest(resolvePromise, rejectPromise) { - var onCanceled; - function done() { - if (config.cancelToken) { - config.cancelToken.unsubscribe(onCanceled); - } - - if (config.signal) { - config.signal.removeEventListener('abort', onCanceled); - } - } - var resolve = function resolve(value) { - done(); - resolvePromise(value); - }; - var rejected = false; - var reject = function reject(value) { - done(); - rejected = true; - rejectPromise(value); - }; - var data = config.data; - var headers = config.headers; - var headerNames = {}; - - Object.keys(headers).forEach(function storeLowerName(name) { - headerNames[name.toLowerCase()] = name; - }); - - // Set User-Agent (required by some servers) - // See https://github.com/axios/axios/issues/69 - if ('user-agent' in headerNames) { - // User-Agent is specified; handle case where no UA header is desired - if (!headers[headerNames['user-agent']]) { - delete headers[headerNames['user-agent']]; - } - // Otherwise, use specified value - } else { - // Only set header if it hasn't been set in config - headers['User-Agent'] = 'axios/' + VERSION; - } - - // support for https://www.npmjs.com/package/form-data api - if (utils.isFormData(data) && utils.isFunction(data.getHeaders)) { - Object.assign(headers, data.getHeaders()); - } else if (data && !utils.isStream(data)) { - if (Buffer.isBuffer(data)) { - // Nothing to do... - } else if (utils.isArrayBuffer(data)) { - data = Buffer.from(new Uint8Array(data)); - } else if (utils.isString(data)) { - data = Buffer.from(data, 'utf-8'); - } else { - return reject(new AxiosError( - 'Data after transformation must be a string, an ArrayBuffer, a Buffer, or a Stream', - AxiosError.ERR_BAD_REQUEST, - config - )); - } - - if (config.maxBodyLength > -1 && data.length > config.maxBodyLength) { - return reject(new AxiosError( - 'Request body larger than maxBodyLength limit', - AxiosError.ERR_BAD_REQUEST, - config - )); - } - - // Add Content-Length header if data exists - if (!headerNames['content-length']) { - headers['Content-Length'] = data.length; - } - } - - // HTTP basic authentication - var auth = undefined; - if (config.auth) { - var username = config.auth.username || ''; - var password = config.auth.password || ''; - auth = username + ':' + password; - } - - // Parse url - var fullPath = buildFullPath(config.baseURL, config.url); - var parsed = url.parse(fullPath); - var protocol = parsed.protocol || supportedProtocols[0]; - - if (supportedProtocols.indexOf(protocol) === -1) { - return reject(new AxiosError( - 'Unsupported protocol ' + protocol, - AxiosError.ERR_BAD_REQUEST, - config - )); - } - - if (!auth && parsed.auth) { - var urlAuth = parsed.auth.split(':'); - var urlUsername = urlAuth[0] || ''; - var urlPassword = urlAuth[1] || ''; - auth = urlUsername + ':' + urlPassword; - } - - if (auth && headerNames.authorization) { - delete headers[headerNames.authorization]; - } - - var isHttpsRequest = isHttps.test(protocol); - var agent = isHttpsRequest ? config.httpsAgent : config.httpAgent; - - try { - buildURL(parsed.path, config.params, config.paramsSerializer).replace(/^\?/, ''); - } catch (err) { - var customErr = new Error(err.message); - customErr.config = config; - customErr.url = config.url; - customErr.exists = true; - reject(customErr); - } - - var options = { - path: buildURL(parsed.path, config.params, config.paramsSerializer).replace(/^\?/, ''), - method: config.method.toUpperCase(), - headers: headers, - agent: agent, - agents: { http: config.httpAgent, https: config.httpsAgent }, - auth: auth - }; - - if (config.socketPath) { - options.socketPath = config.socketPath; - } else { - options.hostname = parsed.hostname; - options.port = parsed.port; - } - - var proxy = config.proxy; - if (!proxy && proxy !== false) { - var proxyEnv = protocol.slice(0, -1) + '_proxy'; - var proxyUrl = process.env[proxyEnv] || process.env[proxyEnv.toUpperCase()]; - if (proxyUrl) { - var parsedProxyUrl = url.parse(proxyUrl); - var noProxyEnv = process.env.no_proxy || process.env.NO_PROXY; - var shouldProxy = true; - - if (noProxyEnv) { - var noProxy = noProxyEnv.split(',').map(function trim(s) { - return s.trim(); - }); - - shouldProxy = !noProxy.some(function proxyMatch(proxyElement) { - if (!proxyElement) { - return false; - } - if (proxyElement === '*') { - return true; - } - if (proxyElement[0] === '.' && - parsed.hostname.substr(parsed.hostname.length - proxyElement.length) === proxyElement) { - return true; - } - - return parsed.hostname === proxyElement; - }); - } - - if (shouldProxy) { - proxy = { - host: parsedProxyUrl.hostname, - port: parsedProxyUrl.port, - protocol: parsedProxyUrl.protocol - }; - - if (parsedProxyUrl.auth) { - var proxyUrlAuth = parsedProxyUrl.auth.split(':'); - proxy.auth = { - username: proxyUrlAuth[0], - password: proxyUrlAuth[1] - }; - } - } - } - } - - if (proxy) { - options.headers.host = parsed.hostname + (parsed.port ? ':' + parsed.port : ''); - setProxy(options, proxy, protocol + '//' + parsed.hostname + (parsed.port ? ':' + parsed.port : '') + options.path); - } - - var transport; - var isHttpsProxy = isHttpsRequest && (proxy ? isHttps.test(proxy.protocol) : true); - if (config.transport) { - transport = config.transport; - } else if (config.maxRedirects === 0) { - transport = isHttpsProxy ? https : http; - } else { - if (config.maxRedirects) { - options.maxRedirects = config.maxRedirects; - } - if (config.beforeRedirect) { - options.beforeRedirect = config.beforeRedirect; - } - transport = isHttpsProxy ? httpsFollow : httpFollow; - } - - if (config.maxBodyLength > -1) { - options.maxBodyLength = config.maxBodyLength; - } - - if (config.insecureHTTPParser) { - options.insecureHTTPParser = config.insecureHTTPParser; - } - - // Create the request - var req = transport.request(options, function handleResponse(res) { - if (req.aborted) return; - - // uncompress the response body transparently if required - var stream = res; - - // return the last request in case of redirects - var lastRequest = res.req || req; - - - // if no content, is HEAD request or decompress disabled we should not decompress - if (res.statusCode !== 204 && lastRequest.method !== 'HEAD' && config.decompress !== false) { - switch (res.headers['content-encoding']) { - /*eslint default-case:0*/ - case 'gzip': - case 'compress': - case 'deflate': - // add the unzipper to the body stream processing pipeline - stream = stream.pipe(zlib.createUnzip()); - - // remove the content-encoding in order to not confuse downstream operations - delete res.headers['content-encoding']; - break; - } - } - - var response = { - status: res.statusCode, - statusText: res.statusMessage, - headers: res.headers, - config: config, - request: lastRequest - }; - - if (config.responseType === 'stream') { - response.data = stream; - settle(resolve, reject, response); - } else { - var responseBuffer = []; - var totalResponseBytes = 0; - stream.on('data', function handleStreamData(chunk) { - responseBuffer.push(chunk); - totalResponseBytes += chunk.length; - - // make sure the content length is not over the maxContentLength if specified - if (config.maxContentLength > -1 && totalResponseBytes > config.maxContentLength) { - // stream.destoy() emit aborted event before calling reject() on Node.js v16 - rejected = true; - stream.destroy(); - reject(new AxiosError('maxContentLength size of ' + config.maxContentLength + ' exceeded', - AxiosError.ERR_BAD_RESPONSE, config, lastRequest)); - } - }); - - stream.on('aborted', function handlerStreamAborted() { - if (rejected) { - return; - } - stream.destroy(); - reject(new AxiosError( - 'maxContentLength size of ' + config.maxContentLength + ' exceeded', - AxiosError.ERR_BAD_RESPONSE, - config, - lastRequest - )); - }); - - stream.on('error', function handleStreamError(err) { - if (req.aborted) return; - reject(AxiosError.from(err, null, config, lastRequest)); - }); - - stream.on('end', function handleStreamEnd() { - try { - var responseData = responseBuffer.length === 1 ? responseBuffer[0] : Buffer.concat(responseBuffer); - if (config.responseType !== 'arraybuffer') { - responseData = responseData.toString(config.responseEncoding); - if (!config.responseEncoding || config.responseEncoding === 'utf8') { - responseData = utils.stripBOM(responseData); - } - } - response.data = responseData; - } catch (err) { - reject(AxiosError.from(err, null, config, response.request, response)); - } - settle(resolve, reject, response); - }); - } - }); - - // Handle errors - req.on('error', function handleRequestError(err) { - // @todo remove - // if (req.aborted && err.code !== AxiosError.ERR_FR_TOO_MANY_REDIRECTS) return; - reject(AxiosError.from(err, null, config, req)); - }); - - // set tcp keep alive to prevent drop connection by peer - req.on('socket', function handleRequestSocket(socket) { - // default interval of sending ack packet is 1 minute - socket.setKeepAlive(true, 1000 * 60); - }); - - // Handle request timeout - if (config.timeout) { - // This is forcing a int timeout to avoid problems if the `req` interface doesn't handle other types. - var timeout = parseInt(config.timeout, 10); - - if (isNaN(timeout)) { - reject(new AxiosError( - 'error trying to parse `config.timeout` to int', - AxiosError.ERR_BAD_OPTION_VALUE, - config, - req - )); - - return; - } - - // Sometime, the response will be very slow, and does not respond, the connect event will be block by event loop system. - // And timer callback will be fired, and abort() will be invoked before connection, then get "socket hang up" and code ECONNRESET. - // At this time, if we have a large number of request, nodejs will hang up some socket on background. and the number will up and up. - // And then these socket which be hang up will devoring CPU little by little. - // ClientRequest.setTimeout will be fired on the specify milliseconds, and can make sure that abort() will be fired after connect. - req.setTimeout(timeout, function handleRequestTimeout() { - req.abort(); - var transitional = config.transitional || transitionalDefaults; - reject(new AxiosError( - 'timeout of ' + timeout + 'ms exceeded', - transitional.clarifyTimeoutError ? AxiosError.ETIMEDOUT : AxiosError.ECONNABORTED, - config, - req - )); - }); - } - - if (config.cancelToken || config.signal) { - // Handle cancellation - // eslint-disable-next-line func-names - onCanceled = function(cancel) { - if (req.aborted) return; - - req.abort(); - reject(!cancel || (cancel && cancel.type) ? new CanceledError() : cancel); - }; - - config.cancelToken && config.cancelToken.subscribe(onCanceled); - if (config.signal) { - config.signal.aborted ? onCanceled() : config.signal.addEventListener('abort', onCanceled); - } - } - - - // Send the request - if (utils.isStream(data)) { - data.on('error', function handleStreamError(err) { - reject(AxiosError.from(err, config, null, req)); - }).pipe(req); - } else { - req.end(data); - } - }); -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/adapters/xhr.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); -var settle = __webpack_require__("../../node_modules/axios/lib/core/settle.js"); -var cookies = __webpack_require__("../../node_modules/axios/lib/helpers/cookies.js"); -var buildURL = __webpack_require__("../../node_modules/axios/lib/helpers/buildURL.js"); -var buildFullPath = __webpack_require__("../../node_modules/axios/lib/core/buildFullPath.js"); -var parseHeaders = __webpack_require__("../../node_modules/axios/lib/helpers/parseHeaders.js"); -var isURLSameOrigin = __webpack_require__("../../node_modules/axios/lib/helpers/isURLSameOrigin.js"); -var transitionalDefaults = __webpack_require__("../../node_modules/axios/lib/defaults/transitional.js"); -var AxiosError = __webpack_require__("../../node_modules/axios/lib/core/AxiosError.js"); -var CanceledError = __webpack_require__("../../node_modules/axios/lib/cancel/CanceledError.js"); -var parseProtocol = __webpack_require__("../../node_modules/axios/lib/helpers/parseProtocol.js"); - -module.exports = function xhrAdapter(config) { - return new Promise(function dispatchXhrRequest(resolve, reject) { - var requestData = config.data; - var requestHeaders = config.headers; - var responseType = config.responseType; - var onCanceled; - function done() { - if (config.cancelToken) { - config.cancelToken.unsubscribe(onCanceled); - } - - if (config.signal) { - config.signal.removeEventListener('abort', onCanceled); - } - } - - if (utils.isFormData(requestData) && utils.isStandardBrowserEnv()) { - delete requestHeaders['Content-Type']; // Let the browser set it - } - - var request = new XMLHttpRequest(); - - // HTTP basic authentication - if (config.auth) { - var username = config.auth.username || ''; - var password = config.auth.password ? unescape(encodeURIComponent(config.auth.password)) : ''; - requestHeaders.Authorization = 'Basic ' + btoa(username + ':' + password); - } - - var fullPath = buildFullPath(config.baseURL, config.url); - - request.open(config.method.toUpperCase(), buildURL(fullPath, config.params, config.paramsSerializer), true); - - // Set the request timeout in MS - request.timeout = config.timeout; - - function onloadend() { - if (!request) { - return; - } - // Prepare the response - var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders(request.getAllResponseHeaders()) : null; - var responseData = !responseType || responseType === 'text' || responseType === 'json' ? - request.responseText : request.response; - var response = { - data: responseData, - status: request.status, - statusText: request.statusText, - headers: responseHeaders, - config: config, - request: request - }; - - settle(function _resolve(value) { - resolve(value); - done(); - }, function _reject(err) { - reject(err); - done(); - }, response); - - // Clean up request - request = null; - } - - if ('onloadend' in request) { - // Use onloadend if available - request.onloadend = onloadend; - } else { - // Listen for ready state to emulate onloadend - request.onreadystatechange = function handleLoad() { - if (!request || request.readyState !== 4) { - return; - } - - // The request errored out and we didn't get a response, this will be - // handled by onerror instead - // With one exception: request that using file: protocol, most browsers - // will return status as 0 even though it's a successful request - if (request.status === 0 && !(request.responseURL && request.responseURL.indexOf('file:') === 0)) { - return; - } - // readystate handler is calling before onerror or ontimeout handlers, - // so we should call onloadend on the next 'tick' - setTimeout(onloadend); - }; - } - - // Handle browser request cancellation (as opposed to a manual cancellation) - request.onabort = function handleAbort() { - if (!request) { - return; - } - - reject(new AxiosError('Request aborted', AxiosError.ECONNABORTED, config, request)); - - // Clean up request - request = null; - }; - - // Handle low level network errors - request.onerror = function handleError() { - // Real errors are hidden from us by the browser - // onerror should only fire if it's a network error - reject(new AxiosError('Network Error', AxiosError.ERR_NETWORK, config, request, request)); - - // Clean up request - request = null; - }; - - // Handle timeout - request.ontimeout = function handleTimeout() { - var timeoutErrorMessage = config.timeout ? 'timeout of ' + config.timeout + 'ms exceeded' : 'timeout exceeded'; - var transitional = config.transitional || transitionalDefaults; - if (config.timeoutErrorMessage) { - timeoutErrorMessage = config.timeoutErrorMessage; - } - reject(new AxiosError( - timeoutErrorMessage, - transitional.clarifyTimeoutError ? AxiosError.ETIMEDOUT : AxiosError.ECONNABORTED, - config, - request)); - - // Clean up request - request = null; - }; - - // Add xsrf header - // This is only done if running in a standard browser environment. - // Specifically not if we're in a web worker, or react-native. - if (utils.isStandardBrowserEnv()) { - // Add xsrf header - var xsrfValue = (config.withCredentials || isURLSameOrigin(fullPath)) && config.xsrfCookieName ? - cookies.read(config.xsrfCookieName) : - undefined; - - if (xsrfValue) { - requestHeaders[config.xsrfHeaderName] = xsrfValue; - } - } - - // Add headers to the request - if ('setRequestHeader' in request) { - utils.forEach(requestHeaders, function setRequestHeader(val, key) { - if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') { - // Remove Content-Type if data is undefined - delete requestHeaders[key]; - } else { - // Otherwise add header to the request - request.setRequestHeader(key, val); - } - }); - } - - // Add withCredentials to request if needed - if (!utils.isUndefined(config.withCredentials)) { - request.withCredentials = !!config.withCredentials; - } - - // Add responseType to request if needed - if (responseType && responseType !== 'json') { - request.responseType = config.responseType; - } - - // Handle progress if needed - if (typeof config.onDownloadProgress === 'function') { - request.addEventListener('progress', config.onDownloadProgress); - } - - // Not all browsers support upload events - if (typeof config.onUploadProgress === 'function' && request.upload) { - request.upload.addEventListener('progress', config.onUploadProgress); - } - - if (config.cancelToken || config.signal) { - // Handle cancellation - // eslint-disable-next-line func-names - onCanceled = function(cancel) { - if (!request) { - return; - } - reject(!cancel || (cancel && cancel.type) ? new CanceledError() : cancel); - request.abort(); - request = null; - }; - - config.cancelToken && config.cancelToken.subscribe(onCanceled); - if (config.signal) { - config.signal.aborted ? onCanceled() : config.signal.addEventListener('abort', onCanceled); - } - } - - if (!requestData) { - requestData = null; - } - - var protocol = parseProtocol(fullPath); - - if (protocol && [ 'http', 'https', 'file' ].indexOf(protocol) === -1) { - reject(new AxiosError('Unsupported protocol ' + protocol + ':', AxiosError.ERR_BAD_REQUEST, config)); - return; - } - - - // Send the request - request.send(requestData); - }); -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/axios.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); -var bind = __webpack_require__("../../node_modules/axios/lib/helpers/bind.js"); -var Axios = __webpack_require__("../../node_modules/axios/lib/core/Axios.js"); -var mergeConfig = __webpack_require__("../../node_modules/axios/lib/core/mergeConfig.js"); -var defaults = __webpack_require__("../../node_modules/axios/lib/defaults/index.js"); - -/** - * Create an instance of Axios - * - * @param {Object} defaultConfig The default config for the instance - * @return {Axios} A new instance of Axios - */ -function createInstance(defaultConfig) { - var context = new Axios(defaultConfig); - var instance = bind(Axios.prototype.request, context); - - // Copy axios.prototype to instance - utils.extend(instance, Axios.prototype, context); - - // Copy context to instance - utils.extend(instance, context); - - // Factory for creating new instances - instance.create = function create(instanceConfig) { - return createInstance(mergeConfig(defaultConfig, instanceConfig)); - }; - - return instance; -} - -// Create the default instance to be exported -var axios = createInstance(defaults); - -// Expose Axios class to allow class inheritance -axios.Axios = Axios; - -// Expose Cancel & CancelToken -axios.CanceledError = __webpack_require__("../../node_modules/axios/lib/cancel/CanceledError.js"); -axios.CancelToken = __webpack_require__("../../node_modules/axios/lib/cancel/CancelToken.js"); -axios.isCancel = __webpack_require__("../../node_modules/axios/lib/cancel/isCancel.js"); -axios.VERSION = __webpack_require__("../../node_modules/axios/lib/env/data.js").version; -axios.toFormData = __webpack_require__("../../node_modules/axios/lib/helpers/toFormData.js"); - -// Expose AxiosError class -axios.AxiosError = __webpack_require__("../../node_modules/axios/lib/core/AxiosError.js"); - -// alias for CanceledError for backward compatibility -axios.Cancel = axios.CanceledError; - -// Expose all/spread -axios.all = function all(promises) { - return Promise.all(promises); -}; -axios.spread = __webpack_require__("../../node_modules/axios/lib/helpers/spread.js"); - -// Expose isAxiosError -axios.isAxiosError = __webpack_require__("../../node_modules/axios/lib/helpers/isAxiosError.js"); - -module.exports = axios; - -// Allow use of default import syntax in TypeScript -module.exports.default = axios; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/cancel/CancelToken.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var CanceledError = __webpack_require__("../../node_modules/axios/lib/cancel/CanceledError.js"); - -/** - * A `CancelToken` is an object that can be used to request cancellation of an operation. - * - * @class - * @param {Function} executor The executor function. - */ -function CancelToken(executor) { - if (typeof executor !== 'function') { - throw new TypeError('executor must be a function.'); - } - - var resolvePromise; - - this.promise = new Promise(function promiseExecutor(resolve) { - resolvePromise = resolve; - }); - - var token = this; - - // eslint-disable-next-line func-names - this.promise.then(function(cancel) { - if (!token._listeners) return; - - var i; - var l = token._listeners.length; - - for (i = 0; i < l; i++) { - token._listeners[i](cancel); - } - token._listeners = null; - }); - - // eslint-disable-next-line func-names - this.promise.then = function(onfulfilled) { - var _resolve; - // eslint-disable-next-line func-names - var promise = new Promise(function(resolve) { - token.subscribe(resolve); - _resolve = resolve; - }).then(onfulfilled); - - promise.cancel = function reject() { - token.unsubscribe(_resolve); - }; - - return promise; - }; - - executor(function cancel(message) { - if (token.reason) { - // Cancellation has already been requested - return; - } - - token.reason = new CanceledError(message); - resolvePromise(token.reason); - }); -} - -/** - * Throws a `CanceledError` if cancellation has been requested. - */ -CancelToken.prototype.throwIfRequested = function throwIfRequested() { - if (this.reason) { - throw this.reason; - } -}; - -/** - * Subscribe to the cancel signal - */ - -CancelToken.prototype.subscribe = function subscribe(listener) { - if (this.reason) { - listener(this.reason); - return; - } - - if (this._listeners) { - this._listeners.push(listener); - } else { - this._listeners = [listener]; - } -}; - -/** - * Unsubscribe from the cancel signal - */ - -CancelToken.prototype.unsubscribe = function unsubscribe(listener) { - if (!this._listeners) { - return; - } - var index = this._listeners.indexOf(listener); - if (index !== -1) { - this._listeners.splice(index, 1); - } -}; - -/** - * Returns an object that contains a new `CancelToken` and a function that, when called, - * cancels the `CancelToken`. - */ -CancelToken.source = function source() { - var cancel; - var token = new CancelToken(function executor(c) { - cancel = c; - }); - return { - token: token, - cancel: cancel - }; -}; - -module.exports = CancelToken; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/cancel/CanceledError.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var AxiosError = __webpack_require__("../../node_modules/axios/lib/core/AxiosError.js"); -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -/** - * A `CanceledError` is an object that is thrown when an operation is canceled. - * - * @class - * @param {string=} message The message. - */ -function CanceledError(message) { - // eslint-disable-next-line no-eq-null,eqeqeq - AxiosError.call(this, message == null ? 'canceled' : message, AxiosError.ERR_CANCELED); - this.name = 'CanceledError'; -} - -utils.inherits(CanceledError, AxiosError, { - __CANCEL__: true -}); - -module.exports = CanceledError; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/cancel/isCancel.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = function isCancel(value) { - return !!(value && value.__CANCEL__); -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/Axios.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); -var buildURL = __webpack_require__("../../node_modules/axios/lib/helpers/buildURL.js"); -var InterceptorManager = __webpack_require__("../../node_modules/axios/lib/core/InterceptorManager.js"); -var dispatchRequest = __webpack_require__("../../node_modules/axios/lib/core/dispatchRequest.js"); -var mergeConfig = __webpack_require__("../../node_modules/axios/lib/core/mergeConfig.js"); -var buildFullPath = __webpack_require__("../../node_modules/axios/lib/core/buildFullPath.js"); -var validator = __webpack_require__("../../node_modules/axios/lib/helpers/validator.js"); - -var validators = validator.validators; -/** - * Create a new instance of Axios - * - * @param {Object} instanceConfig The default config for the instance - */ -function Axios(instanceConfig) { - this.defaults = instanceConfig; - this.interceptors = { - request: new InterceptorManager(), - response: new InterceptorManager() - }; -} - -/** - * Dispatch a request - * - * @param {Object} config The config specific for this request (merged with this.defaults) - */ -Axios.prototype.request = function request(configOrUrl, config) { - /*eslint no-param-reassign:0*/ - // Allow for axios('example/url'[, config]) a la fetch API - if (typeof configOrUrl === 'string') { - config = config || {}; - config.url = configOrUrl; - } else { - config = configOrUrl || {}; - } - - config = mergeConfig(this.defaults, config); - - // Set config.method - if (config.method) { - config.method = config.method.toLowerCase(); - } else if (this.defaults.method) { - config.method = this.defaults.method.toLowerCase(); - } else { - config.method = 'get'; - } - - var transitional = config.transitional; - - if (transitional !== undefined) { - validator.assertOptions(transitional, { - silentJSONParsing: validators.transitional(validators.boolean), - forcedJSONParsing: validators.transitional(validators.boolean), - clarifyTimeoutError: validators.transitional(validators.boolean) - }, false); - } - - // filter out skipped interceptors - var requestInterceptorChain = []; - var synchronousRequestInterceptors = true; - this.interceptors.request.forEach(function unshiftRequestInterceptors(interceptor) { - if (typeof interceptor.runWhen === 'function' && interceptor.runWhen(config) === false) { - return; - } - - synchronousRequestInterceptors = synchronousRequestInterceptors && interceptor.synchronous; - - requestInterceptorChain.unshift(interceptor.fulfilled, interceptor.rejected); - }); - - var responseInterceptorChain = []; - this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) { - responseInterceptorChain.push(interceptor.fulfilled, interceptor.rejected); - }); - - var promise; - - if (!synchronousRequestInterceptors) { - var chain = [dispatchRequest, undefined]; - - Array.prototype.unshift.apply(chain, requestInterceptorChain); - chain = chain.concat(responseInterceptorChain); - - promise = Promise.resolve(config); - while (chain.length) { - promise = promise.then(chain.shift(), chain.shift()); - } - - return promise; - } - - - var newConfig = config; - while (requestInterceptorChain.length) { - var onFulfilled = requestInterceptorChain.shift(); - var onRejected = requestInterceptorChain.shift(); - try { - newConfig = onFulfilled(newConfig); - } catch (error) { - onRejected(error); - break; - } - } - - try { - promise = dispatchRequest(newConfig); - } catch (error) { - return Promise.reject(error); - } - - while (responseInterceptorChain.length) { - promise = promise.then(responseInterceptorChain.shift(), responseInterceptorChain.shift()); - } - - return promise; -}; - -Axios.prototype.getUri = function getUri(config) { - config = mergeConfig(this.defaults, config); - var fullPath = buildFullPath(config.baseURL, config.url); - return buildURL(fullPath, config.params, config.paramsSerializer); -}; - -// Provide aliases for supported request methods -utils.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) { - /*eslint func-names:0*/ - Axios.prototype[method] = function(url, config) { - return this.request(mergeConfig(config || {}, { - method: method, - url: url, - data: (config || {}).data - })); - }; -}); - -utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { - /*eslint func-names:0*/ - - function generateHTTPMethod(isForm) { - return function httpMethod(url, data, config) { - return this.request(mergeConfig(config || {}, { - method: method, - headers: isForm ? { - 'Content-Type': 'multipart/form-data' - } : {}, - url: url, - data: data - })); - }; - } - - Axios.prototype[method] = generateHTTPMethod(); - - Axios.prototype[method + 'Form'] = generateHTTPMethod(true); -}); - -module.exports = Axios; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/AxiosError.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -/** - * Create an Error with the specified message, config, error code, request and response. - * - * @param {string} message The error message. - * @param {string} [code] The error code (for example, 'ECONNABORTED'). - * @param {Object} [config] The config. - * @param {Object} [request] The request. - * @param {Object} [response] The response. - * @returns {Error} The created error. - */ -function AxiosError(message, code, config, request, response) { - Error.call(this); - this.message = message; - this.name = 'AxiosError'; - code && (this.code = code); - config && (this.config = config); - request && (this.request = request); - response && (this.response = response); -} - -utils.inherits(AxiosError, Error, { - toJSON: function toJSON() { - return { - // Standard - message: this.message, - name: this.name, - // Microsoft - description: this.description, - number: this.number, - // Mozilla - fileName: this.fileName, - lineNumber: this.lineNumber, - columnNumber: this.columnNumber, - stack: this.stack, - // Axios - config: this.config, - code: this.code, - status: this.response && this.response.status ? this.response.status : null - }; - } -}); - -var prototype = AxiosError.prototype; -var descriptors = {}; - -[ - 'ERR_BAD_OPTION_VALUE', - 'ERR_BAD_OPTION', - 'ECONNABORTED', - 'ETIMEDOUT', - 'ERR_NETWORK', - 'ERR_FR_TOO_MANY_REDIRECTS', - 'ERR_DEPRECATED', - 'ERR_BAD_RESPONSE', - 'ERR_BAD_REQUEST', - 'ERR_CANCELED' -// eslint-disable-next-line func-names -].forEach(function(code) { - descriptors[code] = {value: code}; -}); - -Object.defineProperties(AxiosError, descriptors); -Object.defineProperty(prototype, 'isAxiosError', {value: true}); - -// eslint-disable-next-line func-names -AxiosError.from = function(error, code, config, request, response, customProps) { - var axiosError = Object.create(prototype); - - utils.toFlatObject(error, axiosError, function filter(obj) { - return obj !== Error.prototype; - }); - - AxiosError.call(axiosError, error.message, code, config, request, response); - - axiosError.name = error.name; - - customProps && Object.assign(axiosError, customProps); - - return axiosError; -}; - -module.exports = AxiosError; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/InterceptorManager.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -function InterceptorManager() { - this.handlers = []; -} - -/** - * Add a new interceptor to the stack - * - * @param {Function} fulfilled The function to handle `then` for a `Promise` - * @param {Function} rejected The function to handle `reject` for a `Promise` - * - * @return {Number} An ID used to remove interceptor later - */ -InterceptorManager.prototype.use = function use(fulfilled, rejected, options) { - this.handlers.push({ - fulfilled: fulfilled, - rejected: rejected, - synchronous: options ? options.synchronous : false, - runWhen: options ? options.runWhen : null - }); - return this.handlers.length - 1; -}; - -/** - * Remove an interceptor from the stack - * - * @param {Number} id The ID that was returned by `use` - */ -InterceptorManager.prototype.eject = function eject(id) { - if (this.handlers[id]) { - this.handlers[id] = null; - } -}; - -/** - * Iterate over all the registered interceptors - * - * This method is particularly useful for skipping over any - * interceptors that may have become `null` calling `eject`. - * - * @param {Function} fn The function to call for each interceptor - */ -InterceptorManager.prototype.forEach = function forEach(fn) { - utils.forEach(this.handlers, function forEachHandler(h) { - if (h !== null) { - fn(h); - } - }); -}; - -module.exports = InterceptorManager; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/buildFullPath.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var isAbsoluteURL = __webpack_require__("../../node_modules/axios/lib/helpers/isAbsoluteURL.js"); -var combineURLs = __webpack_require__("../../node_modules/axios/lib/helpers/combineURLs.js"); - -/** - * Creates a new URL by combining the baseURL with the requestedURL, - * only when the requestedURL is not already an absolute URL. - * If the requestURL is absolute, this function returns the requestedURL untouched. - * - * @param {string} baseURL The base URL - * @param {string} requestedURL Absolute or relative URL to combine - * @returns {string} The combined full path - */ -module.exports = function buildFullPath(baseURL, requestedURL) { - if (baseURL && !isAbsoluteURL(requestedURL)) { - return combineURLs(baseURL, requestedURL); - } - return requestedURL; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/dispatchRequest.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); -var transformData = __webpack_require__("../../node_modules/axios/lib/core/transformData.js"); -var isCancel = __webpack_require__("../../node_modules/axios/lib/cancel/isCancel.js"); -var defaults = __webpack_require__("../../node_modules/axios/lib/defaults/index.js"); -var CanceledError = __webpack_require__("../../node_modules/axios/lib/cancel/CanceledError.js"); - -/** - * Throws a `CanceledError` if cancellation has been requested. - */ -function throwIfCancellationRequested(config) { - if (config.cancelToken) { - config.cancelToken.throwIfRequested(); - } - - if (config.signal && config.signal.aborted) { - throw new CanceledError(); - } -} - -/** - * Dispatch a request to the server using the configured adapter. - * - * @param {object} config The config that is to be used for the request - * @returns {Promise} The Promise to be fulfilled - */ -module.exports = function dispatchRequest(config) { - throwIfCancellationRequested(config); - - // Ensure headers exist - config.headers = config.headers || {}; - - // Transform request data - config.data = transformData.call( - config, - config.data, - config.headers, - config.transformRequest - ); - - // Flatten headers - config.headers = utils.merge( - config.headers.common || {}, - config.headers[config.method] || {}, - config.headers - ); - - utils.forEach( - ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'], - function cleanHeaderConfig(method) { - delete config.headers[method]; - } - ); - - var adapter = config.adapter || defaults.adapter; - - return adapter(config).then(function onAdapterResolution(response) { - throwIfCancellationRequested(config); - - // Transform response data - response.data = transformData.call( - config, - response.data, - response.headers, - config.transformResponse - ); - - return response; - }, function onAdapterRejection(reason) { - if (!isCancel(reason)) { - throwIfCancellationRequested(config); - - // Transform response data - if (reason && reason.response) { - reason.response.data = transformData.call( - config, - reason.response.data, - reason.response.headers, - config.transformResponse - ); - } - } - - return Promise.reject(reason); - }); -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/mergeConfig.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -/** - * Config-specific merge-function which creates a new config-object - * by merging two configuration objects together. - * - * @param {Object} config1 - * @param {Object} config2 - * @returns {Object} New object resulting from merging config2 to config1 - */ -module.exports = function mergeConfig(config1, config2) { - // eslint-disable-next-line no-param-reassign - config2 = config2 || {}; - var config = {}; - - function getMergedValue(target, source) { - if (utils.isPlainObject(target) && utils.isPlainObject(source)) { - return utils.merge(target, source); - } else if (utils.isPlainObject(source)) { - return utils.merge({}, source); - } else if (utils.isArray(source)) { - return source.slice(); - } - return source; - } - - // eslint-disable-next-line consistent-return - function mergeDeepProperties(prop) { - if (!utils.isUndefined(config2[prop])) { - return getMergedValue(config1[prop], config2[prop]); - } else if (!utils.isUndefined(config1[prop])) { - return getMergedValue(undefined, config1[prop]); - } - } - - // eslint-disable-next-line consistent-return - function valueFromConfig2(prop) { - if (!utils.isUndefined(config2[prop])) { - return getMergedValue(undefined, config2[prop]); - } - } - - // eslint-disable-next-line consistent-return - function defaultToConfig2(prop) { - if (!utils.isUndefined(config2[prop])) { - return getMergedValue(undefined, config2[prop]); - } else if (!utils.isUndefined(config1[prop])) { - return getMergedValue(undefined, config1[prop]); - } - } - - // eslint-disable-next-line consistent-return - function mergeDirectKeys(prop) { - if (prop in config2) { - return getMergedValue(config1[prop], config2[prop]); - } else if (prop in config1) { - return getMergedValue(undefined, config1[prop]); - } - } - - var mergeMap = { - 'url': valueFromConfig2, - 'method': valueFromConfig2, - 'data': valueFromConfig2, - 'baseURL': defaultToConfig2, - 'transformRequest': defaultToConfig2, - 'transformResponse': defaultToConfig2, - 'paramsSerializer': defaultToConfig2, - 'timeout': defaultToConfig2, - 'timeoutMessage': defaultToConfig2, - 'withCredentials': defaultToConfig2, - 'adapter': defaultToConfig2, - 'responseType': defaultToConfig2, - 'xsrfCookieName': defaultToConfig2, - 'xsrfHeaderName': defaultToConfig2, - 'onUploadProgress': defaultToConfig2, - 'onDownloadProgress': defaultToConfig2, - 'decompress': defaultToConfig2, - 'maxContentLength': defaultToConfig2, - 'maxBodyLength': defaultToConfig2, - 'beforeRedirect': defaultToConfig2, - 'transport': defaultToConfig2, - 'httpAgent': defaultToConfig2, - 'httpsAgent': defaultToConfig2, - 'cancelToken': defaultToConfig2, - 'socketPath': defaultToConfig2, - 'responseEncoding': defaultToConfig2, - 'validateStatus': mergeDirectKeys - }; - - utils.forEach(Object.keys(config1).concat(Object.keys(config2)), function computeConfigValue(prop) { - var merge = mergeMap[prop] || mergeDeepProperties; - var configValue = merge(prop); - (utils.isUndefined(configValue) && merge !== mergeDirectKeys) || (config[prop] = configValue); - }); - - return config; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/settle.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var AxiosError = __webpack_require__("../../node_modules/axios/lib/core/AxiosError.js"); - -/** - * Resolve or reject a Promise based on response status. - * - * @param {Function} resolve A function that resolves the promise. - * @param {Function} reject A function that rejects the promise. - * @param {object} response The response. - */ -module.exports = function settle(resolve, reject, response) { - var validateStatus = response.config.validateStatus; - if (!response.status || !validateStatus || validateStatus(response.status)) { - resolve(response); - } else { - reject(new AxiosError( - 'Request failed with status code ' + response.status, - [AxiosError.ERR_BAD_REQUEST, AxiosError.ERR_BAD_RESPONSE][Math.floor(response.status / 100) - 4], - response.config, - response.request, - response - )); - } -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/core/transformData.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); -var defaults = __webpack_require__("../../node_modules/axios/lib/defaults/index.js"); - -/** - * Transform the data for a request or a response - * - * @param {Object|String} data The data to be transformed - * @param {Array} headers The headers for the request or response - * @param {Array|Function} fns A single function or Array of functions - * @returns {*} The resulting transformed data - */ -module.exports = function transformData(data, headers, fns) { - var context = this || defaults; - /*eslint no-param-reassign:0*/ - utils.forEach(fns, function transform(fn) { - data = fn.call(context, data, headers); - }); - - return data; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/defaults/env/FormData.js": -/***/ (function(module, exports, __webpack_require__) { - -// eslint-disable-next-line strict -module.exports = __webpack_require__("../../node_modules/form-data/lib/form_data.js"); - - -/***/ }), - -/***/ "../../node_modules/axios/lib/defaults/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); -var normalizeHeaderName = __webpack_require__("../../node_modules/axios/lib/helpers/normalizeHeaderName.js"); -var AxiosError = __webpack_require__("../../node_modules/axios/lib/core/AxiosError.js"); -var transitionalDefaults = __webpack_require__("../../node_modules/axios/lib/defaults/transitional.js"); -var toFormData = __webpack_require__("../../node_modules/axios/lib/helpers/toFormData.js"); - -var DEFAULT_CONTENT_TYPE = { - 'Content-Type': 'application/x-www-form-urlencoded' -}; - -function setContentTypeIfUnset(headers, value) { - if (!utils.isUndefined(headers) && utils.isUndefined(headers['Content-Type'])) { - headers['Content-Type'] = value; - } -} - -function getDefaultAdapter() { - var adapter; - if (typeof XMLHttpRequest !== 'undefined') { - // For browsers use XHR adapter - adapter = __webpack_require__("../../node_modules/axios/lib/adapters/xhr.js"); - } else if (typeof process !== 'undefined' && Object.prototype.toString.call(process) === '[object process]') { - // For node use HTTP adapter - adapter = __webpack_require__("../../node_modules/axios/lib/adapters/http.js"); - } - return adapter; -} - -function stringifySafely(rawValue, parser, encoder) { - if (utils.isString(rawValue)) { - try { - (parser || JSON.parse)(rawValue); - return utils.trim(rawValue); - } catch (e) { - if (e.name !== 'SyntaxError') { - throw e; - } - } - } - - return (encoder || JSON.stringify)(rawValue); -} - -var defaults = { - - transitional: transitionalDefaults, - - adapter: getDefaultAdapter(), - - transformRequest: [function transformRequest(data, headers) { - normalizeHeaderName(headers, 'Accept'); - normalizeHeaderName(headers, 'Content-Type'); - - if (utils.isFormData(data) || - utils.isArrayBuffer(data) || - utils.isBuffer(data) || - utils.isStream(data) || - utils.isFile(data) || - utils.isBlob(data) - ) { - return data; - } - if (utils.isArrayBufferView(data)) { - return data.buffer; - } - if (utils.isURLSearchParams(data)) { - setContentTypeIfUnset(headers, 'application/x-www-form-urlencoded;charset=utf-8'); - return data.toString(); - } - - var isObjectPayload = utils.isObject(data); - var contentType = headers && headers['Content-Type']; - - var isFileList; - - if ((isFileList = utils.isFileList(data)) || (isObjectPayload && contentType === 'multipart/form-data')) { - var _FormData = this.env && this.env.FormData; - return toFormData(isFileList ? {'files[]': data} : data, _FormData && new _FormData()); - } else if (isObjectPayload || contentType === 'application/json') { - setContentTypeIfUnset(headers, 'application/json'); - return stringifySafely(data); - } - - return data; - }], - - transformResponse: [function transformResponse(data) { - var transitional = this.transitional || defaults.transitional; - var silentJSONParsing = transitional && transitional.silentJSONParsing; - var forcedJSONParsing = transitional && transitional.forcedJSONParsing; - var strictJSONParsing = !silentJSONParsing && this.responseType === 'json'; - - if (strictJSONParsing || (forcedJSONParsing && utils.isString(data) && data.length)) { - try { - return JSON.parse(data); - } catch (e) { - if (strictJSONParsing) { - if (e.name === 'SyntaxError') { - throw AxiosError.from(e, AxiosError.ERR_BAD_RESPONSE, this, null, this.response); - } - throw e; - } - } - } - - return data; - }], - - /** - * A timeout in milliseconds to abort a request. If set to 0 (default) a - * timeout is not created. - */ - timeout: 0, - - xsrfCookieName: 'XSRF-TOKEN', - xsrfHeaderName: 'X-XSRF-TOKEN', - - maxContentLength: -1, - maxBodyLength: -1, - - env: { - FormData: __webpack_require__("../../node_modules/axios/lib/defaults/env/FormData.js") - }, - - validateStatus: function validateStatus(status) { - return status >= 200 && status < 300; - }, - - headers: { - common: { - 'Accept': 'application/json, text/plain, */*' - } - } -}; - -utils.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) { - defaults.headers[method] = {}; -}); - -utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { - defaults.headers[method] = utils.merge(DEFAULT_CONTENT_TYPE); -}); - -module.exports = defaults; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/defaults/transitional.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = { - silentJSONParsing: true, - forcedJSONParsing: true, - clarifyTimeoutError: false -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/env/data.js": -/***/ (function(module, exports) { - -module.exports = { - "version": "0.27.2" -}; - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/bind.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = function bind(fn, thisArg) { - return function wrap() { - var args = new Array(arguments.length); - for (var i = 0; i < args.length; i++) { - args[i] = arguments[i]; - } - return fn.apply(thisArg, args); - }; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/buildURL.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -function encode(val) { - return encodeURIComponent(val). - replace(/%3A/gi, ':'). - replace(/%24/g, '$'). - replace(/%2C/gi, ','). - replace(/%20/g, '+'). - replace(/%5B/gi, '['). - replace(/%5D/gi, ']'); -} - -/** - * Build a URL by appending params to the end - * - * @param {string} url The base of the url (e.g., http://www.google.com) - * @param {object} [params] The params to be appended - * @returns {string} The formatted url - */ -module.exports = function buildURL(url, params, paramsSerializer) { - /*eslint no-param-reassign:0*/ - if (!params) { - return url; - } - - var serializedParams; - if (paramsSerializer) { - serializedParams = paramsSerializer(params); - } else if (utils.isURLSearchParams(params)) { - serializedParams = params.toString(); - } else { - var parts = []; - - utils.forEach(params, function serialize(val, key) { - if (val === null || typeof val === 'undefined') { - return; - } - - if (utils.isArray(val)) { - key = key + '[]'; - } else { - val = [val]; - } - - utils.forEach(val, function parseValue(v) { - if (utils.isDate(v)) { - v = v.toISOString(); - } else if (utils.isObject(v)) { - v = JSON.stringify(v); - } - parts.push(encode(key) + '=' + encode(v)); - }); - }); - - serializedParams = parts.join('&'); - } - - if (serializedParams) { - var hashmarkIndex = url.indexOf('#'); - if (hashmarkIndex !== -1) { - url = url.slice(0, hashmarkIndex); - } - - url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams; - } - - return url; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/combineURLs.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -/** - * Creates a new URL by combining the specified URLs - * - * @param {string} baseURL The base URL - * @param {string} relativeURL The relative URL - * @returns {string} The combined URL - */ -module.exports = function combineURLs(baseURL, relativeURL) { - return relativeURL - ? baseURL.replace(/\/+$/, '') + '/' + relativeURL.replace(/^\/+/, '') - : baseURL; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/cookies.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -module.exports = ( - utils.isStandardBrowserEnv() ? - - // Standard browser envs support document.cookie - (function standardBrowserEnv() { - return { - write: function write(name, value, expires, path, domain, secure) { - var cookie = []; - cookie.push(name + '=' + encodeURIComponent(value)); - - if (utils.isNumber(expires)) { - cookie.push('expires=' + new Date(expires).toGMTString()); - } - - if (utils.isString(path)) { - cookie.push('path=' + path); - } - - if (utils.isString(domain)) { - cookie.push('domain=' + domain); - } - - if (secure === true) { - cookie.push('secure'); - } - - document.cookie = cookie.join('; '); - }, - - read: function read(name) { - var match = document.cookie.match(new RegExp('(^|;\\s*)(' + name + ')=([^;]*)')); - return (match ? decodeURIComponent(match[3]) : null); - }, - - remove: function remove(name) { - this.write(name, '', Date.now() - 86400000); - } - }; - })() : - - // Non standard browser env (web workers, react-native) lack needed support. - (function nonStandardBrowserEnv() { - return { - write: function write() {}, - read: function read() { return null; }, - remove: function remove() {} - }; - })() -); - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/isAbsoluteURL.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -/** - * Determines whether the specified URL is absolute - * - * @param {string} url The URL to test - * @returns {boolean} True if the specified URL is absolute, otherwise false - */ -module.exports = function isAbsoluteURL(url) { - // A URL is considered absolute if it begins with "://" or "//" (protocol-relative URL). - // RFC 3986 defines scheme name as a sequence of characters beginning with a letter and followed - // by any combination of letters, digits, plus, period, or hyphen. - return /^([a-z][a-z\d+\-.]*:)?\/\//i.test(url); -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/isAxiosError.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -/** - * Determines whether the payload is an error thrown by Axios - * - * @param {*} payload The value to test - * @returns {boolean} True if the payload is an error thrown by Axios, otherwise false - */ -module.exports = function isAxiosError(payload) { - return utils.isObject(payload) && (payload.isAxiosError === true); -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/isURLSameOrigin.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -module.exports = ( - utils.isStandardBrowserEnv() ? - - // Standard browser envs have full support of the APIs needed to test - // whether the request URL is of the same origin as current location. - (function standardBrowserEnv() { - var msie = /(msie|trident)/i.test(navigator.userAgent); - var urlParsingNode = document.createElement('a'); - var originURL; - - /** - * Parse a URL to discover it's components - * - * @param {String} url The URL to be parsed - * @returns {Object} - */ - function resolveURL(url) { - var href = url; - - if (msie) { - // IE needs attribute set twice to normalize properties - urlParsingNode.setAttribute('href', href); - href = urlParsingNode.href; - } - - urlParsingNode.setAttribute('href', href); - - // urlParsingNode provides the UrlUtils interface - http://url.spec.whatwg.org/#urlutils - return { - href: urlParsingNode.href, - protocol: urlParsingNode.protocol ? urlParsingNode.protocol.replace(/:$/, '') : '', - host: urlParsingNode.host, - search: urlParsingNode.search ? urlParsingNode.search.replace(/^\?/, '') : '', - hash: urlParsingNode.hash ? urlParsingNode.hash.replace(/^#/, '') : '', - hostname: urlParsingNode.hostname, - port: urlParsingNode.port, - pathname: (urlParsingNode.pathname.charAt(0) === '/') ? - urlParsingNode.pathname : - '/' + urlParsingNode.pathname - }; - } - - originURL = resolveURL(window.location.href); - - /** - * Determine if a URL shares the same origin as the current location - * - * @param {String} requestURL The URL to test - * @returns {boolean} True if URL shares the same origin, otherwise false - */ - return function isURLSameOrigin(requestURL) { - var parsed = (utils.isString(requestURL)) ? resolveURL(requestURL) : requestURL; - return (parsed.protocol === originURL.protocol && - parsed.host === originURL.host); - }; - })() : - - // Non standard browser envs (web workers, react-native) lack needed support. - (function nonStandardBrowserEnv() { - return function isURLSameOrigin() { - return true; - }; - })() -); - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/normalizeHeaderName.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -module.exports = function normalizeHeaderName(headers, normalizedName) { - utils.forEach(headers, function processHeader(value, name) { - if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) { - headers[normalizedName] = value; - delete headers[name]; - } - }); -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/parseHeaders.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -// Headers whose duplicates are ignored by node -// c.f. https://nodejs.org/api/http.html#http_message_headers -var ignoreDuplicateOf = [ - 'age', 'authorization', 'content-length', 'content-type', 'etag', - 'expires', 'from', 'host', 'if-modified-since', 'if-unmodified-since', - 'last-modified', 'location', 'max-forwards', 'proxy-authorization', - 'referer', 'retry-after', 'user-agent' -]; - -/** - * Parse headers into an object - * - * ``` - * Date: Wed, 27 Aug 2014 08:58:49 GMT - * Content-Type: application/json - * Connection: keep-alive - * Transfer-Encoding: chunked - * ``` - * - * @param {String} headers Headers needing to be parsed - * @returns {Object} Headers parsed into an object - */ -module.exports = function parseHeaders(headers) { - var parsed = {}; - var key; - var val; - var i; - - if (!headers) { return parsed; } - - utils.forEach(headers.split('\n'), function parser(line) { - i = line.indexOf(':'); - key = utils.trim(line.substr(0, i)).toLowerCase(); - val = utils.trim(line.substr(i + 1)); - - if (key) { - if (parsed[key] && ignoreDuplicateOf.indexOf(key) >= 0) { - return; - } - if (key === 'set-cookie') { - parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]); - } else { - parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val; - } - } - }); - - return parsed; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/parseProtocol.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = function parseProtocol(url) { - var match = /^([-+\w]{1,25})(:?\/\/|:)/.exec(url); - return match && match[1] || ''; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/spread.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -/** - * Syntactic sugar for invoking a function and expanding an array for arguments. - * - * Common use case would be to use `Function.prototype.apply`. - * - * ```js - * function f(x, y, z) {} - * var args = [1, 2, 3]; - * f.apply(null, args); - * ``` - * - * With `spread` this example can be re-written. - * - * ```js - * spread(function(x, y, z) {})([1, 2, 3]); - * ``` - * - * @param {Function} callback - * @returns {Function} - */ -module.exports = function spread(callback) { - return function wrap(arr) { - return callback.apply(null, arr); - }; -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/toFormData.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var utils = __webpack_require__("../../node_modules/axios/lib/utils.js"); - -/** - * Convert a data object to FormData - * @param {Object} obj - * @param {?Object} [formData] - * @returns {Object} - **/ - -function toFormData(obj, formData) { - // eslint-disable-next-line no-param-reassign - formData = formData || new FormData(); - - var stack = []; - - function convertValue(value) { - if (value === null) return ''; - - if (utils.isDate(value)) { - return value.toISOString(); - } - - if (utils.isArrayBuffer(value) || utils.isTypedArray(value)) { - return typeof Blob === 'function' ? new Blob([value]) : Buffer.from(value); - } - - return value; - } - - function build(data, parentKey) { - if (utils.isPlainObject(data) || utils.isArray(data)) { - if (stack.indexOf(data) !== -1) { - throw Error('Circular reference detected in ' + parentKey); - } - - stack.push(data); - - utils.forEach(data, function each(value, key) { - if (utils.isUndefined(value)) return; - var fullKey = parentKey ? parentKey + '.' + key : key; - var arr; - - if (value && !parentKey && typeof value === 'object') { - if (utils.endsWith(key, '{}')) { - // eslint-disable-next-line no-param-reassign - value = JSON.stringify(value); - } else if (utils.endsWith(key, '[]') && (arr = utils.toArray(value))) { - // eslint-disable-next-line func-names - arr.forEach(function(el) { - !utils.isUndefined(el) && formData.append(fullKey, convertValue(el)); - }); - return; - } - } - - build(value, fullKey); - }); - - stack.pop(); - } else { - formData.append(parentKey, convertValue(data)); - } - } - - build(obj); - - return formData; -} - -module.exports = toFormData; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/helpers/validator.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var VERSION = __webpack_require__("../../node_modules/axios/lib/env/data.js").version; -var AxiosError = __webpack_require__("../../node_modules/axios/lib/core/AxiosError.js"); - -var validators = {}; - -// eslint-disable-next-line func-names -['object', 'boolean', 'number', 'function', 'string', 'symbol'].forEach(function(type, i) { - validators[type] = function validator(thing) { - return typeof thing === type || 'a' + (i < 1 ? 'n ' : ' ') + type; - }; -}); - -var deprecatedWarnings = {}; - -/** - * Transitional option validator - * @param {function|boolean?} validator - set to false if the transitional option has been removed - * @param {string?} version - deprecated version / removed since version - * @param {string?} message - some message with additional info - * @returns {function} - */ -validators.transitional = function transitional(validator, version, message) { - function formatMessage(opt, desc) { - return '[Axios v' + VERSION + '] Transitional option \'' + opt + '\'' + desc + (message ? '. ' + message : ''); - } - - // eslint-disable-next-line func-names - return function(value, opt, opts) { - if (validator === false) { - throw new AxiosError( - formatMessage(opt, ' has been removed' + (version ? ' in ' + version : '')), - AxiosError.ERR_DEPRECATED - ); - } - - if (version && !deprecatedWarnings[opt]) { - deprecatedWarnings[opt] = true; - // eslint-disable-next-line no-console - console.warn( - formatMessage( - opt, - ' has been deprecated since v' + version + ' and will be removed in the near future' - ) - ); - } - - return validator ? validator(value, opt, opts) : true; - }; -}; - -/** - * Assert object's properties type - * @param {object} options - * @param {object} schema - * @param {boolean?} allowUnknown - */ - -function assertOptions(options, schema, allowUnknown) { - if (typeof options !== 'object') { - throw new AxiosError('options must be an object', AxiosError.ERR_BAD_OPTION_VALUE); - } - var keys = Object.keys(options); - var i = keys.length; - while (i-- > 0) { - var opt = keys[i]; - var validator = schema[opt]; - if (validator) { - var value = options[opt]; - var result = value === undefined || validator(value, opt, options); - if (result !== true) { - throw new AxiosError('option ' + opt + ' must be ' + result, AxiosError.ERR_BAD_OPTION_VALUE); - } - continue; - } - if (allowUnknown !== true) { - throw new AxiosError('Unknown option ' + opt, AxiosError.ERR_BAD_OPTION); - } - } -} - -module.exports = { - assertOptions: assertOptions, - validators: validators -}; - - -/***/ }), - -/***/ "../../node_modules/axios/lib/utils.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var bind = __webpack_require__("../../node_modules/axios/lib/helpers/bind.js"); - -// utils is a library of generic helper functions non-specific to axios - -var toString = Object.prototype.toString; - -// eslint-disable-next-line func-names -var kindOf = (function(cache) { - // eslint-disable-next-line func-names - return function(thing) { - var str = toString.call(thing); - return cache[str] || (cache[str] = str.slice(8, -1).toLowerCase()); - }; -})(Object.create(null)); - -function kindOfTest(type) { - type = type.toLowerCase(); - return function isKindOf(thing) { - return kindOf(thing) === type; - }; -} - -/** - * Determine if a value is an Array - * - * @param {Object} val The value to test - * @returns {boolean} True if value is an Array, otherwise false - */ -function isArray(val) { - return Array.isArray(val); -} - -/** - * Determine if a value is undefined - * - * @param {Object} val The value to test - * @returns {boolean} True if the value is undefined, otherwise false - */ -function isUndefined(val) { - return typeof val === 'undefined'; -} - -/** - * Determine if a value is a Buffer - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Buffer, otherwise false - */ -function isBuffer(val) { - return val !== null && !isUndefined(val) && val.constructor !== null && !isUndefined(val.constructor) - && typeof val.constructor.isBuffer === 'function' && val.constructor.isBuffer(val); -} - -/** - * Determine if a value is an ArrayBuffer - * - * @function - * @param {Object} val The value to test - * @returns {boolean} True if value is an ArrayBuffer, otherwise false - */ -var isArrayBuffer = kindOfTest('ArrayBuffer'); - - -/** - * Determine if a value is a view on an ArrayBuffer - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false - */ -function isArrayBufferView(val) { - var result; - if ((typeof ArrayBuffer !== 'undefined') && (ArrayBuffer.isView)) { - result = ArrayBuffer.isView(val); - } else { - result = (val) && (val.buffer) && (isArrayBuffer(val.buffer)); - } - return result; -} - -/** - * Determine if a value is a String - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a String, otherwise false - */ -function isString(val) { - return typeof val === 'string'; -} - -/** - * Determine if a value is a Number - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Number, otherwise false - */ -function isNumber(val) { - return typeof val === 'number'; -} - -/** - * Determine if a value is an Object - * - * @param {Object} val The value to test - * @returns {boolean} True if value is an Object, otherwise false - */ -function isObject(val) { - return val !== null && typeof val === 'object'; -} - -/** - * Determine if a value is a plain Object - * - * @param {Object} val The value to test - * @return {boolean} True if value is a plain Object, otherwise false - */ -function isPlainObject(val) { - if (kindOf(val) !== 'object') { - return false; - } - - var prototype = Object.getPrototypeOf(val); - return prototype === null || prototype === Object.prototype; -} - -/** - * Determine if a value is a Date - * - * @function - * @param {Object} val The value to test - * @returns {boolean} True if value is a Date, otherwise false - */ -var isDate = kindOfTest('Date'); - -/** - * Determine if a value is a File - * - * @function - * @param {Object} val The value to test - * @returns {boolean} True if value is a File, otherwise false - */ -var isFile = kindOfTest('File'); - -/** - * Determine if a value is a Blob - * - * @function - * @param {Object} val The value to test - * @returns {boolean} True if value is a Blob, otherwise false - */ -var isBlob = kindOfTest('Blob'); - -/** - * Determine if a value is a FileList - * - * @function - * @param {Object} val The value to test - * @returns {boolean} True if value is a File, otherwise false - */ -var isFileList = kindOfTest('FileList'); - -/** - * Determine if a value is a Function - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Function, otherwise false - */ -function isFunction(val) { - return toString.call(val) === '[object Function]'; -} - -/** - * Determine if a value is a Stream - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Stream, otherwise false - */ -function isStream(val) { - return isObject(val) && isFunction(val.pipe); -} - -/** - * Determine if a value is a FormData - * - * @param {Object} thing The value to test - * @returns {boolean} True if value is an FormData, otherwise false - */ -function isFormData(thing) { - var pattern = '[object FormData]'; - return thing && ( - (typeof FormData === 'function' && thing instanceof FormData) || - toString.call(thing) === pattern || - (isFunction(thing.toString) && thing.toString() === pattern) - ); -} - -/** - * Determine if a value is a URLSearchParams object - * @function - * @param {Object} val The value to test - * @returns {boolean} True if value is a URLSearchParams object, otherwise false - */ -var isURLSearchParams = kindOfTest('URLSearchParams'); - -/** - * Trim excess whitespace off the beginning and end of a string - * - * @param {String} str The String to trim - * @returns {String} The String freed of excess whitespace - */ -function trim(str) { - return str.trim ? str.trim() : str.replace(/^\s+|\s+$/g, ''); -} - -/** - * Determine if we're running in a standard browser environment - * - * This allows axios to run in a web worker, and react-native. - * Both environments support XMLHttpRequest, but not fully standard globals. - * - * web workers: - * typeof window -> undefined - * typeof document -> undefined - * - * react-native: - * navigator.product -> 'ReactNative' - * nativescript - * navigator.product -> 'NativeScript' or 'NS' - */ -function isStandardBrowserEnv() { - if (typeof navigator !== 'undefined' && (navigator.product === 'ReactNative' || - navigator.product === 'NativeScript' || - navigator.product === 'NS')) { - return false; - } - return ( - typeof window !== 'undefined' && - typeof document !== 'undefined' - ); -} - -/** - * Iterate over an Array or an Object invoking a function for each item. - * - * If `obj` is an Array callback will be called passing - * the value, index, and complete array for each item. - * - * If 'obj' is an Object callback will be called passing - * the value, key, and complete object for each property. - * - * @param {Object|Array} obj The object to iterate - * @param {Function} fn The callback to invoke for each item - */ -function forEach(obj, fn) { - // Don't bother if no value provided - if (obj === null || typeof obj === 'undefined') { - return; - } - - // Force an array if not already something iterable - if (typeof obj !== 'object') { - /*eslint no-param-reassign:0*/ - obj = [obj]; - } - - if (isArray(obj)) { - // Iterate over array values - for (var i = 0, l = obj.length; i < l; i++) { - fn.call(null, obj[i], i, obj); - } - } else { - // Iterate over object keys - for (var key in obj) { - if (Object.prototype.hasOwnProperty.call(obj, key)) { - fn.call(null, obj[key], key, obj); - } - } - } -} - -/** - * Accepts varargs expecting each argument to be an object, then - * immutably merges the properties of each object and returns result. - * - * When multiple objects contain the same key the later object in - * the arguments list will take precedence. - * - * Example: - * - * ```js - * var result = merge({foo: 123}, {foo: 456}); - * console.log(result.foo); // outputs 456 - * ``` - * - * @param {Object} obj1 Object to merge - * @returns {Object} Result of all merge properties - */ -function merge(/* obj1, obj2, obj3, ... */) { - var result = {}; - function assignValue(val, key) { - if (isPlainObject(result[key]) && isPlainObject(val)) { - result[key] = merge(result[key], val); - } else if (isPlainObject(val)) { - result[key] = merge({}, val); - } else if (isArray(val)) { - result[key] = val.slice(); - } else { - result[key] = val; - } - } - - for (var i = 0, l = arguments.length; i < l; i++) { - forEach(arguments[i], assignValue); - } - return result; -} - -/** - * Extends object a by mutably adding to it the properties of object b. - * - * @param {Object} a The object to be extended - * @param {Object} b The object to copy properties from - * @param {Object} thisArg The object to bind function to - * @return {Object} The resulting value of object a - */ -function extend(a, b, thisArg) { - forEach(b, function assignValue(val, key) { - if (thisArg && typeof val === 'function') { - a[key] = bind(val, thisArg); - } else { - a[key] = val; - } - }); - return a; -} - -/** - * Remove byte order marker. This catches EF BB BF (the UTF-8 BOM) - * - * @param {string} content with BOM - * @return {string} content value without BOM - */ -function stripBOM(content) { - if (content.charCodeAt(0) === 0xFEFF) { - content = content.slice(1); - } - return content; -} - -/** - * Inherit the prototype methods from one constructor into another - * @param {function} constructor - * @param {function} superConstructor - * @param {object} [props] - * @param {object} [descriptors] - */ - -function inherits(constructor, superConstructor, props, descriptors) { - constructor.prototype = Object.create(superConstructor.prototype, descriptors); - constructor.prototype.constructor = constructor; - props && Object.assign(constructor.prototype, props); -} - -/** - * Resolve object with deep prototype chain to a flat object - * @param {Object} sourceObj source object - * @param {Object} [destObj] - * @param {Function} [filter] - * @returns {Object} - */ - -function toFlatObject(sourceObj, destObj, filter) { - var props; - var i; - var prop; - var merged = {}; - - destObj = destObj || {}; - - do { - props = Object.getOwnPropertyNames(sourceObj); - i = props.length; - while (i-- > 0) { - prop = props[i]; - if (!merged[prop]) { - destObj[prop] = sourceObj[prop]; - merged[prop] = true; - } - } - sourceObj = Object.getPrototypeOf(sourceObj); - } while (sourceObj && (!filter || filter(sourceObj, destObj)) && sourceObj !== Object.prototype); - - return destObj; -} - -/* - * determines whether a string ends with the characters of a specified string - * @param {String} str - * @param {String} searchString - * @param {Number} [position= 0] - * @returns {boolean} - */ -function endsWith(str, searchString, position) { - str = String(str); - if (position === undefined || position > str.length) { - position = str.length; - } - position -= searchString.length; - var lastIndex = str.indexOf(searchString, position); - return lastIndex !== -1 && lastIndex === position; -} - - -/** - * Returns new array from array like object - * @param {*} [thing] - * @returns {Array} - */ -function toArray(thing) { - if (!thing) return null; - var i = thing.length; - if (isUndefined(i)) return null; - var arr = new Array(i); - while (i-- > 0) { - arr[i] = thing[i]; - } - return arr; -} - -// eslint-disable-next-line func-names -var isTypedArray = (function(TypedArray) { - // eslint-disable-next-line func-names - return function(thing) { - return TypedArray && thing instanceof TypedArray; - }; -})(typeof Uint8Array !== 'undefined' && Object.getPrototypeOf(Uint8Array)); - -module.exports = { - isArray: isArray, - isArrayBuffer: isArrayBuffer, - isBuffer: isBuffer, - isFormData: isFormData, - isArrayBufferView: isArrayBufferView, - isString: isString, - isNumber: isNumber, - isObject: isObject, - isPlainObject: isPlainObject, - isUndefined: isUndefined, - isDate: isDate, - isFile: isFile, - isBlob: isBlob, - isFunction: isFunction, - isStream: isStream, - isURLSearchParams: isURLSearchParams, - isStandardBrowserEnv: isStandardBrowserEnv, - forEach: forEach, - merge: merge, - extend: extend, - trim: trim, - stripBOM: stripBOM, - inherits: inherits, - toFlatObject: toFlatObject, - kindOf: kindOf, - kindOfTest: kindOfTest, - endsWith: endsWith, - toArray: toArray, - isTypedArray: isTypedArray, - isFileList: isFileList -}; - - -/***/ }), - -/***/ "../../node_modules/balanced-match/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = balanced; -function balanced(a, b, str) { - if (a instanceof RegExp) a = maybeMatch(a, str); - if (b instanceof RegExp) b = maybeMatch(b, str); - - var r = range(a, b, str); - - return r && { - start: r[0], - end: r[1], - pre: str.slice(0, r[0]), - body: str.slice(r[0] + a.length, r[1]), - post: str.slice(r[1] + b.length) - }; -} - -function maybeMatch(reg, str) { - var m = str.match(reg); - return m ? m[0] : null; -} - -balanced.range = range; -function range(a, b, str) { - var begs, beg, left, right, result; - var ai = str.indexOf(a); - var bi = str.indexOf(b, ai + 1); - var i = ai; - - if (ai >= 0 && bi > 0) { - begs = []; - left = str.length; - - while (i >= 0 && !result) { - if (i == ai) { - begs.push(i); - ai = str.indexOf(a, i + 1); - } else if (begs.length == 1) { - result = [ begs.pop(), bi ]; - } else { - beg = begs.pop(); - if (beg < left) { - left = beg; - right = bi; - } - - bi = str.indexOf(b, i + 1); - } - - i = ai < bi && ai >= 0 ? ai : bi; - } - - if (begs.length) { - result = [ left, right ]; - } - } - - return result; -} - - -/***/ }), - -/***/ "../../node_modules/brace-expansion/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var concatMap = __webpack_require__("../../node_modules/concat-map/index.js"); -var balanced = __webpack_require__("../../node_modules/balanced-match/index.js"); - -module.exports = expandTop; - -var escSlash = '\0SLASH'+Math.random()+'\0'; -var escOpen = '\0OPEN'+Math.random()+'\0'; -var escClose = '\0CLOSE'+Math.random()+'\0'; -var escComma = '\0COMMA'+Math.random()+'\0'; -var escPeriod = '\0PERIOD'+Math.random()+'\0'; - -function numeric(str) { - return parseInt(str, 10) == str - ? parseInt(str, 10) - : str.charCodeAt(0); -} - -function escapeBraces(str) { - return str.split('\\\\').join(escSlash) - .split('\\{').join(escOpen) - .split('\\}').join(escClose) - .split('\\,').join(escComma) - .split('\\.').join(escPeriod); -} - -function unescapeBraces(str) { - return str.split(escSlash).join('\\') - .split(escOpen).join('{') - .split(escClose).join('}') - .split(escComma).join(',') - .split(escPeriod).join('.'); -} - - -// Basically just str.split(","), but handling cases -// where we have nested braced sections, which should be -// treated as individual members, like {a,{b,c},d} -function parseCommaParts(str) { - if (!str) - return ['']; - - var parts = []; - var m = balanced('{', '}', str); - - if (!m) - return str.split(','); - - var pre = m.pre; - var body = m.body; - var post = m.post; - var p = pre.split(','); - - p[p.length-1] += '{' + body + '}'; - var postParts = parseCommaParts(post); - if (post.length) { - p[p.length-1] += postParts.shift(); - p.push.apply(p, postParts); - } - - parts.push.apply(parts, p); - - return parts; -} - -function expandTop(str) { - if (!str) - return []; - - // I don't know why Bash 4.3 does this, but it does. - // Anything starting with {} will have the first two bytes preserved - // but *only* at the top level, so {},a}b will not expand to anything, - // but a{},b}c will be expanded to [a}c,abc]. - // One could argue that this is a bug in Bash, but since the goal of - // this module is to match Bash's rules, we escape a leading {} - if (str.substr(0, 2) === '{}') { - str = '\\{\\}' + str.substr(2); - } - - return expand(escapeBraces(str), true).map(unescapeBraces); -} - -function identity(e) { - return e; -} - -function embrace(str) { - return '{' + str + '}'; -} -function isPadded(el) { - return /^-?0\d/.test(el); -} - -function lte(i, y) { - return i <= y; -} -function gte(i, y) { - return i >= y; -} - -function expand(str, isTop) { - var expansions = []; - - var m = balanced('{', '}', str); - if (!m || /\$$/.test(m.pre)) return [str]; - - var isNumericSequence = /^-?\d+\.\.-?\d+(?:\.\.-?\d+)?$/.test(m.body); - var isAlphaSequence = /^[a-zA-Z]\.\.[a-zA-Z](?:\.\.-?\d+)?$/.test(m.body); - var isSequence = isNumericSequence || isAlphaSequence; - var isOptions = m.body.indexOf(',') >= 0; - if (!isSequence && !isOptions) { - // {a},b} - if (m.post.match(/,.*\}/)) { - str = m.pre + '{' + m.body + escClose + m.post; - return expand(str); - } - return [str]; - } - - var n; - if (isSequence) { - n = m.body.split(/\.\./); - } else { - n = parseCommaParts(m.body); - if (n.length === 1) { - // x{{a,b}}y ==> x{a}y x{b}y - n = expand(n[0], false).map(embrace); - if (n.length === 1) { - var post = m.post.length - ? expand(m.post, false) - : ['']; - return post.map(function(p) { - return m.pre + n[0] + p; - }); - } - } - } - - // at this point, n is the parts, and we know it's not a comma set - // with a single entry. - - // no need to expand pre, since it is guaranteed to be free of brace-sets - var pre = m.pre; - var post = m.post.length - ? expand(m.post, false) - : ['']; - - var N; - - if (isSequence) { - var x = numeric(n[0]); - var y = numeric(n[1]); - var width = Math.max(n[0].length, n[1].length) - var incr = n.length == 3 - ? Math.abs(numeric(n[2])) - : 1; - var test = lte; - var reverse = y < x; - if (reverse) { - incr *= -1; - test = gte; - } - var pad = n.some(isPadded); - - N = []; - - for (var i = x; test(i, y); i += incr) { - var c; - if (isAlphaSequence) { - c = String.fromCharCode(i); - if (c === '\\') - c = ''; - } else { - c = String(i); - if (pad) { - var need = width - c.length; - if (need > 0) { - var z = new Array(need + 1).join('0'); - if (i < 0) - c = '-' + z + c.slice(1); - else - c = z + c; - } - } - } - N.push(c); - } - } else { - N = concatMap(n, function(el) { return expand(el, false) }); - } - - for (var j = 0; j < N.length; j++) { - for (var k = 0; k < post.length; k++) { - var expansion = pre + N[j] + post[k]; - if (!isTop || isSequence || expansion) - expansions.push(expansion); - } - } - - return expansions; -} - - - -/***/ }), - -/***/ "../../node_modules/braces/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const stringify = __webpack_require__("../../node_modules/braces/lib/stringify.js"); -const compile = __webpack_require__("../../node_modules/braces/lib/compile.js"); -const expand = __webpack_require__("../../node_modules/braces/lib/expand.js"); -const parse = __webpack_require__("../../node_modules/braces/lib/parse.js"); - -/** - * Expand the given pattern or create a regex-compatible string. - * - * ```js - * const braces = require('braces'); - * console.log(braces('{a,b,c}', { compile: true })); //=> ['(a|b|c)'] - * console.log(braces('{a,b,c}')); //=> ['a', 'b', 'c'] - * ``` - * @param {String} `str` - * @param {Object} `options` - * @return {String} - * @api public - */ - -const braces = (input, options = {}) => { - let output = []; - - if (Array.isArray(input)) { - for (let pattern of input) { - let result = braces.create(pattern, options); - if (Array.isArray(result)) { - output.push(...result); - } else { - output.push(result); - } - } - } else { - output = [].concat(braces.create(input, options)); - } - - if (options && options.expand === true && options.nodupes === true) { - output = [...new Set(output)]; - } - return output; -}; - -/** - * Parse the given `str` with the given `options`. - * - * ```js - * // braces.parse(pattern, [, options]); - * const ast = braces.parse('a/{b,c}/d'); - * console.log(ast); - * ``` - * @param {String} pattern Brace pattern to parse - * @param {Object} options - * @return {Object} Returns an AST - * @api public - */ - -braces.parse = (input, options = {}) => parse(input, options); - -/** - * Creates a braces string from an AST, or an AST node. - * - * ```js - * const braces = require('braces'); - * let ast = braces.parse('foo/{a,b}/bar'); - * console.log(stringify(ast.nodes[2])); //=> '{a,b}' - * ``` - * @param {String} `input` Brace pattern or AST. - * @param {Object} `options` - * @return {Array} Returns an array of expanded values. - * @api public - */ - -braces.stringify = (input, options = {}) => { - if (typeof input === 'string') { - return stringify(braces.parse(input, options), options); - } - return stringify(input, options); -}; - -/** - * Compiles a brace pattern into a regex-compatible, optimized string. - * This method is called by the main [braces](#braces) function by default. - * - * ```js - * const braces = require('braces'); - * console.log(braces.compile('a/{b,c}/d')); - * //=> ['a/(b|c)/d'] - * ``` - * @param {String} `input` Brace pattern or AST. - * @param {Object} `options` - * @return {Array} Returns an array of expanded values. - * @api public - */ - -braces.compile = (input, options = {}) => { - if (typeof input === 'string') { - input = braces.parse(input, options); - } - return compile(input, options); -}; - -/** - * Expands a brace pattern into an array. This method is called by the - * main [braces](#braces) function when `options.expand` is true. Before - * using this method it's recommended that you read the [performance notes](#performance)) - * and advantages of using [.compile](#compile) instead. - * - * ```js - * const braces = require('braces'); - * console.log(braces.expand('a/{b,c}/d')); - * //=> ['a/b/d', 'a/c/d']; - * ``` - * @param {String} `pattern` Brace pattern - * @param {Object} `options` - * @return {Array} Returns an array of expanded values. - * @api public - */ - -braces.expand = (input, options = {}) => { - if (typeof input === 'string') { - input = braces.parse(input, options); - } - - let result = expand(input, options); - - // filter out empty strings if specified - if (options.noempty === true) { - result = result.filter(Boolean); - } - - // filter out duplicates if specified - if (options.nodupes === true) { - result = [...new Set(result)]; - } - - return result; -}; - -/** - * Processes a brace pattern and returns either an expanded array - * (if `options.expand` is true), a highly optimized regex-compatible string. - * This method is called by the main [braces](#braces) function. - * - * ```js - * const braces = require('braces'); - * console.log(braces.create('user-{200..300}/project-{a,b,c}-{1..10}')) - * //=> 'user-(20[0-9]|2[1-9][0-9]|300)/project-(a|b|c)-([1-9]|10)' - * ``` - * @param {String} `pattern` Brace pattern - * @param {Object} `options` - * @return {Array} Returns an array of expanded values. - * @api public - */ - -braces.create = (input, options = {}) => { - if (input === '' || input.length < 3) { - return [input]; - } - - return options.expand !== true - ? braces.compile(input, options) - : braces.expand(input, options); -}; - -/** - * Expose "braces" - */ - -module.exports = braces; - - -/***/ }), - -/***/ "../../node_modules/braces/lib/compile.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const fill = __webpack_require__("../../node_modules/fill-range/index.js"); -const utils = __webpack_require__("../../node_modules/braces/lib/utils.js"); - -const compile = (ast, options = {}) => { - let walk = (node, parent = {}) => { - let invalidBlock = utils.isInvalidBrace(parent); - let invalidNode = node.invalid === true && options.escapeInvalid === true; - let invalid = invalidBlock === true || invalidNode === true; - let prefix = options.escapeInvalid === true ? '\\' : ''; - let output = ''; - - if (node.isOpen === true) { - return prefix + node.value; - } - if (node.isClose === true) { - return prefix + node.value; - } - - if (node.type === 'open') { - return invalid ? (prefix + node.value) : '('; - } - - if (node.type === 'close') { - return invalid ? (prefix + node.value) : ')'; - } - - if (node.type === 'comma') { - return node.prev.type === 'comma' ? '' : (invalid ? node.value : '|'); - } - - if (node.value) { - return node.value; - } - - if (node.nodes && node.ranges > 0) { - let args = utils.reduce(node.nodes); - let range = fill(...args, { ...options, wrap: false, toRegex: true }); - - if (range.length !== 0) { - return args.length > 1 && range.length > 1 ? `(${range})` : range; - } - } - - if (node.nodes) { - for (let child of node.nodes) { - output += walk(child, node); - } - } - return output; - }; - - return walk(ast); -}; - -module.exports = compile; - - -/***/ }), - -/***/ "../../node_modules/braces/lib/constants.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = { - MAX_LENGTH: 1024 * 64, - - // Digits - CHAR_0: '0', /* 0 */ - CHAR_9: '9', /* 9 */ - - // Alphabet chars. - CHAR_UPPERCASE_A: 'A', /* A */ - CHAR_LOWERCASE_A: 'a', /* a */ - CHAR_UPPERCASE_Z: 'Z', /* Z */ - CHAR_LOWERCASE_Z: 'z', /* z */ - - CHAR_LEFT_PARENTHESES: '(', /* ( */ - CHAR_RIGHT_PARENTHESES: ')', /* ) */ - - CHAR_ASTERISK: '*', /* * */ - - // Non-alphabetic chars. - CHAR_AMPERSAND: '&', /* & */ - CHAR_AT: '@', /* @ */ - CHAR_BACKSLASH: '\\', /* \ */ - CHAR_BACKTICK: '`', /* ` */ - CHAR_CARRIAGE_RETURN: '\r', /* \r */ - CHAR_CIRCUMFLEX_ACCENT: '^', /* ^ */ - CHAR_COLON: ':', /* : */ - CHAR_COMMA: ',', /* , */ - CHAR_DOLLAR: '$', /* . */ - CHAR_DOT: '.', /* . */ - CHAR_DOUBLE_QUOTE: '"', /* " */ - CHAR_EQUAL: '=', /* = */ - CHAR_EXCLAMATION_MARK: '!', /* ! */ - CHAR_FORM_FEED: '\f', /* \f */ - CHAR_FORWARD_SLASH: '/', /* / */ - CHAR_HASH: '#', /* # */ - CHAR_HYPHEN_MINUS: '-', /* - */ - CHAR_LEFT_ANGLE_BRACKET: '<', /* < */ - CHAR_LEFT_CURLY_BRACE: '{', /* { */ - CHAR_LEFT_SQUARE_BRACKET: '[', /* [ */ - CHAR_LINE_FEED: '\n', /* \n */ - CHAR_NO_BREAK_SPACE: '\u00A0', /* \u00A0 */ - CHAR_PERCENT: '%', /* % */ - CHAR_PLUS: '+', /* + */ - CHAR_QUESTION_MARK: '?', /* ? */ - CHAR_RIGHT_ANGLE_BRACKET: '>', /* > */ - CHAR_RIGHT_CURLY_BRACE: '}', /* } */ - CHAR_RIGHT_SQUARE_BRACKET: ']', /* ] */ - CHAR_SEMICOLON: ';', /* ; */ - CHAR_SINGLE_QUOTE: '\'', /* ' */ - CHAR_SPACE: ' ', /* */ - CHAR_TAB: '\t', /* \t */ - CHAR_UNDERSCORE: '_', /* _ */ - CHAR_VERTICAL_LINE: '|', /* | */ - CHAR_ZERO_WIDTH_NOBREAK_SPACE: '\uFEFF' /* \uFEFF */ -}; - - -/***/ }), - -/***/ "../../node_modules/braces/lib/expand.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const fill = __webpack_require__("../../node_modules/fill-range/index.js"); -const stringify = __webpack_require__("../../node_modules/braces/lib/stringify.js"); -const utils = __webpack_require__("../../node_modules/braces/lib/utils.js"); - -const append = (queue = '', stash = '', enclose = false) => { - let result = []; - - queue = [].concat(queue); - stash = [].concat(stash); - - if (!stash.length) return queue; - if (!queue.length) { - return enclose ? utils.flatten(stash).map(ele => `{${ele}}`) : stash; - } - - for (let item of queue) { - if (Array.isArray(item)) { - for (let value of item) { - result.push(append(value, stash, enclose)); - } - } else { - for (let ele of stash) { - if (enclose === true && typeof ele === 'string') ele = `{${ele}}`; - result.push(Array.isArray(ele) ? append(item, ele, enclose) : (item + ele)); - } - } - } - return utils.flatten(result); -}; - -const expand = (ast, options = {}) => { - let rangeLimit = options.rangeLimit === void 0 ? 1000 : options.rangeLimit; - - let walk = (node, parent = {}) => { - node.queue = []; - - let p = parent; - let q = parent.queue; - - while (p.type !== 'brace' && p.type !== 'root' && p.parent) { - p = p.parent; - q = p.queue; - } - - if (node.invalid || node.dollar) { - q.push(append(q.pop(), stringify(node, options))); - return; - } - - if (node.type === 'brace' && node.invalid !== true && node.nodes.length === 2) { - q.push(append(q.pop(), ['{}'])); - return; - } - - if (node.nodes && node.ranges > 0) { - let args = utils.reduce(node.nodes); - - if (utils.exceedsLimit(...args, options.step, rangeLimit)) { - throw new RangeError('expanded array length exceeds range limit. Use options.rangeLimit to increase or disable the limit.'); - } - - let range = fill(...args, options); - if (range.length === 0) { - range = stringify(node, options); - } - - q.push(append(q.pop(), range)); - node.nodes = []; - return; - } - - let enclose = utils.encloseBrace(node); - let queue = node.queue; - let block = node; - - while (block.type !== 'brace' && block.type !== 'root' && block.parent) { - block = block.parent; - queue = block.queue; - } - - for (let i = 0; i < node.nodes.length; i++) { - let child = node.nodes[i]; - - if (child.type === 'comma' && node.type === 'brace') { - if (i === 1) queue.push(''); - queue.push(''); - continue; - } - - if (child.type === 'close') { - q.push(append(q.pop(), queue, enclose)); - continue; - } - - if (child.value && child.type !== 'open') { - queue.push(append(queue.pop(), child.value)); - continue; - } - - if (child.nodes) { - walk(child, node); - } - } - - return queue; - }; - - return utils.flatten(walk(ast)); -}; - -module.exports = expand; - - -/***/ }), - -/***/ "../../node_modules/braces/lib/parse.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const stringify = __webpack_require__("../../node_modules/braces/lib/stringify.js"); - -/** - * Constants - */ - -const { - MAX_LENGTH, - CHAR_BACKSLASH, /* \ */ - CHAR_BACKTICK, /* ` */ - CHAR_COMMA, /* , */ - CHAR_DOT, /* . */ - CHAR_LEFT_PARENTHESES, /* ( */ - CHAR_RIGHT_PARENTHESES, /* ) */ - CHAR_LEFT_CURLY_BRACE, /* { */ - CHAR_RIGHT_CURLY_BRACE, /* } */ - CHAR_LEFT_SQUARE_BRACKET, /* [ */ - CHAR_RIGHT_SQUARE_BRACKET, /* ] */ - CHAR_DOUBLE_QUOTE, /* " */ - CHAR_SINGLE_QUOTE, /* ' */ - CHAR_NO_BREAK_SPACE, - CHAR_ZERO_WIDTH_NOBREAK_SPACE -} = __webpack_require__("../../node_modules/braces/lib/constants.js"); - -/** - * parse - */ - -const parse = (input, options = {}) => { - if (typeof input !== 'string') { - throw new TypeError('Expected a string'); - } - - let opts = options || {}; - let max = typeof opts.maxLength === 'number' ? Math.min(MAX_LENGTH, opts.maxLength) : MAX_LENGTH; - if (input.length > max) { - throw new SyntaxError(`Input length (${input.length}), exceeds max characters (${max})`); - } - - let ast = { type: 'root', input, nodes: [] }; - let stack = [ast]; - let block = ast; - let prev = ast; - let brackets = 0; - let length = input.length; - let index = 0; - let depth = 0; - let value; - let memo = {}; - - /** - * Helpers - */ - - const advance = () => input[index++]; - const push = node => { - if (node.type === 'text' && prev.type === 'dot') { - prev.type = 'text'; - } - - if (prev && prev.type === 'text' && node.type === 'text') { - prev.value += node.value; - return; - } - - block.nodes.push(node); - node.parent = block; - node.prev = prev; - prev = node; - return node; - }; - - push({ type: 'bos' }); - - while (index < length) { - block = stack[stack.length - 1]; - value = advance(); - - /** - * Invalid chars - */ - - if (value === CHAR_ZERO_WIDTH_NOBREAK_SPACE || value === CHAR_NO_BREAK_SPACE) { - continue; - } - - /** - * Escaped chars - */ - - if (value === CHAR_BACKSLASH) { - push({ type: 'text', value: (options.keepEscaping ? value : '') + advance() }); - continue; - } - - /** - * Right square bracket (literal): ']' - */ - - if (value === CHAR_RIGHT_SQUARE_BRACKET) { - push({ type: 'text', value: '\\' + value }); - continue; - } - - /** - * Left square bracket: '[' - */ - - if (value === CHAR_LEFT_SQUARE_BRACKET) { - brackets++; - - let closed = true; - let next; - - while (index < length && (next = advance())) { - value += next; - - if (next === CHAR_LEFT_SQUARE_BRACKET) { - brackets++; - continue; - } - - if (next === CHAR_BACKSLASH) { - value += advance(); - continue; - } - - if (next === CHAR_RIGHT_SQUARE_BRACKET) { - brackets--; - - if (brackets === 0) { - break; - } - } - } - - push({ type: 'text', value }); - continue; - } - - /** - * Parentheses - */ - - if (value === CHAR_LEFT_PARENTHESES) { - block = push({ type: 'paren', nodes: [] }); - stack.push(block); - push({ type: 'text', value }); - continue; - } - - if (value === CHAR_RIGHT_PARENTHESES) { - if (block.type !== 'paren') { - push({ type: 'text', value }); - continue; - } - block = stack.pop(); - push({ type: 'text', value }); - block = stack[stack.length - 1]; - continue; - } - - /** - * Quotes: '|"|` - */ - - if (value === CHAR_DOUBLE_QUOTE || value === CHAR_SINGLE_QUOTE || value === CHAR_BACKTICK) { - let open = value; - let next; - - if (options.keepQuotes !== true) { - value = ''; - } - - while (index < length && (next = advance())) { - if (next === CHAR_BACKSLASH) { - value += next + advance(); - continue; - } - - if (next === open) { - if (options.keepQuotes === true) value += next; - break; - } - - value += next; - } - - push({ type: 'text', value }); - continue; - } - - /** - * Left curly brace: '{' - */ - - if (value === CHAR_LEFT_CURLY_BRACE) { - depth++; - - let dollar = prev.value && prev.value.slice(-1) === '$' || block.dollar === true; - let brace = { - type: 'brace', - open: true, - close: false, - dollar, - depth, - commas: 0, - ranges: 0, - nodes: [] - }; - - block = push(brace); - stack.push(block); - push({ type: 'open', value }); - continue; - } - - /** - * Right curly brace: '}' - */ - - if (value === CHAR_RIGHT_CURLY_BRACE) { - if (block.type !== 'brace') { - push({ type: 'text', value }); - continue; - } - - let type = 'close'; - block = stack.pop(); - block.close = true; - - push({ type, value }); - depth--; - - block = stack[stack.length - 1]; - continue; - } - - /** - * Comma: ',' - */ - - if (value === CHAR_COMMA && depth > 0) { - if (block.ranges > 0) { - block.ranges = 0; - let open = block.nodes.shift(); - block.nodes = [open, { type: 'text', value: stringify(block) }]; - } - - push({ type: 'comma', value }); - block.commas++; - continue; - } - - /** - * Dot: '.' - */ - - if (value === CHAR_DOT && depth > 0 && block.commas === 0) { - let siblings = block.nodes; - - if (depth === 0 || siblings.length === 0) { - push({ type: 'text', value }); - continue; - } - - if (prev.type === 'dot') { - block.range = []; - prev.value += value; - prev.type = 'range'; - - if (block.nodes.length !== 3 && block.nodes.length !== 5) { - block.invalid = true; - block.ranges = 0; - prev.type = 'text'; - continue; - } - - block.ranges++; - block.args = []; - continue; - } - - if (prev.type === 'range') { - siblings.pop(); - - let before = siblings[siblings.length - 1]; - before.value += prev.value + value; - prev = before; - block.ranges--; - continue; - } - - push({ type: 'dot', value }); - continue; - } - - /** - * Text - */ - - push({ type: 'text', value }); - } - - // Mark imbalanced braces and brackets as invalid - do { - block = stack.pop(); - - if (block.type !== 'root') { - block.nodes.forEach(node => { - if (!node.nodes) { - if (node.type === 'open') node.isOpen = true; - if (node.type === 'close') node.isClose = true; - if (!node.nodes) node.type = 'text'; - node.invalid = true; - } - }); - - // get the location of the block on parent.nodes (block's siblings) - let parent = stack[stack.length - 1]; - let index = parent.nodes.indexOf(block); - // replace the (invalid) block with it's nodes - parent.nodes.splice(index, 1, ...block.nodes); - } - } while (stack.length > 0); - - push({ type: 'eos' }); - return ast; -}; - -module.exports = parse; - - -/***/ }), - -/***/ "../../node_modules/braces/lib/stringify.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const utils = __webpack_require__("../../node_modules/braces/lib/utils.js"); - -module.exports = (ast, options = {}) => { - let stringify = (node, parent = {}) => { - let invalidBlock = options.escapeInvalid && utils.isInvalidBrace(parent); - let invalidNode = node.invalid === true && options.escapeInvalid === true; - let output = ''; - - if (node.value) { - if ((invalidBlock || invalidNode) && utils.isOpenOrClose(node)) { - return '\\' + node.value; - } - return node.value; - } - - if (node.value) { - return node.value; - } - - if (node.nodes) { - for (let child of node.nodes) { - output += stringify(child); - } - } - return output; - }; - - return stringify(ast); -}; - - - -/***/ }), - -/***/ "../../node_modules/braces/lib/utils.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -exports.isInteger = num => { - if (typeof num === 'number') { - return Number.isInteger(num); - } - if (typeof num === 'string' && num.trim() !== '') { - return Number.isInteger(Number(num)); - } - return false; -}; - -/** - * Find a node of the given type - */ - -exports.find = (node, type) => node.nodes.find(node => node.type === type); - -/** - * Find a node of the given type - */ - -exports.exceedsLimit = (min, max, step = 1, limit) => { - if (limit === false) return false; - if (!exports.isInteger(min) || !exports.isInteger(max)) return false; - return ((Number(max) - Number(min)) / Number(step)) >= limit; -}; - -/** - * Escape the given node with '\\' before node.value - */ - -exports.escapeNode = (block, n = 0, type) => { - let node = block.nodes[n]; - if (!node) return; - - if ((type && node.type === type) || node.type === 'open' || node.type === 'close') { - if (node.escaped !== true) { - node.value = '\\' + node.value; - node.escaped = true; - } - } -}; - -/** - * Returns true if the given brace node should be enclosed in literal braces - */ - -exports.encloseBrace = node => { - if (node.type !== 'brace') return false; - if ((node.commas >> 0 + node.ranges >> 0) === 0) { - node.invalid = true; - return true; - } - return false; -}; - -/** - * Returns true if a brace node is invalid. - */ - -exports.isInvalidBrace = block => { - if (block.type !== 'brace') return false; - if (block.invalid === true || block.dollar) return true; - if ((block.commas >> 0 + block.ranges >> 0) === 0) { - block.invalid = true; - return true; - } - if (block.open !== true || block.close !== true) { - block.invalid = true; - return true; - } - return false; -}; - -/** - * Returns true if a node is an open or close node - */ - -exports.isOpenOrClose = node => { - if (node.type === 'open' || node.type === 'close') { - return true; - } - return node.open === true || node.close === true; -}; - -/** - * Reduce an array of text nodes. - */ - -exports.reduce = nodes => nodes.reduce((acc, node) => { - if (node.type === 'text') acc.push(node.value); - if (node.type === 'range') node.type = 'text'; - return acc; -}, []); - -/** - * Flatten an array - */ - -exports.flatten = (...args) => { - const result = []; - const flat = arr => { - for (let i = 0; i < arr.length; i++) { - let ele = arr[i]; - Array.isArray(ele) ? flat(ele, result) : ele !== void 0 && result.push(ele); - } - return result; - }; - flat(args); - return result; -}; - - -/***/ }), - -/***/ "../../node_modules/chalk/source/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const ansiStyles = __webpack_require__("../../node_modules/ansi-styles/index.js"); -const {stdout: stdoutColor, stderr: stderrColor} = __webpack_require__("../../node_modules/supports-color/index.js"); -const { - stringReplaceAll, - stringEncaseCRLFWithFirstIndex -} = __webpack_require__("../../node_modules/chalk/source/util.js"); - -const {isArray} = Array; - -// `supportsColor.level` → `ansiStyles.color[name]` mapping -const levelMapping = [ - 'ansi', - 'ansi', - 'ansi256', - 'ansi16m' -]; - -const styles = Object.create(null); - -const applyOptions = (object, options = {}) => { - if (options.level && !(Number.isInteger(options.level) && options.level >= 0 && options.level <= 3)) { - throw new Error('The `level` option should be an integer from 0 to 3'); - } - - // Detect level if not set manually - const colorLevel = stdoutColor ? stdoutColor.level : 0; - object.level = options.level === undefined ? colorLevel : options.level; -}; - -class ChalkClass { - constructor(options) { - // eslint-disable-next-line no-constructor-return - return chalkFactory(options); - } -} - -const chalkFactory = options => { - const chalk = {}; - applyOptions(chalk, options); - - chalk.template = (...arguments_) => chalkTag(chalk.template, ...arguments_); - - Object.setPrototypeOf(chalk, Chalk.prototype); - Object.setPrototypeOf(chalk.template, chalk); - - chalk.template.constructor = () => { - throw new Error('`chalk.constructor()` is deprecated. Use `new chalk.Instance()` instead.'); - }; - - chalk.template.Instance = ChalkClass; - - return chalk.template; -}; - -function Chalk(options) { - return chalkFactory(options); -} - -for (const [styleName, style] of Object.entries(ansiStyles)) { - styles[styleName] = { - get() { - const builder = createBuilder(this, createStyler(style.open, style.close, this._styler), this._isEmpty); - Object.defineProperty(this, styleName, {value: builder}); - return builder; - } - }; -} - -styles.visible = { - get() { - const builder = createBuilder(this, this._styler, true); - Object.defineProperty(this, 'visible', {value: builder}); - return builder; - } -}; - -const usedModels = ['rgb', 'hex', 'keyword', 'hsl', 'hsv', 'hwb', 'ansi', 'ansi256']; - -for (const model of usedModels) { - styles[model] = { - get() { - const {level} = this; - return function (...arguments_) { - const styler = createStyler(ansiStyles.color[levelMapping[level]][model](...arguments_), ansiStyles.color.close, this._styler); - return createBuilder(this, styler, this._isEmpty); - }; - } - }; -} - -for (const model of usedModels) { - const bgModel = 'bg' + model[0].toUpperCase() + model.slice(1); - styles[bgModel] = { - get() { - const {level} = this; - return function (...arguments_) { - const styler = createStyler(ansiStyles.bgColor[levelMapping[level]][model](...arguments_), ansiStyles.bgColor.close, this._styler); - return createBuilder(this, styler, this._isEmpty); - }; - } - }; -} - -const proto = Object.defineProperties(() => {}, { - ...styles, - level: { - enumerable: true, - get() { - return this._generator.level; - }, - set(level) { - this._generator.level = level; - } - } -}); - -const createStyler = (open, close, parent) => { - let openAll; - let closeAll; - if (parent === undefined) { - openAll = open; - closeAll = close; - } else { - openAll = parent.openAll + open; - closeAll = close + parent.closeAll; - } - - return { - open, - close, - openAll, - closeAll, - parent - }; -}; - -const createBuilder = (self, _styler, _isEmpty) => { - const builder = (...arguments_) => { - if (isArray(arguments_[0]) && isArray(arguments_[0].raw)) { - // Called as a template literal, for example: chalk.red`2 + 3 = {bold ${2+3}}` - return applyStyle(builder, chalkTag(builder, ...arguments_)); - } - - // Single argument is hot path, implicit coercion is faster than anything - // eslint-disable-next-line no-implicit-coercion - return applyStyle(builder, (arguments_.length === 1) ? ('' + arguments_[0]) : arguments_.join(' ')); - }; - - // We alter the prototype because we must return a function, but there is - // no way to create a function with a different prototype - Object.setPrototypeOf(builder, proto); - - builder._generator = self; - builder._styler = _styler; - builder._isEmpty = _isEmpty; - - return builder; -}; - -const applyStyle = (self, string) => { - if (self.level <= 0 || !string) { - return self._isEmpty ? '' : string; - } - - let styler = self._styler; - - if (styler === undefined) { - return string; - } - - const {openAll, closeAll} = styler; - if (string.indexOf('\u001B') !== -1) { - while (styler !== undefined) { - // Replace any instances already present with a re-opening code - // otherwise only the part of the string until said closing code - // will be colored, and the rest will simply be 'plain'. - string = stringReplaceAll(string, styler.close, styler.open); - - styler = styler.parent; - } - } - - // We can move both next actions out of loop, because remaining actions in loop won't have - // any/visible effect on parts we add here. Close the styling before a linebreak and reopen - // after next line to fix a bleed issue on macOS: https://github.com/chalk/chalk/pull/92 - const lfIndex = string.indexOf('\n'); - if (lfIndex !== -1) { - string = stringEncaseCRLFWithFirstIndex(string, closeAll, openAll, lfIndex); - } - - return openAll + string + closeAll; -}; - -let template; -const chalkTag = (chalk, ...strings) => { - const [firstString] = strings; - - if (!isArray(firstString) || !isArray(firstString.raw)) { - // If chalk() was called by itself or with a string, - // return the string itself as a string. - return strings.join(' '); - } - - const arguments_ = strings.slice(1); - const parts = [firstString.raw[0]]; - - for (let i = 1; i < firstString.length; i++) { - parts.push( - String(arguments_[i - 1]).replace(/[{}\\]/g, '\\$&'), - String(firstString.raw[i]) - ); - } - - if (template === undefined) { - template = __webpack_require__("../../node_modules/chalk/source/templates.js"); - } - - return template(chalk, parts.join('')); -}; - -Object.defineProperties(Chalk.prototype, styles); - -const chalk = Chalk(); // eslint-disable-line new-cap -chalk.supportsColor = stdoutColor; -chalk.stderr = Chalk({level: stderrColor ? stderrColor.level : 0}); // eslint-disable-line new-cap -chalk.stderr.supportsColor = stderrColor; - -module.exports = chalk; - - -/***/ }), - -/***/ "../../node_modules/chalk/source/templates.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const TEMPLATE_REGEX = /(?:\\(u(?:[a-f\d]{4}|\{[a-f\d]{1,6}\})|x[a-f\d]{2}|.))|(?:\{(~)?(\w+(?:\([^)]*\))?(?:\.\w+(?:\([^)]*\))?)*)(?:[ \t]|(?=\r?\n)))|(\})|((?:.|[\r\n\f])+?)/gi; -const STYLE_REGEX = /(?:^|\.)(\w+)(?:\(([^)]*)\))?/g; -const STRING_REGEX = /^(['"])((?:\\.|(?!\1)[^\\])*)\1$/; -const ESCAPE_REGEX = /\\(u(?:[a-f\d]{4}|{[a-f\d]{1,6}})|x[a-f\d]{2}|.)|([^\\])/gi; - -const ESCAPES = new Map([ - ['n', '\n'], - ['r', '\r'], - ['t', '\t'], - ['b', '\b'], - ['f', '\f'], - ['v', '\v'], - ['0', '\0'], - ['\\', '\\'], - ['e', '\u001B'], - ['a', '\u0007'] -]); - -function unescape(c) { - const u = c[0] === 'u'; - const bracket = c[1] === '{'; - - if ((u && !bracket && c.length === 5) || (c[0] === 'x' && c.length === 3)) { - return String.fromCharCode(parseInt(c.slice(1), 16)); - } - - if (u && bracket) { - return String.fromCodePoint(parseInt(c.slice(2, -1), 16)); - } - - return ESCAPES.get(c) || c; -} - -function parseArguments(name, arguments_) { - const results = []; - const chunks = arguments_.trim().split(/\s*,\s*/g); - let matches; - - for (const chunk of chunks) { - const number = Number(chunk); - if (!Number.isNaN(number)) { - results.push(number); - } else if ((matches = chunk.match(STRING_REGEX))) { - results.push(matches[2].replace(ESCAPE_REGEX, (m, escape, character) => escape ? unescape(escape) : character)); - } else { - throw new Error(`Invalid Chalk template style argument: ${chunk} (in style '${name}')`); - } - } - - return results; -} - -function parseStyle(style) { - STYLE_REGEX.lastIndex = 0; - - const results = []; - let matches; - - while ((matches = STYLE_REGEX.exec(style)) !== null) { - const name = matches[1]; - - if (matches[2]) { - const args = parseArguments(name, matches[2]); - results.push([name].concat(args)); - } else { - results.push([name]); - } - } - - return results; -} - -function buildStyle(chalk, styles) { - const enabled = {}; - - for (const layer of styles) { - for (const style of layer.styles) { - enabled[style[0]] = layer.inverse ? null : style.slice(1); - } - } - - let current = chalk; - for (const [styleName, styles] of Object.entries(enabled)) { - if (!Array.isArray(styles)) { - continue; - } - - if (!(styleName in current)) { - throw new Error(`Unknown Chalk style: ${styleName}`); - } - - current = styles.length > 0 ? current[styleName](...styles) : current[styleName]; - } - - return current; -} - -module.exports = (chalk, temporary) => { - const styles = []; - const chunks = []; - let chunk = []; - - // eslint-disable-next-line max-params - temporary.replace(TEMPLATE_REGEX, (m, escapeCharacter, inverse, style, close, character) => { - if (escapeCharacter) { - chunk.push(unescape(escapeCharacter)); - } else if (style) { - const string = chunk.join(''); - chunk = []; - chunks.push(styles.length === 0 ? string : buildStyle(chalk, styles)(string)); - styles.push({inverse, styles: parseStyle(style)}); - } else if (close) { - if (styles.length === 0) { - throw new Error('Found extraneous } in Chalk template literal'); - } - - chunks.push(buildStyle(chalk, styles)(chunk.join(''))); - chunk = []; - styles.pop(); - } else { - chunk.push(character); - } - }); - - chunks.push(chunk.join('')); - - if (styles.length > 0) { - const errMessage = `Chalk template literal is missing ${styles.length} closing bracket${styles.length === 1 ? '' : 's'} (\`}\`)`; - throw new Error(errMessage); - } - - return chunks.join(''); -}; - - -/***/ }), - -/***/ "../../node_modules/chalk/source/util.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const stringReplaceAll = (string, substring, replacer) => { - let index = string.indexOf(substring); - if (index === -1) { - return string; - } - - const substringLength = substring.length; - let endIndex = 0; - let returnValue = ''; - do { - returnValue += string.substr(endIndex, index - endIndex) + substring + replacer; - endIndex = index + substringLength; - index = string.indexOf(substring, endIndex); - } while (index !== -1); - - returnValue += string.substr(endIndex); - return returnValue; -}; - -const stringEncaseCRLFWithFirstIndex = (string, prefix, postfix, index) => { - let endIndex = 0; - let returnValue = ''; - do { - const gotCR = string[index - 1] === '\r'; - returnValue += string.substr(endIndex, (gotCR ? index - 1 : index) - endIndex) + prefix + (gotCR ? '\r\n' : '\n') + postfix; - endIndex = index + 1; - index = string.indexOf('\n', endIndex); - } while (index !== -1); - - returnValue += string.substr(endIndex); - return returnValue; -}; - -module.exports = { - stringReplaceAll, - stringEncaseCRLFWithFirstIndex -}; - - -/***/ }), - -/***/ "../../node_modules/clean-stack/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const os = __webpack_require__("os"); - -const extractPathRegex = /\s+at.*(?:\(|\s)(.*)\)?/; -const pathRegex = /^(?:(?:(?:node|(?:internal\/[\w/]*|.*node_modules\/(?:babel-polyfill|pirates)\/.*)?\w+)\.js:\d+:\d+)|native)/; -const homeDir = typeof os.homedir === 'undefined' ? '' : os.homedir(); - -module.exports = (stack, options) => { - options = Object.assign({pretty: false}, options); - - return stack.replace(/\\/g, '/') - .split('\n') - .filter(line => { - const pathMatches = line.match(extractPathRegex); - if (pathMatches === null || !pathMatches[1]) { - return true; - } - - const match = pathMatches[1]; - - // Electron - if ( - match.includes('.app/Contents/Resources/electron.asar') || - match.includes('.app/Contents/Resources/default_app.asar') - ) { - return false; - } - - return !pathRegex.test(match); - }) - .filter(line => line.trim() !== '') - .map(line => { - if (options.pretty) { - return line.replace(extractPathRegex, (m, p1) => m.replace(p1, p1.replace(homeDir, '~'))); - } - - return line; - }) - .join('\n'); -}; - - -/***/ }), - -/***/ "../../node_modules/cli-cursor/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const restoreCursor = __webpack_require__("../../node_modules/restore-cursor/index.js"); - -let isHidden = false; - -exports.show = (writableStream = process.stderr) => { - if (!writableStream.isTTY) { - return; - } - - isHidden = false; - writableStream.write('\u001B[?25h'); -}; - -exports.hide = (writableStream = process.stderr) => { - if (!writableStream.isTTY) { - return; - } - - restoreCursor(); - isHidden = true; - writableStream.write('\u001B[?25l'); -}; - -exports.toggle = (force, writableStream) => { - if (force !== undefined) { - isHidden = force; - } - - if (isHidden) { - exports.show(writableStream); - } else { - exports.hide(writableStream); - } -}; - - -/***/ }), - -/***/ "../../node_modules/cli-spinners/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const spinners = Object.assign({}, __webpack_require__("../../node_modules/cli-spinners/spinners.json")); - -const spinnersList = Object.keys(spinners); - -Object.defineProperty(spinners, 'random', { - get() { - const randomIndex = Math.floor(Math.random() * spinnersList.length); - const spinnerName = spinnersList[randomIndex]; - return spinners[spinnerName]; - } -}); - -module.exports = spinners; -// TODO: Remove this for the next major release -module.exports.default = spinners; - - -/***/ }), - -/***/ "../../node_modules/cli-spinners/spinners.json": -/***/ (function(module) { - -module.exports = JSON.parse("{\"dots\":{\"interval\":80,\"frames\":[\"⠋\",\"⠙\",\"⠹\",\"⠸\",\"⠼\",\"⠴\",\"⠦\",\"⠧\",\"⠇\",\"⠏\"]},\"dots2\":{\"interval\":80,\"frames\":[\"⣾\",\"⣽\",\"⣻\",\"⢿\",\"⡿\",\"⣟\",\"⣯\",\"⣷\"]},\"dots3\":{\"interval\":80,\"frames\":[\"⠋\",\"⠙\",\"⠚\",\"⠞\",\"⠖\",\"⠦\",\"⠴\",\"⠲\",\"⠳\",\"⠓\"]},\"dots4\":{\"interval\":80,\"frames\":[\"⠄\",\"⠆\",\"⠇\",\"⠋\",\"⠙\",\"⠸\",\"⠰\",\"⠠\",\"⠰\",\"⠸\",\"⠙\",\"⠋\",\"⠇\",\"⠆\"]},\"dots5\":{\"interval\":80,\"frames\":[\"⠋\",\"⠙\",\"⠚\",\"⠒\",\"⠂\",\"⠂\",\"⠒\",\"⠲\",\"⠴\",\"⠦\",\"⠖\",\"⠒\",\"⠐\",\"⠐\",\"⠒\",\"⠓\",\"⠋\"]},\"dots6\":{\"interval\":80,\"frames\":[\"⠁\",\"⠉\",\"⠙\",\"⠚\",\"⠒\",\"⠂\",\"⠂\",\"⠒\",\"⠲\",\"⠴\",\"⠤\",\"⠄\",\"⠄\",\"⠤\",\"⠴\",\"⠲\",\"⠒\",\"⠂\",\"⠂\",\"⠒\",\"⠚\",\"⠙\",\"⠉\",\"⠁\"]},\"dots7\":{\"interval\":80,\"frames\":[\"⠈\",\"⠉\",\"⠋\",\"⠓\",\"⠒\",\"⠐\",\"⠐\",\"⠒\",\"⠖\",\"⠦\",\"⠤\",\"⠠\",\"⠠\",\"⠤\",\"⠦\",\"⠖\",\"⠒\",\"⠐\",\"⠐\",\"⠒\",\"⠓\",\"⠋\",\"⠉\",\"⠈\"]},\"dots8\":{\"interval\":80,\"frames\":[\"⠁\",\"⠁\",\"⠉\",\"⠙\",\"⠚\",\"⠒\",\"⠂\",\"⠂\",\"⠒\",\"⠲\",\"⠴\",\"⠤\",\"⠄\",\"⠄\",\"⠤\",\"⠠\",\"⠠\",\"⠤\",\"⠦\",\"⠖\",\"⠒\",\"⠐\",\"⠐\",\"⠒\",\"⠓\",\"⠋\",\"⠉\",\"⠈\",\"⠈\"]},\"dots9\":{\"interval\":80,\"frames\":[\"⢹\",\"⢺\",\"⢼\",\"⣸\",\"⣇\",\"⡧\",\"⡗\",\"⡏\"]},\"dots10\":{\"interval\":80,\"frames\":[\"⢄\",\"⢂\",\"⢁\",\"⡁\",\"⡈\",\"⡐\",\"⡠\"]},\"dots11\":{\"interval\":100,\"frames\":[\"⠁\",\"⠂\",\"⠄\",\"⡀\",\"⢀\",\"⠠\",\"⠐\",\"⠈\"]},\"dots12\":{\"interval\":80,\"frames\":[\"⢀⠀\",\"⡀⠀\",\"⠄⠀\",\"⢂⠀\",\"⡂⠀\",\"⠅⠀\",\"⢃⠀\",\"⡃⠀\",\"⠍⠀\",\"⢋⠀\",\"⡋⠀\",\"⠍⠁\",\"⢋⠁\",\"⡋⠁\",\"⠍⠉\",\"⠋⠉\",\"⠋⠉\",\"⠉⠙\",\"⠉⠙\",\"⠉⠩\",\"⠈⢙\",\"⠈⡙\",\"⢈⠩\",\"⡀⢙\",\"⠄⡙\",\"⢂⠩\",\"⡂⢘\",\"⠅⡘\",\"⢃⠨\",\"⡃⢐\",\"⠍⡐\",\"⢋⠠\",\"⡋⢀\",\"⠍⡁\",\"⢋⠁\",\"⡋⠁\",\"⠍⠉\",\"⠋⠉\",\"⠋⠉\",\"⠉⠙\",\"⠉⠙\",\"⠉⠩\",\"⠈⢙\",\"⠈⡙\",\"⠈⠩\",\"⠀⢙\",\"⠀⡙\",\"⠀⠩\",\"⠀⢘\",\"⠀⡘\",\"⠀⠨\",\"⠀⢐\",\"⠀⡐\",\"⠀⠠\",\"⠀⢀\",\"⠀⡀\"]},\"dots8Bit\":{\"interval\":80,\"frames\":[\"⠀\",\"⠁\",\"⠂\",\"⠃\",\"⠄\",\"⠅\",\"⠆\",\"⠇\",\"⡀\",\"⡁\",\"⡂\",\"⡃\",\"⡄\",\"⡅\",\"⡆\",\"⡇\",\"⠈\",\"⠉\",\"⠊\",\"⠋\",\"⠌\",\"⠍\",\"⠎\",\"⠏\",\"⡈\",\"⡉\",\"⡊\",\"⡋\",\"⡌\",\"⡍\",\"⡎\",\"⡏\",\"⠐\",\"⠑\",\"⠒\",\"⠓\",\"⠔\",\"⠕\",\"⠖\",\"⠗\",\"⡐\",\"⡑\",\"⡒\",\"⡓\",\"⡔\",\"⡕\",\"⡖\",\"⡗\",\"⠘\",\"⠙\",\"⠚\",\"⠛\",\"⠜\",\"⠝\",\"⠞\",\"⠟\",\"⡘\",\"⡙\",\"⡚\",\"⡛\",\"⡜\",\"⡝\",\"⡞\",\"⡟\",\"⠠\",\"⠡\",\"⠢\",\"⠣\",\"⠤\",\"⠥\",\"⠦\",\"⠧\",\"⡠\",\"⡡\",\"⡢\",\"⡣\",\"⡤\",\"⡥\",\"⡦\",\"⡧\",\"⠨\",\"⠩\",\"⠪\",\"⠫\",\"⠬\",\"⠭\",\"⠮\",\"⠯\",\"⡨\",\"⡩\",\"⡪\",\"⡫\",\"⡬\",\"⡭\",\"⡮\",\"⡯\",\"⠰\",\"⠱\",\"⠲\",\"⠳\",\"⠴\",\"⠵\",\"⠶\",\"⠷\",\"⡰\",\"⡱\",\"⡲\",\"⡳\",\"⡴\",\"⡵\",\"⡶\",\"⡷\",\"⠸\",\"⠹\",\"⠺\",\"⠻\",\"⠼\",\"⠽\",\"⠾\",\"⠿\",\"⡸\",\"⡹\",\"⡺\",\"⡻\",\"⡼\",\"⡽\",\"⡾\",\"⡿\",\"⢀\",\"⢁\",\"⢂\",\"⢃\",\"⢄\",\"⢅\",\"⢆\",\"⢇\",\"⣀\",\"⣁\",\"⣂\",\"⣃\",\"⣄\",\"⣅\",\"⣆\",\"⣇\",\"⢈\",\"⢉\",\"⢊\",\"⢋\",\"⢌\",\"⢍\",\"⢎\",\"⢏\",\"⣈\",\"⣉\",\"⣊\",\"⣋\",\"⣌\",\"⣍\",\"⣎\",\"⣏\",\"⢐\",\"⢑\",\"⢒\",\"⢓\",\"⢔\",\"⢕\",\"⢖\",\"⢗\",\"⣐\",\"⣑\",\"⣒\",\"⣓\",\"⣔\",\"⣕\",\"⣖\",\"⣗\",\"⢘\",\"⢙\",\"⢚\",\"⢛\",\"⢜\",\"⢝\",\"⢞\",\"⢟\",\"⣘\",\"⣙\",\"⣚\",\"⣛\",\"⣜\",\"⣝\",\"⣞\",\"⣟\",\"⢠\",\"⢡\",\"⢢\",\"⢣\",\"⢤\",\"⢥\",\"⢦\",\"⢧\",\"⣠\",\"⣡\",\"⣢\",\"⣣\",\"⣤\",\"⣥\",\"⣦\",\"⣧\",\"⢨\",\"⢩\",\"⢪\",\"⢫\",\"⢬\",\"⢭\",\"⢮\",\"⢯\",\"⣨\",\"⣩\",\"⣪\",\"⣫\",\"⣬\",\"⣭\",\"⣮\",\"⣯\",\"⢰\",\"⢱\",\"⢲\",\"⢳\",\"⢴\",\"⢵\",\"⢶\",\"⢷\",\"⣰\",\"⣱\",\"⣲\",\"⣳\",\"⣴\",\"⣵\",\"⣶\",\"⣷\",\"⢸\",\"⢹\",\"⢺\",\"⢻\",\"⢼\",\"⢽\",\"⢾\",\"⢿\",\"⣸\",\"⣹\",\"⣺\",\"⣻\",\"⣼\",\"⣽\",\"⣾\",\"⣿\"]},\"line\":{\"interval\":130,\"frames\":[\"-\",\"\\\\\",\"|\",\"/\"]},\"line2\":{\"interval\":100,\"frames\":[\"⠂\",\"-\",\"–\",\"—\",\"–\",\"-\"]},\"pipe\":{\"interval\":100,\"frames\":[\"┤\",\"┘\",\"┴\",\"└\",\"├\",\"┌\",\"┬\",\"┐\"]},\"simpleDots\":{\"interval\":400,\"frames\":[\". \",\".. \",\"...\",\" \"]},\"simpleDotsScrolling\":{\"interval\":200,\"frames\":[\". \",\".. \",\"...\",\" ..\",\" .\",\" \"]},\"star\":{\"interval\":70,\"frames\":[\"✶\",\"✸\",\"✹\",\"✺\",\"✹\",\"✷\"]},\"star2\":{\"interval\":80,\"frames\":[\"+\",\"x\",\"*\"]},\"flip\":{\"interval\":70,\"frames\":[\"_\",\"_\",\"_\",\"-\",\"`\",\"`\",\"'\",\"´\",\"-\",\"_\",\"_\",\"_\"]},\"hamburger\":{\"interval\":100,\"frames\":[\"☱\",\"☲\",\"☴\"]},\"growVertical\":{\"interval\":120,\"frames\":[\"▁\",\"▃\",\"▄\",\"▅\",\"▆\",\"▇\",\"▆\",\"▅\",\"▄\",\"▃\"]},\"growHorizontal\":{\"interval\":120,\"frames\":[\"▏\",\"▎\",\"▍\",\"▌\",\"▋\",\"▊\",\"▉\",\"▊\",\"▋\",\"▌\",\"▍\",\"▎\"]},\"balloon\":{\"interval\":140,\"frames\":[\" \",\".\",\"o\",\"O\",\"@\",\"*\",\" \"]},\"balloon2\":{\"interval\":120,\"frames\":[\".\",\"o\",\"O\",\"°\",\"O\",\"o\",\".\"]},\"noise\":{\"interval\":100,\"frames\":[\"▓\",\"▒\",\"░\"]},\"bounce\":{\"interval\":120,\"frames\":[\"⠁\",\"⠂\",\"⠄\",\"⠂\"]},\"boxBounce\":{\"interval\":120,\"frames\":[\"▖\",\"▘\",\"▝\",\"▗\"]},\"boxBounce2\":{\"interval\":100,\"frames\":[\"▌\",\"▀\",\"▐\",\"▄\"]},\"triangle\":{\"interval\":50,\"frames\":[\"◢\",\"◣\",\"◤\",\"◥\"]},\"arc\":{\"interval\":100,\"frames\":[\"◜\",\"◠\",\"◝\",\"◞\",\"◡\",\"◟\"]},\"circle\":{\"interval\":120,\"frames\":[\"◡\",\"⊙\",\"◠\"]},\"squareCorners\":{\"interval\":180,\"frames\":[\"◰\",\"◳\",\"◲\",\"◱\"]},\"circleQuarters\":{\"interval\":120,\"frames\":[\"◴\",\"◷\",\"◶\",\"◵\"]},\"circleHalves\":{\"interval\":50,\"frames\":[\"◐\",\"◓\",\"◑\",\"◒\"]},\"squish\":{\"interval\":100,\"frames\":[\"╫\",\"╪\"]},\"toggle\":{\"interval\":250,\"frames\":[\"⊶\",\"⊷\"]},\"toggle2\":{\"interval\":80,\"frames\":[\"▫\",\"▪\"]},\"toggle3\":{\"interval\":120,\"frames\":[\"□\",\"■\"]},\"toggle4\":{\"interval\":100,\"frames\":[\"■\",\"□\",\"▪\",\"▫\"]},\"toggle5\":{\"interval\":100,\"frames\":[\"▮\",\"▯\"]},\"toggle6\":{\"interval\":300,\"frames\":[\"ဝ\",\"၀\"]},\"toggle7\":{\"interval\":80,\"frames\":[\"⦾\",\"⦿\"]},\"toggle8\":{\"interval\":100,\"frames\":[\"◍\",\"◌\"]},\"toggle9\":{\"interval\":100,\"frames\":[\"◉\",\"◎\"]},\"toggle10\":{\"interval\":100,\"frames\":[\"㊂\",\"㊀\",\"㊁\"]},\"toggle11\":{\"interval\":50,\"frames\":[\"⧇\",\"⧆\"]},\"toggle12\":{\"interval\":120,\"frames\":[\"☗\",\"☖\"]},\"toggle13\":{\"interval\":80,\"frames\":[\"=\",\"*\",\"-\"]},\"arrow\":{\"interval\":100,\"frames\":[\"←\",\"↖\",\"↑\",\"↗\",\"→\",\"↘\",\"↓\",\"↙\"]},\"arrow2\":{\"interval\":80,\"frames\":[\"⬆️ \",\"↗️ \",\"➡️ \",\"↘️ \",\"⬇️ \",\"↙️ \",\"⬅️ \",\"↖️ \"]},\"arrow3\":{\"interval\":120,\"frames\":[\"▹▹▹▹▹\",\"▸▹▹▹▹\",\"▹▸▹▹▹\",\"▹▹▸▹▹\",\"▹▹▹▸▹\",\"▹▹▹▹▸\"]},\"bouncingBar\":{\"interval\":80,\"frames\":[\"[ ]\",\"[= ]\",\"[== ]\",\"[=== ]\",\"[ ===]\",\"[ ==]\",\"[ =]\",\"[ ]\",\"[ =]\",\"[ ==]\",\"[ ===]\",\"[====]\",\"[=== ]\",\"[== ]\",\"[= ]\"]},\"bouncingBall\":{\"interval\":80,\"frames\":[\"( ● )\",\"( ● )\",\"( ● )\",\"( ● )\",\"( ●)\",\"( ● )\",\"( ● )\",\"( ● )\",\"( ● )\",\"(● )\"]},\"smiley\":{\"interval\":200,\"frames\":[\"😄 \",\"😝 \"]},\"monkey\":{\"interval\":300,\"frames\":[\"🙈 \",\"🙈 \",\"🙉 \",\"🙊 \"]},\"hearts\":{\"interval\":100,\"frames\":[\"💛 \",\"💙 \",\"💜 \",\"💚 \",\"❤️ \"]},\"clock\":{\"interval\":100,\"frames\":[\"🕛 \",\"🕐 \",\"🕑 \",\"🕒 \",\"🕓 \",\"🕔 \",\"🕕 \",\"🕖 \",\"🕗 \",\"🕘 \",\"🕙 \",\"🕚 \"]},\"earth\":{\"interval\":180,\"frames\":[\"🌍 \",\"🌎 \",\"🌏 \"]},\"material\":{\"interval\":17,\"frames\":[\"█▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"██▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"███▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"████▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"██████▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"██████▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"███████▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"████████▁▁▁▁▁▁▁▁▁▁▁▁\",\"█████████▁▁▁▁▁▁▁▁▁▁▁\",\"█████████▁▁▁▁▁▁▁▁▁▁▁\",\"██████████▁▁▁▁▁▁▁▁▁▁\",\"███████████▁▁▁▁▁▁▁▁▁\",\"█████████████▁▁▁▁▁▁▁\",\"██████████████▁▁▁▁▁▁\",\"██████████████▁▁▁▁▁▁\",\"▁██████████████▁▁▁▁▁\",\"▁██████████████▁▁▁▁▁\",\"▁██████████████▁▁▁▁▁\",\"▁▁██████████████▁▁▁▁\",\"▁▁▁██████████████▁▁▁\",\"▁▁▁▁█████████████▁▁▁\",\"▁▁▁▁██████████████▁▁\",\"▁▁▁▁██████████████▁▁\",\"▁▁▁▁▁██████████████▁\",\"▁▁▁▁▁██████████████▁\",\"▁▁▁▁▁██████████████▁\",\"▁▁▁▁▁▁██████████████\",\"▁▁▁▁▁▁██████████████\",\"▁▁▁▁▁▁▁█████████████\",\"▁▁▁▁▁▁▁█████████████\",\"▁▁▁▁▁▁▁▁████████████\",\"▁▁▁▁▁▁▁▁████████████\",\"▁▁▁▁▁▁▁▁▁███████████\",\"▁▁▁▁▁▁▁▁▁███████████\",\"▁▁▁▁▁▁▁▁▁▁██████████\",\"▁▁▁▁▁▁▁▁▁▁██████████\",\"▁▁▁▁▁▁▁▁▁▁▁▁████████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁███████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁██████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁█████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁█████\",\"█▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁████\",\"██▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁███\",\"██▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁███\",\"███▁▁▁▁▁▁▁▁▁▁▁▁▁▁███\",\"████▁▁▁▁▁▁▁▁▁▁▁▁▁▁██\",\"█████▁▁▁▁▁▁▁▁▁▁▁▁▁▁█\",\"█████▁▁▁▁▁▁▁▁▁▁▁▁▁▁█\",\"██████▁▁▁▁▁▁▁▁▁▁▁▁▁█\",\"████████▁▁▁▁▁▁▁▁▁▁▁▁\",\"█████████▁▁▁▁▁▁▁▁▁▁▁\",\"█████████▁▁▁▁▁▁▁▁▁▁▁\",\"█████████▁▁▁▁▁▁▁▁▁▁▁\",\"█████████▁▁▁▁▁▁▁▁▁▁▁\",\"███████████▁▁▁▁▁▁▁▁▁\",\"████████████▁▁▁▁▁▁▁▁\",\"████████████▁▁▁▁▁▁▁▁\",\"██████████████▁▁▁▁▁▁\",\"██████████████▁▁▁▁▁▁\",\"▁██████████████▁▁▁▁▁\",\"▁██████████████▁▁▁▁▁\",\"▁▁▁█████████████▁▁▁▁\",\"▁▁▁▁▁████████████▁▁▁\",\"▁▁▁▁▁████████████▁▁▁\",\"▁▁▁▁▁▁███████████▁▁▁\",\"▁▁▁▁▁▁▁▁█████████▁▁▁\",\"▁▁▁▁▁▁▁▁█████████▁▁▁\",\"▁▁▁▁▁▁▁▁▁█████████▁▁\",\"▁▁▁▁▁▁▁▁▁█████████▁▁\",\"▁▁▁▁▁▁▁▁▁▁█████████▁\",\"▁▁▁▁▁▁▁▁▁▁▁████████▁\",\"▁▁▁▁▁▁▁▁▁▁▁████████▁\",\"▁▁▁▁▁▁▁▁▁▁▁▁███████▁\",\"▁▁▁▁▁▁▁▁▁▁▁▁███████▁\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁███████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁███████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁█████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁████\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁███\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁███\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁██\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁██\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁██\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁█\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁█\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁█\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\",\"▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁\"]},\"moon\":{\"interval\":80,\"frames\":[\"🌑 \",\"🌒 \",\"🌓 \",\"🌔 \",\"🌕 \",\"🌖 \",\"🌗 \",\"🌘 \"]},\"runner\":{\"interval\":140,\"frames\":[\"🚶 \",\"🏃 \"]},\"pong\":{\"interval\":80,\"frames\":[\"▐⠂ ▌\",\"▐⠈ ▌\",\"▐ ⠂ ▌\",\"▐ ⠠ ▌\",\"▐ ⡀ ▌\",\"▐ ⠠ ▌\",\"▐ ⠂ ▌\",\"▐ ⠈ ▌\",\"▐ ⠂ ▌\",\"▐ ⠠ ▌\",\"▐ ⡀ ▌\",\"▐ ⠠ ▌\",\"▐ ⠂ ▌\",\"▐ ⠈ ▌\",\"▐ ⠂▌\",\"▐ ⠠▌\",\"▐ ⡀▌\",\"▐ ⠠ ▌\",\"▐ ⠂ ▌\",\"▐ ⠈ ▌\",\"▐ ⠂ ▌\",\"▐ ⠠ ▌\",\"▐ ⡀ ▌\",\"▐ ⠠ ▌\",\"▐ ⠂ ▌\",\"▐ ⠈ ▌\",\"▐ ⠂ ▌\",\"▐ ⠠ ▌\",\"▐ ⡀ ▌\",\"▐⠠ ▌\"]},\"shark\":{\"interval\":120,\"frames\":[\"▐|\\\\____________▌\",\"▐_|\\\\___________▌\",\"▐__|\\\\__________▌\",\"▐___|\\\\_________▌\",\"▐____|\\\\________▌\",\"▐_____|\\\\_______▌\",\"▐______|\\\\______▌\",\"▐_______|\\\\_____▌\",\"▐________|\\\\____▌\",\"▐_________|\\\\___▌\",\"▐__________|\\\\__▌\",\"▐___________|\\\\_▌\",\"▐____________|\\\\▌\",\"▐____________/|▌\",\"▐___________/|_▌\",\"▐__________/|__▌\",\"▐_________/|___▌\",\"▐________/|____▌\",\"▐_______/|_____▌\",\"▐______/|______▌\",\"▐_____/|_______▌\",\"▐____/|________▌\",\"▐___/|_________▌\",\"▐__/|__________▌\",\"▐_/|___________▌\",\"▐/|____________▌\"]},\"dqpb\":{\"interval\":100,\"frames\":[\"d\",\"q\",\"p\",\"b\"]},\"weather\":{\"interval\":100,\"frames\":[\"☀️ \",\"☀️ \",\"☀️ \",\"🌤 \",\"⛅️ \",\"🌥 \",\"☁️ \",\"🌧 \",\"🌨 \",\"🌧 \",\"🌨 \",\"🌧 \",\"🌨 \",\"⛈ \",\"🌨 \",\"🌧 \",\"🌨 \",\"☁️ \",\"🌥 \",\"⛅️ \",\"🌤 \",\"☀️ \",\"☀️ \"]},\"christmas\":{\"interval\":400,\"frames\":[\"🌲\",\"🎄\"]},\"grenade\":{\"interval\":80,\"frames\":[\"، \",\"′ \",\" ´ \",\" ‾ \",\" ⸌\",\" ⸊\",\" |\",\" ⁎\",\" ⁕\",\" ෴ \",\" ⁓\",\" \",\" \",\" \"]},\"point\":{\"interval\":125,\"frames\":[\"∙∙∙\",\"●∙∙\",\"∙●∙\",\"∙∙●\",\"∙∙∙\"]},\"layer\":{\"interval\":150,\"frames\":[\"-\",\"=\",\"≡\"]},\"betaWave\":{\"interval\":80,\"frames\":[\"ρββββββ\",\"βρβββββ\",\"ββρββββ\",\"βββρβββ\",\"ββββρββ\",\"βββββρβ\",\"ββββββρ\"]},\"aesthetic\":{\"interval\":80,\"frames\":[\"▰▱▱▱▱▱▱\",\"▰▰▱▱▱▱▱\",\"▰▰▰▱▱▱▱\",\"▰▰▰▰▱▱▱\",\"▰▰▰▰▰▱▱\",\"▰▰▰▰▰▰▱\",\"▰▰▰▰▰▰▰\",\"▰▱▱▱▱▱▱\"]}}"); - -/***/ }), - -/***/ "../../node_modules/clone/clone.js": -/***/ (function(module, exports, __webpack_require__) { - -var clone = (function() { -'use strict'; - -/** - * Clones (copies) an Object using deep copying. - * - * This function supports circular references by default, but if you are certain - * there are no circular references in your object, you can save some CPU time - * by calling clone(obj, false). - * - * Caution: if `circular` is false and `parent` contains circular references, - * your program may enter an infinite loop and crash. - * - * @param `parent` - the object to be cloned - * @param `circular` - set to true if the object to be cloned may contain - * circular references. (optional - true by default) - * @param `depth` - set to a number if the object is only to be cloned to - * a particular depth. (optional - defaults to Infinity) - * @param `prototype` - sets the prototype to be used when cloning an object. - * (optional - defaults to parent prototype). -*/ -function clone(parent, circular, depth, prototype) { - var filter; - if (typeof circular === 'object') { - depth = circular.depth; - prototype = circular.prototype; - filter = circular.filter; - circular = circular.circular - } - // maintain two arrays for circular references, where corresponding parents - // and children have the same index - var allParents = []; - var allChildren = []; - - var useBuffer = typeof Buffer != 'undefined'; - - if (typeof circular == 'undefined') - circular = true; - - if (typeof depth == 'undefined') - depth = Infinity; - - // recurse this function so we don't reset allParents and allChildren - function _clone(parent, depth) { - // cloning null always returns null - if (parent === null) - return null; - - if (depth == 0) - return parent; - - var child; - var proto; - if (typeof parent != 'object') { - return parent; - } - - if (clone.__isArray(parent)) { - child = []; - } else if (clone.__isRegExp(parent)) { - child = new RegExp(parent.source, __getRegExpFlags(parent)); - if (parent.lastIndex) child.lastIndex = parent.lastIndex; - } else if (clone.__isDate(parent)) { - child = new Date(parent.getTime()); - } else if (useBuffer && Buffer.isBuffer(parent)) { - if (Buffer.allocUnsafe) { - // Node.js >= 4.5.0 - child = Buffer.allocUnsafe(parent.length); - } else { - // Older Node.js versions - child = new Buffer(parent.length); - } - parent.copy(child); - return child; - } else { - if (typeof prototype == 'undefined') { - proto = Object.getPrototypeOf(parent); - child = Object.create(proto); - } - else { - child = Object.create(prototype); - proto = prototype; - } - } - - if (circular) { - var index = allParents.indexOf(parent); - - if (index != -1) { - return allChildren[index]; - } - allParents.push(parent); - allChildren.push(child); - } - - for (var i in parent) { - var attrs; - if (proto) { - attrs = Object.getOwnPropertyDescriptor(proto, i); - } - - if (attrs && attrs.set == null) { - continue; - } - child[i] = _clone(parent[i], depth - 1); - } - - return child; - } - - return _clone(parent, depth); -} - -/** - * Simple flat clone using prototype, accepts only objects, usefull for property - * override on FLAT configuration object (no nested props). - * - * USE WITH CAUTION! This may not behave as you wish if you do not know how this - * works. - */ -clone.clonePrototype = function clonePrototype(parent) { - if (parent === null) - return null; - - var c = function () {}; - c.prototype = parent; - return new c(); -}; - -// private utility functions - -function __objToStr(o) { - return Object.prototype.toString.call(o); -}; -clone.__objToStr = __objToStr; - -function __isDate(o) { - return typeof o === 'object' && __objToStr(o) === '[object Date]'; -}; -clone.__isDate = __isDate; - -function __isArray(o) { - return typeof o === 'object' && __objToStr(o) === '[object Array]'; -}; -clone.__isArray = __isArray; - -function __isRegExp(o) { - return typeof o === 'object' && __objToStr(o) === '[object RegExp]'; -}; -clone.__isRegExp = __isRegExp; - -function __getRegExpFlags(re) { - var flags = ''; - if (re.global) flags += 'g'; - if (re.ignoreCase) flags += 'i'; - if (re.multiline) flags += 'm'; - return flags; -}; -clone.__getRegExpFlags = __getRegExpFlags; - -return clone; -})(); - -if ( true && module.exports) { - module.exports = clone; -} - - -/***/ }), - -/***/ "../../node_modules/cmd-shim/index.js": -/***/ (function(module, exports, __webpack_require__) { - -// On windows, create a .cmd file. -// Read the #! in the file to see what it uses. The vast majority -// of the time, this will be either: -// "#!/usr/bin/env " -// or: -// "#! " -// -// Write a binroot/pkg.bin + ".cmd" file that has this line in it: -// @ %~dp0 %* - -module.exports = cmdShim -cmdShim.ifExists = cmdShimIfExists - -var fs = __webpack_require__("../../node_modules/graceful-fs/graceful-fs.js") - -var mkdir = __webpack_require__("../../node_modules/mkdirp/index.js") - , path = __webpack_require__("path") - , toBatchSyntax = __webpack_require__("../../node_modules/cmd-shim/lib/to-batch-syntax.js") - , shebangExpr = /^#\!\s*(?:\/usr\/bin\/env)?\s*([^ \t]+=[^ \t]+\s+)*\s*([^ \t]+)(.*)$/ - -function cmdShimIfExists (from, to, cb) { - fs.stat(from, function (er) { - if (er) return cb() - cmdShim(from, to, cb) - }) -} - -// Try to unlink, but ignore errors. -// Any problems will surface later. -function rm (path, cb) { - fs.unlink(path, function(er) { - cb() - }) -} - -function cmdShim (from, to, cb) { - fs.stat(from, function (er, stat) { - if (er) - return cb(er) - - cmdShim_(from, to, cb) - }) -} - -function cmdShim_ (from, to, cb) { - var then = times(2, next, cb) - rm(to, then) - rm(to + ".cmd", then) - - function next(er) { - writeShim(from, to, cb) - } -} - -function writeShim (from, to, cb) { - // make a cmd file and a sh script - // First, check if the bin is a #! of some sort. - // If not, then assume it's something that'll be compiled, or some other - // sort of script, and just call it directly. - mkdir(path.dirname(to), function (er) { - if (er) - return cb(er) - fs.readFile(from, "utf8", function (er, data) { - if (er) return writeShim_(from, to, null, null, cb) - var firstLine = data.trim().split(/\r*\n/)[0] - , shebang = firstLine.match(shebangExpr) - if (!shebang) return writeShim_(from, to, null, null, null, cb) - var vars = shebang[1] || "" - , prog = shebang[2] - , args = shebang[3] || "" - return writeShim_(from, to, prog, args, vars, cb) - }) - }) -} - - -function writeShim_ (from, to, prog, args, variables, cb) { - var shTarget = path.relative(path.dirname(to), from) - , target = shTarget.split("/").join("\\") - , longProg - , shProg = prog && prog.split("\\").join("/") - , shLongProg - , pwshProg = shProg && "\"" + shProg + "$exe\"" - , pwshLongProg - shTarget = shTarget.split("\\").join("/") - args = args || "" - variables = variables || "" - if (!prog) { - prog = "\"%~dp0\\" + target + "\"" - shProg = "\"$basedir/" + shTarget + "\"" - pwshProg = shProg - args = "" - target = "" - shTarget = "" - } else { - longProg = "\"%~dp0\\" + prog + ".exe\"" - shLongProg = "\"$basedir/" + prog + "\"" - pwshLongProg = "\"$basedir/" + prog + "$exe\"" - target = "\"%~dp0\\" + target + "\"" - shTarget = "\"$basedir/" + shTarget + "\"" - } - - // @SETLOCAL - // - // @IF EXIST "%~dp0\node.exe" ( - // @SET "_prog=%~dp0\node.exe" - // ) ELSE ( - // @SET "_prog=node" - // @SET PATHEXT=%PATHEXT:;.JS;=;% - // ) - // - // "%_prog%" "%~dp0\.\node_modules\npm\bin\npm-cli.js" %* - // @ENDLOCAL - var cmd - if (longProg) { - shLongProg = shLongProg.trim(); - args = args.trim(); - var variableDeclarationsAsBatch = toBatchSyntax.convertToSetCommands(variables) - cmd = "@SETLOCAL\r\n" - + variableDeclarationsAsBatch - + "\r\n" - + "@IF EXIST " + longProg + " (\r\n" - + " @SET \"_prog=" + longProg.replace(/(^")|("$)/g, '') + "\"\r\n" - + ") ELSE (\r\n" - + " @SET \"_prog=" + prog.replace(/(^")|("$)/g, '') + "\"\r\n" - + " @SET PATHEXT=%PATHEXT:;.JS;=;%\r\n" - + ")\r\n" - + "\r\n" - + "\"%_prog%\" " + args + " " + target + " %*\r\n" - + '@ENDLOCAL\r\n' - } else { - cmd = "@" + prog + " " + args + " " + target + " %*\r\n" - } - - // #!/bin/sh - // basedir=`dirname "$0"` - // - // case `uname` in - // *CYGWIN*|*MINGW*|*MSYS*) basedir=`cygpath -w "$basedir"`;; - // esac - // - // if [ -x "$basedir/node.exe" ]; then - // "$basedir/node.exe" "$basedir/node_modules/npm/bin/npm-cli.js" "$@" - // ret=$? - // else - // node "$basedir/node_modules/npm/bin/npm-cli.js" "$@" - // ret=$? - // fi - // exit $ret - - var sh = "#!/bin/sh\n" - - sh = sh - + "basedir=$(dirname \"$(echo \"$0\" | sed -e 's,\\\\,/,g')\")\n" - + "\n" - + "case `uname` in\n" - + " *CYGWIN*|*MINGW*|*MSYS*) basedir=`cygpath -w \"$basedir\"`;;\n" - + "esac\n" - + "\n" - - if (shLongProg) { - sh = sh - + "if [ -x "+shLongProg+" ]; then\n" - + " " + variables + shLongProg + " " + args + " " + shTarget + " \"$@\"\n" - + " ret=$?\n" - + "else \n" - + " " + variables + shProg + " " + args + " " + shTarget + " \"$@\"\n" - + " ret=$?\n" - + "fi\n" - + "exit $ret\n" - } else { - sh = sh - + shProg + " " + args + " " + shTarget + " \"$@\"\n" - + "exit $?\n" - } - - // #!/usr/bin/env pwsh - // $basedir=Split-Path $MyInvocation.MyCommand.Definition -Parent - // - // $ret=0 - // $exe = "" - // if ($PSVersionTable.PSVersion -lt "6.0" -or $IsWindows) { - // # Fix case when both the Windows and Linux builds of Node - // # are installed in the same directory - // $exe = ".exe" - // } - // if (Test-Path "$basedir/node") { - // & "$basedir/node$exe" "$basedir/node_modules/npm/bin/npm-cli.js" $args - // $ret=$LASTEXITCODE - // } else { - // & "node$exe" "$basedir/node_modules/npm/bin/npm-cli.js" $args - // $ret=$LASTEXITCODE - // } - // exit $ret - var pwsh = "#!/usr/bin/env pwsh\n" - + "$basedir=Split-Path $MyInvocation.MyCommand.Definition -Parent\n" - + "\n" - + "$exe=\"\"\n" - + "if ($PSVersionTable.PSVersion -lt \"6.0\" -or $IsWindows) {\n" - + " # Fix case when both the Windows and Linux builds of Node\n" - + " # are installed in the same directory\n" - + " $exe=\".exe\"\n" - + "}\n" - if (shLongProg) { - pwsh = pwsh - + "$ret=0\n" - + "if (Test-Path " + pwshLongProg + ") {\n" - + " & " + pwshLongProg + " " + args + " " + shTarget + " $args\n" - + " $ret=$LASTEXITCODE\n" - + "} else {\n" - + " & " + pwshProg + " " + args + " " + shTarget + " $args\n" - + " $ret=$LASTEXITCODE\n" - + "}\n" - + "exit $ret\n" - } else { - pwsh = pwsh - + "& " + pwshProg + " " + args + " " + shTarget + " $args\n" - + "exit $LASTEXITCODE\n" - } - - var then = times(3, next, cb) - fs.writeFile(to + ".ps1", pwsh, "utf8", then) - fs.writeFile(to + ".cmd", cmd, "utf8", then) - fs.writeFile(to, sh, "utf8", then) - function next () { - chmodShim(to, cb) - } -} - -function chmodShim (to, cb) { - var then = times(2, cb, cb) - fs.chmod(to, "0755", then) - fs.chmod(to + ".cmd", "0755", then) - fs.chmod(to + ".ps1", "0755", then) -} - -function times(n, ok, cb) { - var errState = null - return function(er) { - if (!errState) { - if (er) - cb(errState = er) - else if (--n === 0) - ok() - } - } -} - - -/***/ }), - -/***/ "../../node_modules/cmd-shim/lib/to-batch-syntax.js": -/***/ (function(module, exports) { - -exports.replaceDollarWithPercentPair = replaceDollarWithPercentPair -exports.convertToSetCommand = convertToSetCommand -exports.convertToSetCommands = convertToSetCommands - -function convertToSetCommand(key, value) { - var line = "" - key = key || "" - key = key.trim() - value = value || "" - value = value.trim() - if(key && value && value.length > 0) { - line = "@SET " + key + "=" + replaceDollarWithPercentPair(value) + "\r\n" - } - return line -} - -function extractVariableValuePairs(declarations) { - var pairs = {} - declarations.map(function(declaration) { - var split = declaration.split("=") - pairs[split[0]]=split[1] - }) - return pairs -} - -function convertToSetCommands(variableString) { - var variableValuePairs = extractVariableValuePairs(variableString.split(" ")) - var variableDeclarationsAsBatch = "" - Object.keys(variableValuePairs).forEach(function (key) { - variableDeclarationsAsBatch += convertToSetCommand(key, variableValuePairs[key]) - }) - return variableDeclarationsAsBatch -} - -function replaceDollarWithPercentPair(value) { - var dollarExpressions = /\$\{?([^\$@#\?\- \t{}:]+)\}?/g - var result = "" - var startIndex = 0 - value = value || "" - do { - var match = dollarExpressions.exec(value) - if(match) { - var betweenMatches = value.substring(startIndex, match.index) || "" - result += betweenMatches + "%" + match[1] + "%" - startIndex = dollarExpressions.lastIndex - } - } while (dollarExpressions.lastIndex > 0) - result += value.substr(startIndex) - return result -} - - - - -/***/ }), - -/***/ "../../node_modules/color-convert/conversions.js": -/***/ (function(module, exports, __webpack_require__) { - -/* MIT license */ -var cssKeywords = __webpack_require__("../../node_modules/color-convert/node_modules/color-name/index.js"); - -// NOTE: conversions should only return primitive values (i.e. arrays, or -// values that give correct `typeof` results). -// do not use box values types (i.e. Number(), String(), etc.) - -var reverseKeywords = {}; -for (var key in cssKeywords) { - if (cssKeywords.hasOwnProperty(key)) { - reverseKeywords[cssKeywords[key]] = key; - } -} - -var convert = module.exports = { - rgb: {channels: 3, labels: 'rgb'}, - hsl: {channels: 3, labels: 'hsl'}, - hsv: {channels: 3, labels: 'hsv'}, - hwb: {channels: 3, labels: 'hwb'}, - cmyk: {channels: 4, labels: 'cmyk'}, - xyz: {channels: 3, labels: 'xyz'}, - lab: {channels: 3, labels: 'lab'}, - lch: {channels: 3, labels: 'lch'}, - hex: {channels: 1, labels: ['hex']}, - keyword: {channels: 1, labels: ['keyword']}, - ansi16: {channels: 1, labels: ['ansi16']}, - ansi256: {channels: 1, labels: ['ansi256']}, - hcg: {channels: 3, labels: ['h', 'c', 'g']}, - apple: {channels: 3, labels: ['r16', 'g16', 'b16']}, - gray: {channels: 1, labels: ['gray']} -}; - -// hide .channels and .labels properties -for (var model in convert) { - if (convert.hasOwnProperty(model)) { - if (!('channels' in convert[model])) { - throw new Error('missing channels property: ' + model); - } - - if (!('labels' in convert[model])) { - throw new Error('missing channel labels property: ' + model); - } - - if (convert[model].labels.length !== convert[model].channels) { - throw new Error('channel and label counts mismatch: ' + model); - } - - var channels = convert[model].channels; - var labels = convert[model].labels; - delete convert[model].channels; - delete convert[model].labels; - Object.defineProperty(convert[model], 'channels', {value: channels}); - Object.defineProperty(convert[model], 'labels', {value: labels}); - } -} - -convert.rgb.hsl = function (rgb) { - var r = rgb[0] / 255; - var g = rgb[1] / 255; - var b = rgb[2] / 255; - var min = Math.min(r, g, b); - var max = Math.max(r, g, b); - var delta = max - min; - var h; - var s; - var l; - - if (max === min) { - h = 0; - } else if (r === max) { - h = (g - b) / delta; - } else if (g === max) { - h = 2 + (b - r) / delta; - } else if (b === max) { - h = 4 + (r - g) / delta; - } - - h = Math.min(h * 60, 360); - - if (h < 0) { - h += 360; - } - - l = (min + max) / 2; - - if (max === min) { - s = 0; - } else if (l <= 0.5) { - s = delta / (max + min); - } else { - s = delta / (2 - max - min); - } - - return [h, s * 100, l * 100]; -}; - -convert.rgb.hsv = function (rgb) { - var rdif; - var gdif; - var bdif; - var h; - var s; - - var r = rgb[0] / 255; - var g = rgb[1] / 255; - var b = rgb[2] / 255; - var v = Math.max(r, g, b); - var diff = v - Math.min(r, g, b); - var diffc = function (c) { - return (v - c) / 6 / diff + 1 / 2; - }; - - if (diff === 0) { - h = s = 0; - } else { - s = diff / v; - rdif = diffc(r); - gdif = diffc(g); - bdif = diffc(b); - - if (r === v) { - h = bdif - gdif; - } else if (g === v) { - h = (1 / 3) + rdif - bdif; - } else if (b === v) { - h = (2 / 3) + gdif - rdif; - } - if (h < 0) { - h += 1; - } else if (h > 1) { - h -= 1; - } - } - - return [ - h * 360, - s * 100, - v * 100 - ]; -}; - -convert.rgb.hwb = function (rgb) { - var r = rgb[0]; - var g = rgb[1]; - var b = rgb[2]; - var h = convert.rgb.hsl(rgb)[0]; - var w = 1 / 255 * Math.min(r, Math.min(g, b)); - - b = 1 - 1 / 255 * Math.max(r, Math.max(g, b)); - - return [h, w * 100, b * 100]; -}; - -convert.rgb.cmyk = function (rgb) { - var r = rgb[0] / 255; - var g = rgb[1] / 255; - var b = rgb[2] / 255; - var c; - var m; - var y; - var k; - - k = Math.min(1 - r, 1 - g, 1 - b); - c = (1 - r - k) / (1 - k) || 0; - m = (1 - g - k) / (1 - k) || 0; - y = (1 - b - k) / (1 - k) || 0; - - return [c * 100, m * 100, y * 100, k * 100]; -}; - -/** - * See https://en.m.wikipedia.org/wiki/Euclidean_distance#Squared_Euclidean_distance - * */ -function comparativeDistance(x, y) { - return ( - Math.pow(x[0] - y[0], 2) + - Math.pow(x[1] - y[1], 2) + - Math.pow(x[2] - y[2], 2) - ); -} - -convert.rgb.keyword = function (rgb) { - var reversed = reverseKeywords[rgb]; - if (reversed) { - return reversed; - } - - var currentClosestDistance = Infinity; - var currentClosestKeyword; - - for (var keyword in cssKeywords) { - if (cssKeywords.hasOwnProperty(keyword)) { - var value = cssKeywords[keyword]; - - // Compute comparative distance - var distance = comparativeDistance(rgb, value); - - // Check if its less, if so set as closest - if (distance < currentClosestDistance) { - currentClosestDistance = distance; - currentClosestKeyword = keyword; - } - } - } - - return currentClosestKeyword; -}; - -convert.keyword.rgb = function (keyword) { - return cssKeywords[keyword]; -}; - -convert.rgb.xyz = function (rgb) { - var r = rgb[0] / 255; - var g = rgb[1] / 255; - var b = rgb[2] / 255; - - // assume sRGB - r = r > 0.04045 ? Math.pow(((r + 0.055) / 1.055), 2.4) : (r / 12.92); - g = g > 0.04045 ? Math.pow(((g + 0.055) / 1.055), 2.4) : (g / 12.92); - b = b > 0.04045 ? Math.pow(((b + 0.055) / 1.055), 2.4) : (b / 12.92); - - var x = (r * 0.4124) + (g * 0.3576) + (b * 0.1805); - var y = (r * 0.2126) + (g * 0.7152) + (b * 0.0722); - var z = (r * 0.0193) + (g * 0.1192) + (b * 0.9505); - - return [x * 100, y * 100, z * 100]; -}; - -convert.rgb.lab = function (rgb) { - var xyz = convert.rgb.xyz(rgb); - var x = xyz[0]; - var y = xyz[1]; - var z = xyz[2]; - var l; - var a; - var b; - - x /= 95.047; - y /= 100; - z /= 108.883; - - x = x > 0.008856 ? Math.pow(x, 1 / 3) : (7.787 * x) + (16 / 116); - y = y > 0.008856 ? Math.pow(y, 1 / 3) : (7.787 * y) + (16 / 116); - z = z > 0.008856 ? Math.pow(z, 1 / 3) : (7.787 * z) + (16 / 116); - - l = (116 * y) - 16; - a = 500 * (x - y); - b = 200 * (y - z); - - return [l, a, b]; -}; - -convert.hsl.rgb = function (hsl) { - var h = hsl[0] / 360; - var s = hsl[1] / 100; - var l = hsl[2] / 100; - var t1; - var t2; - var t3; - var rgb; - var val; - - if (s === 0) { - val = l * 255; - return [val, val, val]; - } - - if (l < 0.5) { - t2 = l * (1 + s); - } else { - t2 = l + s - l * s; - } - - t1 = 2 * l - t2; - - rgb = [0, 0, 0]; - for (var i = 0; i < 3; i++) { - t3 = h + 1 / 3 * -(i - 1); - if (t3 < 0) { - t3++; - } - if (t3 > 1) { - t3--; - } - - if (6 * t3 < 1) { - val = t1 + (t2 - t1) * 6 * t3; - } else if (2 * t3 < 1) { - val = t2; - } else if (3 * t3 < 2) { - val = t1 + (t2 - t1) * (2 / 3 - t3) * 6; - } else { - val = t1; - } - - rgb[i] = val * 255; - } - - return rgb; -}; - -convert.hsl.hsv = function (hsl) { - var h = hsl[0]; - var s = hsl[1] / 100; - var l = hsl[2] / 100; - var smin = s; - var lmin = Math.max(l, 0.01); - var sv; - var v; - - l *= 2; - s *= (l <= 1) ? l : 2 - l; - smin *= lmin <= 1 ? lmin : 2 - lmin; - v = (l + s) / 2; - sv = l === 0 ? (2 * smin) / (lmin + smin) : (2 * s) / (l + s); - - return [h, sv * 100, v * 100]; -}; - -convert.hsv.rgb = function (hsv) { - var h = hsv[0] / 60; - var s = hsv[1] / 100; - var v = hsv[2] / 100; - var hi = Math.floor(h) % 6; - - var f = h - Math.floor(h); - var p = 255 * v * (1 - s); - var q = 255 * v * (1 - (s * f)); - var t = 255 * v * (1 - (s * (1 - f))); - v *= 255; - - switch (hi) { - case 0: - return [v, t, p]; - case 1: - return [q, v, p]; - case 2: - return [p, v, t]; - case 3: - return [p, q, v]; - case 4: - return [t, p, v]; - case 5: - return [v, p, q]; - } -}; - -convert.hsv.hsl = function (hsv) { - var h = hsv[0]; - var s = hsv[1] / 100; - var v = hsv[2] / 100; - var vmin = Math.max(v, 0.01); - var lmin; - var sl; - var l; - - l = (2 - s) * v; - lmin = (2 - s) * vmin; - sl = s * vmin; - sl /= (lmin <= 1) ? lmin : 2 - lmin; - sl = sl || 0; - l /= 2; - - return [h, sl * 100, l * 100]; -}; - -// http://dev.w3.org/csswg/css-color/#hwb-to-rgb -convert.hwb.rgb = function (hwb) { - var h = hwb[0] / 360; - var wh = hwb[1] / 100; - var bl = hwb[2] / 100; - var ratio = wh + bl; - var i; - var v; - var f; - var n; - - // wh + bl cant be > 1 - if (ratio > 1) { - wh /= ratio; - bl /= ratio; - } - - i = Math.floor(6 * h); - v = 1 - bl; - f = 6 * h - i; - - if ((i & 0x01) !== 0) { - f = 1 - f; - } - - n = wh + f * (v - wh); // linear interpolation - - var r; - var g; - var b; - switch (i) { - default: - case 6: - case 0: r = v; g = n; b = wh; break; - case 1: r = n; g = v; b = wh; break; - case 2: r = wh; g = v; b = n; break; - case 3: r = wh; g = n; b = v; break; - case 4: r = n; g = wh; b = v; break; - case 5: r = v; g = wh; b = n; break; - } - - return [r * 255, g * 255, b * 255]; -}; - -convert.cmyk.rgb = function (cmyk) { - var c = cmyk[0] / 100; - var m = cmyk[1] / 100; - var y = cmyk[2] / 100; - var k = cmyk[3] / 100; - var r; - var g; - var b; - - r = 1 - Math.min(1, c * (1 - k) + k); - g = 1 - Math.min(1, m * (1 - k) + k); - b = 1 - Math.min(1, y * (1 - k) + k); - - return [r * 255, g * 255, b * 255]; -}; - -convert.xyz.rgb = function (xyz) { - var x = xyz[0] / 100; - var y = xyz[1] / 100; - var z = xyz[2] / 100; - var r; - var g; - var b; - - r = (x * 3.2406) + (y * -1.5372) + (z * -0.4986); - g = (x * -0.9689) + (y * 1.8758) + (z * 0.0415); - b = (x * 0.0557) + (y * -0.2040) + (z * 1.0570); - - // assume sRGB - r = r > 0.0031308 - ? ((1.055 * Math.pow(r, 1.0 / 2.4)) - 0.055) - : r * 12.92; - - g = g > 0.0031308 - ? ((1.055 * Math.pow(g, 1.0 / 2.4)) - 0.055) - : g * 12.92; - - b = b > 0.0031308 - ? ((1.055 * Math.pow(b, 1.0 / 2.4)) - 0.055) - : b * 12.92; - - r = Math.min(Math.max(0, r), 1); - g = Math.min(Math.max(0, g), 1); - b = Math.min(Math.max(0, b), 1); - - return [r * 255, g * 255, b * 255]; -}; - -convert.xyz.lab = function (xyz) { - var x = xyz[0]; - var y = xyz[1]; - var z = xyz[2]; - var l; - var a; - var b; - - x /= 95.047; - y /= 100; - z /= 108.883; - - x = x > 0.008856 ? Math.pow(x, 1 / 3) : (7.787 * x) + (16 / 116); - y = y > 0.008856 ? Math.pow(y, 1 / 3) : (7.787 * y) + (16 / 116); - z = z > 0.008856 ? Math.pow(z, 1 / 3) : (7.787 * z) + (16 / 116); - - l = (116 * y) - 16; - a = 500 * (x - y); - b = 200 * (y - z); - - return [l, a, b]; -}; - -convert.lab.xyz = function (lab) { - var l = lab[0]; - var a = lab[1]; - var b = lab[2]; - var x; - var y; - var z; - - y = (l + 16) / 116; - x = a / 500 + y; - z = y - b / 200; - - var y2 = Math.pow(y, 3); - var x2 = Math.pow(x, 3); - var z2 = Math.pow(z, 3); - y = y2 > 0.008856 ? y2 : (y - 16 / 116) / 7.787; - x = x2 > 0.008856 ? x2 : (x - 16 / 116) / 7.787; - z = z2 > 0.008856 ? z2 : (z - 16 / 116) / 7.787; - - x *= 95.047; - y *= 100; - z *= 108.883; - - return [x, y, z]; -}; - -convert.lab.lch = function (lab) { - var l = lab[0]; - var a = lab[1]; - var b = lab[2]; - var hr; - var h; - var c; - - hr = Math.atan2(b, a); - h = hr * 360 / 2 / Math.PI; - - if (h < 0) { - h += 360; - } - - c = Math.sqrt(a * a + b * b); - - return [l, c, h]; -}; - -convert.lch.lab = function (lch) { - var l = lch[0]; - var c = lch[1]; - var h = lch[2]; - var a; - var b; - var hr; - - hr = h / 360 * 2 * Math.PI; - a = c * Math.cos(hr); - b = c * Math.sin(hr); - - return [l, a, b]; -}; - -convert.rgb.ansi16 = function (args) { - var r = args[0]; - var g = args[1]; - var b = args[2]; - var value = 1 in arguments ? arguments[1] : convert.rgb.hsv(args)[2]; // hsv -> ansi16 optimization - - value = Math.round(value / 50); - - if (value === 0) { - return 30; - } - - var ansi = 30 - + ((Math.round(b / 255) << 2) - | (Math.round(g / 255) << 1) - | Math.round(r / 255)); - - if (value === 2) { - ansi += 60; - } - - return ansi; -}; - -convert.hsv.ansi16 = function (args) { - // optimization here; we already know the value and don't need to get - // it converted for us. - return convert.rgb.ansi16(convert.hsv.rgb(args), args[2]); -}; - -convert.rgb.ansi256 = function (args) { - var r = args[0]; - var g = args[1]; - var b = args[2]; - - // we use the extended greyscale palette here, with the exception of - // black and white. normal palette only has 4 greyscale shades. - if (r === g && g === b) { - if (r < 8) { - return 16; - } - - if (r > 248) { - return 231; - } - - return Math.round(((r - 8) / 247) * 24) + 232; - } - - var ansi = 16 - + (36 * Math.round(r / 255 * 5)) - + (6 * Math.round(g / 255 * 5)) - + Math.round(b / 255 * 5); - - return ansi; -}; - -convert.ansi16.rgb = function (args) { - var color = args % 10; - - // handle greyscale - if (color === 0 || color === 7) { - if (args > 50) { - color += 3.5; - } - - color = color / 10.5 * 255; - - return [color, color, color]; - } - - var mult = (~~(args > 50) + 1) * 0.5; - var r = ((color & 1) * mult) * 255; - var g = (((color >> 1) & 1) * mult) * 255; - var b = (((color >> 2) & 1) * mult) * 255; - - return [r, g, b]; -}; - -convert.ansi256.rgb = function (args) { - // handle greyscale - if (args >= 232) { - var c = (args - 232) * 10 + 8; - return [c, c, c]; - } - - args -= 16; - - var rem; - var r = Math.floor(args / 36) / 5 * 255; - var g = Math.floor((rem = args % 36) / 6) / 5 * 255; - var b = (rem % 6) / 5 * 255; - - return [r, g, b]; -}; - -convert.rgb.hex = function (args) { - var integer = ((Math.round(args[0]) & 0xFF) << 16) - + ((Math.round(args[1]) & 0xFF) << 8) - + (Math.round(args[2]) & 0xFF); - - var string = integer.toString(16).toUpperCase(); - return '000000'.substring(string.length) + string; -}; - -convert.hex.rgb = function (args) { - var match = args.toString(16).match(/[a-f0-9]{6}|[a-f0-9]{3}/i); - if (!match) { - return [0, 0, 0]; - } - - var colorString = match[0]; - - if (match[0].length === 3) { - colorString = colorString.split('').map(function (char) { - return char + char; - }).join(''); - } - - var integer = parseInt(colorString, 16); - var r = (integer >> 16) & 0xFF; - var g = (integer >> 8) & 0xFF; - var b = integer & 0xFF; - - return [r, g, b]; -}; - -convert.rgb.hcg = function (rgb) { - var r = rgb[0] / 255; - var g = rgb[1] / 255; - var b = rgb[2] / 255; - var max = Math.max(Math.max(r, g), b); - var min = Math.min(Math.min(r, g), b); - var chroma = (max - min); - var grayscale; - var hue; - - if (chroma < 1) { - grayscale = min / (1 - chroma); - } else { - grayscale = 0; - } - - if (chroma <= 0) { - hue = 0; - } else - if (max === r) { - hue = ((g - b) / chroma) % 6; - } else - if (max === g) { - hue = 2 + (b - r) / chroma; - } else { - hue = 4 + (r - g) / chroma + 4; - } - - hue /= 6; - hue %= 1; - - return [hue * 360, chroma * 100, grayscale * 100]; -}; - -convert.hsl.hcg = function (hsl) { - var s = hsl[1] / 100; - var l = hsl[2] / 100; - var c = 1; - var f = 0; - - if (l < 0.5) { - c = 2.0 * s * l; - } else { - c = 2.0 * s * (1.0 - l); - } - - if (c < 1.0) { - f = (l - 0.5 * c) / (1.0 - c); - } - - return [hsl[0], c * 100, f * 100]; -}; - -convert.hsv.hcg = function (hsv) { - var s = hsv[1] / 100; - var v = hsv[2] / 100; - - var c = s * v; - var f = 0; - - if (c < 1.0) { - f = (v - c) / (1 - c); - } - - return [hsv[0], c * 100, f * 100]; -}; - -convert.hcg.rgb = function (hcg) { - var h = hcg[0] / 360; - var c = hcg[1] / 100; - var g = hcg[2] / 100; - - if (c === 0.0) { - return [g * 255, g * 255, g * 255]; - } - - var pure = [0, 0, 0]; - var hi = (h % 1) * 6; - var v = hi % 1; - var w = 1 - v; - var mg = 0; - - switch (Math.floor(hi)) { - case 0: - pure[0] = 1; pure[1] = v; pure[2] = 0; break; - case 1: - pure[0] = w; pure[1] = 1; pure[2] = 0; break; - case 2: - pure[0] = 0; pure[1] = 1; pure[2] = v; break; - case 3: - pure[0] = 0; pure[1] = w; pure[2] = 1; break; - case 4: - pure[0] = v; pure[1] = 0; pure[2] = 1; break; - default: - pure[0] = 1; pure[1] = 0; pure[2] = w; - } - - mg = (1.0 - c) * g; - - return [ - (c * pure[0] + mg) * 255, - (c * pure[1] + mg) * 255, - (c * pure[2] + mg) * 255 - ]; -}; - -convert.hcg.hsv = function (hcg) { - var c = hcg[1] / 100; - var g = hcg[2] / 100; - - var v = c + g * (1.0 - c); - var f = 0; - - if (v > 0.0) { - f = c / v; - } - - return [hcg[0], f * 100, v * 100]; -}; - -convert.hcg.hsl = function (hcg) { - var c = hcg[1] / 100; - var g = hcg[2] / 100; - - var l = g * (1.0 - c) + 0.5 * c; - var s = 0; - - if (l > 0.0 && l < 0.5) { - s = c / (2 * l); - } else - if (l >= 0.5 && l < 1.0) { - s = c / (2 * (1 - l)); - } - - return [hcg[0], s * 100, l * 100]; -}; - -convert.hcg.hwb = function (hcg) { - var c = hcg[1] / 100; - var g = hcg[2] / 100; - var v = c + g * (1.0 - c); - return [hcg[0], (v - c) * 100, (1 - v) * 100]; -}; - -convert.hwb.hcg = function (hwb) { - var w = hwb[1] / 100; - var b = hwb[2] / 100; - var v = 1 - b; - var c = v - w; - var g = 0; - - if (c < 1) { - g = (v - c) / (1 - c); - } - - return [hwb[0], c * 100, g * 100]; -}; - -convert.apple.rgb = function (apple) { - return [(apple[0] / 65535) * 255, (apple[1] / 65535) * 255, (apple[2] / 65535) * 255]; -}; - -convert.rgb.apple = function (rgb) { - return [(rgb[0] / 255) * 65535, (rgb[1] / 255) * 65535, (rgb[2] / 255) * 65535]; -}; - -convert.gray.rgb = function (args) { - return [args[0] / 100 * 255, args[0] / 100 * 255, args[0] / 100 * 255]; -}; - -convert.gray.hsl = convert.gray.hsv = function (args) { - return [0, 0, args[0]]; -}; - -convert.gray.hwb = function (gray) { - return [0, 100, gray[0]]; -}; - -convert.gray.cmyk = function (gray) { - return [0, 0, 0, gray[0]]; -}; - -convert.gray.lab = function (gray) { - return [gray[0], 0, 0]; -}; - -convert.gray.hex = function (gray) { - var val = Math.round(gray[0] / 100 * 255) & 0xFF; - var integer = (val << 16) + (val << 8) + val; - - var string = integer.toString(16).toUpperCase(); - return '000000'.substring(string.length) + string; -}; - -convert.rgb.gray = function (rgb) { - var val = (rgb[0] + rgb[1] + rgb[2]) / 3; - return [val / 255 * 100]; -}; - - -/***/ }), - -/***/ "../../node_modules/color-convert/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var conversions = __webpack_require__("../../node_modules/color-convert/conversions.js"); -var route = __webpack_require__("../../node_modules/color-convert/route.js"); - -var convert = {}; - -var models = Object.keys(conversions); - -function wrapRaw(fn) { - var wrappedFn = function (args) { - if (args === undefined || args === null) { - return args; - } - - if (arguments.length > 1) { - args = Array.prototype.slice.call(arguments); - } - - return fn(args); - }; - - // preserve .conversion property if there is one - if ('conversion' in fn) { - wrappedFn.conversion = fn.conversion; - } - - return wrappedFn; -} - -function wrapRounded(fn) { - var wrappedFn = function (args) { - if (args === undefined || args === null) { - return args; - } - - if (arguments.length > 1) { - args = Array.prototype.slice.call(arguments); - } - - var result = fn(args); - - // we're assuming the result is an array here. - // see notice in conversions.js; don't use box types - // in conversion functions. - if (typeof result === 'object') { - for (var len = result.length, i = 0; i < len; i++) { - result[i] = Math.round(result[i]); - } - } - - return result; - }; - - // preserve .conversion property if there is one - if ('conversion' in fn) { - wrappedFn.conversion = fn.conversion; - } - - return wrappedFn; -} - -models.forEach(function (fromModel) { - convert[fromModel] = {}; - - Object.defineProperty(convert[fromModel], 'channels', {value: conversions[fromModel].channels}); - Object.defineProperty(convert[fromModel], 'labels', {value: conversions[fromModel].labels}); - - var routes = route(fromModel); - var routeModels = Object.keys(routes); - - routeModels.forEach(function (toModel) { - var fn = routes[toModel]; - - convert[fromModel][toModel] = wrapRounded(fn); - convert[fromModel][toModel].raw = wrapRaw(fn); - }); -}); - -module.exports = convert; - - -/***/ }), - -/***/ "../../node_modules/color-convert/node_modules/color-name/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = { - "aliceblue": [240, 248, 255], - "antiquewhite": [250, 235, 215], - "aqua": [0, 255, 255], - "aquamarine": [127, 255, 212], - "azure": [240, 255, 255], - "beige": [245, 245, 220], - "bisque": [255, 228, 196], - "black": [0, 0, 0], - "blanchedalmond": [255, 235, 205], - "blue": [0, 0, 255], - "blueviolet": [138, 43, 226], - "brown": [165, 42, 42], - "burlywood": [222, 184, 135], - "cadetblue": [95, 158, 160], - "chartreuse": [127, 255, 0], - "chocolate": [210, 105, 30], - "coral": [255, 127, 80], - "cornflowerblue": [100, 149, 237], - "cornsilk": [255, 248, 220], - "crimson": [220, 20, 60], - "cyan": [0, 255, 255], - "darkblue": [0, 0, 139], - "darkcyan": [0, 139, 139], - "darkgoldenrod": [184, 134, 11], - "darkgray": [169, 169, 169], - "darkgreen": [0, 100, 0], - "darkgrey": [169, 169, 169], - "darkkhaki": [189, 183, 107], - "darkmagenta": [139, 0, 139], - "darkolivegreen": [85, 107, 47], - "darkorange": [255, 140, 0], - "darkorchid": [153, 50, 204], - "darkred": [139, 0, 0], - "darksalmon": [233, 150, 122], - "darkseagreen": [143, 188, 143], - "darkslateblue": [72, 61, 139], - "darkslategray": [47, 79, 79], - "darkslategrey": [47, 79, 79], - "darkturquoise": [0, 206, 209], - "darkviolet": [148, 0, 211], - "deeppink": [255, 20, 147], - "deepskyblue": [0, 191, 255], - "dimgray": [105, 105, 105], - "dimgrey": [105, 105, 105], - "dodgerblue": [30, 144, 255], - "firebrick": [178, 34, 34], - "floralwhite": [255, 250, 240], - "forestgreen": [34, 139, 34], - "fuchsia": [255, 0, 255], - "gainsboro": [220, 220, 220], - "ghostwhite": [248, 248, 255], - "gold": [255, 215, 0], - "goldenrod": [218, 165, 32], - "gray": [128, 128, 128], - "green": [0, 128, 0], - "greenyellow": [173, 255, 47], - "grey": [128, 128, 128], - "honeydew": [240, 255, 240], - "hotpink": [255, 105, 180], - "indianred": [205, 92, 92], - "indigo": [75, 0, 130], - "ivory": [255, 255, 240], - "khaki": [240, 230, 140], - "lavender": [230, 230, 250], - "lavenderblush": [255, 240, 245], - "lawngreen": [124, 252, 0], - "lemonchiffon": [255, 250, 205], - "lightblue": [173, 216, 230], - "lightcoral": [240, 128, 128], - "lightcyan": [224, 255, 255], - "lightgoldenrodyellow": [250, 250, 210], - "lightgray": [211, 211, 211], - "lightgreen": [144, 238, 144], - "lightgrey": [211, 211, 211], - "lightpink": [255, 182, 193], - "lightsalmon": [255, 160, 122], - "lightseagreen": [32, 178, 170], - "lightskyblue": [135, 206, 250], - "lightslategray": [119, 136, 153], - "lightslategrey": [119, 136, 153], - "lightsteelblue": [176, 196, 222], - "lightyellow": [255, 255, 224], - "lime": [0, 255, 0], - "limegreen": [50, 205, 50], - "linen": [250, 240, 230], - "magenta": [255, 0, 255], - "maroon": [128, 0, 0], - "mediumaquamarine": [102, 205, 170], - "mediumblue": [0, 0, 205], - "mediumorchid": [186, 85, 211], - "mediumpurple": [147, 112, 219], - "mediumseagreen": [60, 179, 113], - "mediumslateblue": [123, 104, 238], - "mediumspringgreen": [0, 250, 154], - "mediumturquoise": [72, 209, 204], - "mediumvioletred": [199, 21, 133], - "midnightblue": [25, 25, 112], - "mintcream": [245, 255, 250], - "mistyrose": [255, 228, 225], - "moccasin": [255, 228, 181], - "navajowhite": [255, 222, 173], - "navy": [0, 0, 128], - "oldlace": [253, 245, 230], - "olive": [128, 128, 0], - "olivedrab": [107, 142, 35], - "orange": [255, 165, 0], - "orangered": [255, 69, 0], - "orchid": [218, 112, 214], - "palegoldenrod": [238, 232, 170], - "palegreen": [152, 251, 152], - "paleturquoise": [175, 238, 238], - "palevioletred": [219, 112, 147], - "papayawhip": [255, 239, 213], - "peachpuff": [255, 218, 185], - "peru": [205, 133, 63], - "pink": [255, 192, 203], - "plum": [221, 160, 221], - "powderblue": [176, 224, 230], - "purple": [128, 0, 128], - "rebeccapurple": [102, 51, 153], - "red": [255, 0, 0], - "rosybrown": [188, 143, 143], - "royalblue": [65, 105, 225], - "saddlebrown": [139, 69, 19], - "salmon": [250, 128, 114], - "sandybrown": [244, 164, 96], - "seagreen": [46, 139, 87], - "seashell": [255, 245, 238], - "sienna": [160, 82, 45], - "silver": [192, 192, 192], - "skyblue": [135, 206, 235], - "slateblue": [106, 90, 205], - "slategray": [112, 128, 144], - "slategrey": [112, 128, 144], - "snow": [255, 250, 250], - "springgreen": [0, 255, 127], - "steelblue": [70, 130, 180], - "tan": [210, 180, 140], - "teal": [0, 128, 128], - "thistle": [216, 191, 216], - "tomato": [255, 99, 71], - "turquoise": [64, 224, 208], - "violet": [238, 130, 238], - "wheat": [245, 222, 179], - "white": [255, 255, 255], - "whitesmoke": [245, 245, 245], - "yellow": [255, 255, 0], - "yellowgreen": [154, 205, 50] -}; - - -/***/ }), - -/***/ "../../node_modules/color-convert/route.js": -/***/ (function(module, exports, __webpack_require__) { - -var conversions = __webpack_require__("../../node_modules/color-convert/conversions.js"); - -/* - this function routes a model to all other models. - - all functions that are routed have a property `.conversion` attached - to the returned synthetic function. This property is an array - of strings, each with the steps in between the 'from' and 'to' - color models (inclusive). - - conversions that are not possible simply are not included. -*/ - -function buildGraph() { - var graph = {}; - // https://jsperf.com/object-keys-vs-for-in-with-closure/3 - var models = Object.keys(conversions); - - for (var len = models.length, i = 0; i < len; i++) { - graph[models[i]] = { - // http://jsperf.com/1-vs-infinity - // micro-opt, but this is simple. - distance: -1, - parent: null - }; - } - - return graph; -} - -// https://en.wikipedia.org/wiki/Breadth-first_search -function deriveBFS(fromModel) { - var graph = buildGraph(); - var queue = [fromModel]; // unshift -> queue -> pop - - graph[fromModel].distance = 0; - - while (queue.length) { - var current = queue.pop(); - var adjacents = Object.keys(conversions[current]); - - for (var len = adjacents.length, i = 0; i < len; i++) { - var adjacent = adjacents[i]; - var node = graph[adjacent]; - - if (node.distance === -1) { - node.distance = graph[current].distance + 1; - node.parent = current; - queue.unshift(adjacent); - } - } - } - - return graph; -} - -function link(from, to) { - return function (args) { - return to(from(args)); - }; -} - -function wrapConversion(toModel, graph) { - var path = [graph[toModel].parent, toModel]; - var fn = conversions[graph[toModel].parent][toModel]; - - var cur = graph[toModel].parent; - while (graph[cur].parent) { - path.unshift(graph[cur].parent); - fn = link(conversions[graph[cur].parent][cur], fn); - cur = graph[cur].parent; - } - - fn.conversion = path; - return fn; -} - -module.exports = function (fromModel) { - var graph = deriveBFS(fromModel); - var conversion = {}; - - var models = Object.keys(graph); - for (var len = models.length, i = 0; i < len; i++) { - var toModel = models[i]; - var node = graph[toModel]; - - if (node.parent === null) { - // no possible conversion, or this node is the source model. - continue; - } - - conversion[toModel] = wrapConversion(toModel, graph); - } - - return conversion; -}; - - - -/***/ }), - -/***/ "../../node_modules/color-name/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = { - "aliceblue": [240, 248, 255], - "antiquewhite": [250, 235, 215], - "aqua": [0, 255, 255], - "aquamarine": [127, 255, 212], - "azure": [240, 255, 255], - "beige": [245, 245, 220], - "bisque": [255, 228, 196], - "black": [0, 0, 0], - "blanchedalmond": [255, 235, 205], - "blue": [0, 0, 255], - "blueviolet": [138, 43, 226], - "brown": [165, 42, 42], - "burlywood": [222, 184, 135], - "cadetblue": [95, 158, 160], - "chartreuse": [127, 255, 0], - "chocolate": [210, 105, 30], - "coral": [255, 127, 80], - "cornflowerblue": [100, 149, 237], - "cornsilk": [255, 248, 220], - "crimson": [220, 20, 60], - "cyan": [0, 255, 255], - "darkblue": [0, 0, 139], - "darkcyan": [0, 139, 139], - "darkgoldenrod": [184, 134, 11], - "darkgray": [169, 169, 169], - "darkgreen": [0, 100, 0], - "darkgrey": [169, 169, 169], - "darkkhaki": [189, 183, 107], - "darkmagenta": [139, 0, 139], - "darkolivegreen": [85, 107, 47], - "darkorange": [255, 140, 0], - "darkorchid": [153, 50, 204], - "darkred": [139, 0, 0], - "darksalmon": [233, 150, 122], - "darkseagreen": [143, 188, 143], - "darkslateblue": [72, 61, 139], - "darkslategray": [47, 79, 79], - "darkslategrey": [47, 79, 79], - "darkturquoise": [0, 206, 209], - "darkviolet": [148, 0, 211], - "deeppink": [255, 20, 147], - "deepskyblue": [0, 191, 255], - "dimgray": [105, 105, 105], - "dimgrey": [105, 105, 105], - "dodgerblue": [30, 144, 255], - "firebrick": [178, 34, 34], - "floralwhite": [255, 250, 240], - "forestgreen": [34, 139, 34], - "fuchsia": [255, 0, 255], - "gainsboro": [220, 220, 220], - "ghostwhite": [248, 248, 255], - "gold": [255, 215, 0], - "goldenrod": [218, 165, 32], - "gray": [128, 128, 128], - "green": [0, 128, 0], - "greenyellow": [173, 255, 47], - "grey": [128, 128, 128], - "honeydew": [240, 255, 240], - "hotpink": [255, 105, 180], - "indianred": [205, 92, 92], - "indigo": [75, 0, 130], - "ivory": [255, 255, 240], - "khaki": [240, 230, 140], - "lavender": [230, 230, 250], - "lavenderblush": [255, 240, 245], - "lawngreen": [124, 252, 0], - "lemonchiffon": [255, 250, 205], - "lightblue": [173, 216, 230], - "lightcoral": [240, 128, 128], - "lightcyan": [224, 255, 255], - "lightgoldenrodyellow": [250, 250, 210], - "lightgray": [211, 211, 211], - "lightgreen": [144, 238, 144], - "lightgrey": [211, 211, 211], - "lightpink": [255, 182, 193], - "lightsalmon": [255, 160, 122], - "lightseagreen": [32, 178, 170], - "lightskyblue": [135, 206, 250], - "lightslategray": [119, 136, 153], - "lightslategrey": [119, 136, 153], - "lightsteelblue": [176, 196, 222], - "lightyellow": [255, 255, 224], - "lime": [0, 255, 0], - "limegreen": [50, 205, 50], - "linen": [250, 240, 230], - "magenta": [255, 0, 255], - "maroon": [128, 0, 0], - "mediumaquamarine": [102, 205, 170], - "mediumblue": [0, 0, 205], - "mediumorchid": [186, 85, 211], - "mediumpurple": [147, 112, 219], - "mediumseagreen": [60, 179, 113], - "mediumslateblue": [123, 104, 238], - "mediumspringgreen": [0, 250, 154], - "mediumturquoise": [72, 209, 204], - "mediumvioletred": [199, 21, 133], - "midnightblue": [25, 25, 112], - "mintcream": [245, 255, 250], - "mistyrose": [255, 228, 225], - "moccasin": [255, 228, 181], - "navajowhite": [255, 222, 173], - "navy": [0, 0, 128], - "oldlace": [253, 245, 230], - "olive": [128, 128, 0], - "olivedrab": [107, 142, 35], - "orange": [255, 165, 0], - "orangered": [255, 69, 0], - "orchid": [218, 112, 214], - "palegoldenrod": [238, 232, 170], - "palegreen": [152, 251, 152], - "paleturquoise": [175, 238, 238], - "palevioletred": [219, 112, 147], - "papayawhip": [255, 239, 213], - "peachpuff": [255, 218, 185], - "peru": [205, 133, 63], - "pink": [255, 192, 203], - "plum": [221, 160, 221], - "powderblue": [176, 224, 230], - "purple": [128, 0, 128], - "rebeccapurple": [102, 51, 153], - "red": [255, 0, 0], - "rosybrown": [188, 143, 143], - "royalblue": [65, 105, 225], - "saddlebrown": [139, 69, 19], - "salmon": [250, 128, 114], - "sandybrown": [244, 164, 96], - "seagreen": [46, 139, 87], - "seashell": [255, 245, 238], - "sienna": [160, 82, 45], - "silver": [192, 192, 192], - "skyblue": [135, 206, 235], - "slateblue": [106, 90, 205], - "slategray": [112, 128, 144], - "slategrey": [112, 128, 144], - "snow": [255, 250, 250], - "springgreen": [0, 255, 127], - "steelblue": [70, 130, 180], - "tan": [210, 180, 140], - "teal": [0, 128, 128], - "thistle": [216, 191, 216], - "tomato": [255, 99, 71], - "turquoise": [64, 224, 208], - "violet": [238, 130, 238], - "wheat": [245, 222, 179], - "white": [255, 255, 255], - "whitesmoke": [245, 245, 245], - "yellow": [255, 255, 0], - "yellowgreen": [154, 205, 50] -}; - - -/***/ }), - -/***/ "../../node_modules/combined-stream/lib/combined_stream.js": -/***/ (function(module, exports, __webpack_require__) { - -var util = __webpack_require__("util"); -var Stream = __webpack_require__("stream").Stream; -var DelayedStream = __webpack_require__("../../node_modules/delayed-stream/lib/delayed_stream.js"); - -module.exports = CombinedStream; -function CombinedStream() { - this.writable = false; - this.readable = true; - this.dataSize = 0; - this.maxDataSize = 2 * 1024 * 1024; - this.pauseStreams = true; - - this._released = false; - this._streams = []; - this._currentStream = null; - this._insideLoop = false; - this._pendingNext = false; -} -util.inherits(CombinedStream, Stream); - -CombinedStream.create = function(options) { - var combinedStream = new this(); - - options = options || {}; - for (var option in options) { - combinedStream[option] = options[option]; - } - - return combinedStream; -}; - -CombinedStream.isStreamLike = function(stream) { - return (typeof stream !== 'function') - && (typeof stream !== 'string') - && (typeof stream !== 'boolean') - && (typeof stream !== 'number') - && (!Buffer.isBuffer(stream)); -}; - -CombinedStream.prototype.append = function(stream) { - var isStreamLike = CombinedStream.isStreamLike(stream); - - if (isStreamLike) { - if (!(stream instanceof DelayedStream)) { - var newStream = DelayedStream.create(stream, { - maxDataSize: Infinity, - pauseStream: this.pauseStreams, - }); - stream.on('data', this._checkDataSize.bind(this)); - stream = newStream; - } - - this._handleErrors(stream); - - if (this.pauseStreams) { - stream.pause(); - } - } - - this._streams.push(stream); - return this; -}; - -CombinedStream.prototype.pipe = function(dest, options) { - Stream.prototype.pipe.call(this, dest, options); - this.resume(); - return dest; -}; - -CombinedStream.prototype._getNext = function() { - this._currentStream = null; - - if (this._insideLoop) { - this._pendingNext = true; - return; // defer call - } - - this._insideLoop = true; - try { - do { - this._pendingNext = false; - this._realGetNext(); - } while (this._pendingNext); - } finally { - this._insideLoop = false; - } -}; - -CombinedStream.prototype._realGetNext = function() { - var stream = this._streams.shift(); - - - if (typeof stream == 'undefined') { - this.end(); - return; - } - - if (typeof stream !== 'function') { - this._pipeNext(stream); - return; - } - - var getStream = stream; - getStream(function(stream) { - var isStreamLike = CombinedStream.isStreamLike(stream); - if (isStreamLike) { - stream.on('data', this._checkDataSize.bind(this)); - this._handleErrors(stream); - } - - this._pipeNext(stream); - }.bind(this)); -}; - -CombinedStream.prototype._pipeNext = function(stream) { - this._currentStream = stream; - - var isStreamLike = CombinedStream.isStreamLike(stream); - if (isStreamLike) { - stream.on('end', this._getNext.bind(this)); - stream.pipe(this, {end: false}); - return; - } - - var value = stream; - this.write(value); - this._getNext(); -}; - -CombinedStream.prototype._handleErrors = function(stream) { - var self = this; - stream.on('error', function(err) { - self._emitError(err); - }); -}; - -CombinedStream.prototype.write = function(data) { - this.emit('data', data); -}; - -CombinedStream.prototype.pause = function() { - if (!this.pauseStreams) { - return; - } - - if(this.pauseStreams && this._currentStream && typeof(this._currentStream.pause) == 'function') this._currentStream.pause(); - this.emit('pause'); -}; - -CombinedStream.prototype.resume = function() { - if (!this._released) { - this._released = true; - this.writable = true; - this._getNext(); - } - - if(this.pauseStreams && this._currentStream && typeof(this._currentStream.resume) == 'function') this._currentStream.resume(); - this.emit('resume'); -}; - -CombinedStream.prototype.end = function() { - this._reset(); - this.emit('end'); -}; - -CombinedStream.prototype.destroy = function() { - this._reset(); - this.emit('close'); -}; - -CombinedStream.prototype._reset = function() { - this.writable = false; - this._streams = []; - this._currentStream = null; -}; - -CombinedStream.prototype._checkDataSize = function() { - this._updateDataSize(); - if (this.dataSize <= this.maxDataSize) { - return; - } - - var message = - 'DelayedStream#maxDataSize of ' + this.maxDataSize + ' bytes exceeded.'; - this._emitError(new Error(message)); -}; - -CombinedStream.prototype._updateDataSize = function() { - this.dataSize = 0; - - var self = this; - this._streams.forEach(function(stream) { - if (!stream.dataSize) { - return; - } - - self.dataSize += stream.dataSize; - }); - - if (this._currentStream && this._currentStream.dataSize) { - this.dataSize += this._currentStream.dataSize; - } -}; - -CombinedStream.prototype._emitError = function(err) { - this._reset(); - this.emit('error', err); -}; - - -/***/ }), - -/***/ "../../node_modules/concat-map/index.js": -/***/ (function(module, exports) { - -module.exports = function (xs, fn) { - var res = []; - for (var i = 0; i < xs.length; i++) { - var x = fn(xs[i], i); - if (isArray(x)) res.push.apply(res, x); - else res.push(x); - } - return res; -}; - -var isArray = Array.isArray || function (xs) { - return Object.prototype.toString.call(xs) === '[object Array]'; -}; - - -/***/ }), - -/***/ "../../node_modules/cross-spawn/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const cp = __webpack_require__("child_process"); -const parse = __webpack_require__("../../node_modules/cross-spawn/lib/parse.js"); -const enoent = __webpack_require__("../../node_modules/cross-spawn/lib/enoent.js"); - -function spawn(command, args, options) { - // Parse the arguments - const parsed = parse(command, args, options); - - // Spawn the child process - const spawned = cp.spawn(parsed.command, parsed.args, parsed.options); - - // Hook into child process "exit" event to emit an error if the command - // does not exists, see: https://github.com/IndigoUnited/node-cross-spawn/issues/16 - enoent.hookChildProcess(spawned, parsed); - - return spawned; -} - -function spawnSync(command, args, options) { - // Parse the arguments - const parsed = parse(command, args, options); - - // Spawn the child process - const result = cp.spawnSync(parsed.command, parsed.args, parsed.options); - - // Analyze if the command does not exist, see: https://github.com/IndigoUnited/node-cross-spawn/issues/16 - result.error = result.error || enoent.verifyENOENTSync(result.status, parsed); - - return result; -} - -module.exports = spawn; -module.exports.spawn = spawn; -module.exports.sync = spawnSync; - -module.exports._parse = parse; -module.exports._enoent = enoent; - - -/***/ }), - -/***/ "../../node_modules/cross-spawn/lib/enoent.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const isWin = process.platform === 'win32'; - -function notFoundError(original, syscall) { - return Object.assign(new Error(`${syscall} ${original.command} ENOENT`), { - code: 'ENOENT', - errno: 'ENOENT', - syscall: `${syscall} ${original.command}`, - path: original.command, - spawnargs: original.args, - }); -} - -function hookChildProcess(cp, parsed) { - if (!isWin) { - return; - } - - const originalEmit = cp.emit; - - cp.emit = function (name, arg1) { - // If emitting "exit" event and exit code is 1, we need to check if - // the command exists and emit an "error" instead - // See https://github.com/IndigoUnited/node-cross-spawn/issues/16 - if (name === 'exit') { - const err = verifyENOENT(arg1, parsed, 'spawn'); - - if (err) { - return originalEmit.call(cp, 'error', err); - } - } - - return originalEmit.apply(cp, arguments); // eslint-disable-line prefer-rest-params - }; -} - -function verifyENOENT(status, parsed) { - if (isWin && status === 1 && !parsed.file) { - return notFoundError(parsed.original, 'spawn'); - } - - return null; -} - -function verifyENOENTSync(status, parsed) { - if (isWin && status === 1 && !parsed.file) { - return notFoundError(parsed.original, 'spawnSync'); - } - - return null; -} - -module.exports = { - hookChildProcess, - verifyENOENT, - verifyENOENTSync, - notFoundError, -}; - - -/***/ }), - -/***/ "../../node_modules/cross-spawn/lib/parse.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const path = __webpack_require__("path"); -const resolveCommand = __webpack_require__("../../node_modules/cross-spawn/lib/util/resolveCommand.js"); -const escape = __webpack_require__("../../node_modules/cross-spawn/lib/util/escape.js"); -const readShebang = __webpack_require__("../../node_modules/cross-spawn/lib/util/readShebang.js"); - -const isWin = process.platform === 'win32'; -const isExecutableRegExp = /\.(?:com|exe)$/i; -const isCmdShimRegExp = /node_modules[\\/].bin[\\/][^\\/]+\.cmd$/i; - -function detectShebang(parsed) { - parsed.file = resolveCommand(parsed); - - const shebang = parsed.file && readShebang(parsed.file); - - if (shebang) { - parsed.args.unshift(parsed.file); - parsed.command = shebang; - - return resolveCommand(parsed); - } - - return parsed.file; -} - -function parseNonShell(parsed) { - if (!isWin) { - return parsed; - } - - // Detect & add support for shebangs - const commandFile = detectShebang(parsed); - - // We don't need a shell if the command filename is an executable - const needsShell = !isExecutableRegExp.test(commandFile); - - // If a shell is required, use cmd.exe and take care of escaping everything correctly - // Note that `forceShell` is an hidden option used only in tests - if (parsed.options.forceShell || needsShell) { - // Need to double escape meta chars if the command is a cmd-shim located in `node_modules/.bin/` - // The cmd-shim simply calls execute the package bin file with NodeJS, proxying any argument - // Because the escape of metachars with ^ gets interpreted when the cmd.exe is first called, - // we need to double escape them - const needsDoubleEscapeMetaChars = isCmdShimRegExp.test(commandFile); - - // Normalize posix paths into OS compatible paths (e.g.: foo/bar -> foo\bar) - // This is necessary otherwise it will always fail with ENOENT in those cases - parsed.command = path.normalize(parsed.command); - - // Escape command & arguments - parsed.command = escape.command(parsed.command); - parsed.args = parsed.args.map((arg) => escape.argument(arg, needsDoubleEscapeMetaChars)); - - const shellCommand = [parsed.command].concat(parsed.args).join(' '); - - parsed.args = ['/d', '/s', '/c', `"${shellCommand}"`]; - parsed.command = process.env.comspec || 'cmd.exe'; - parsed.options.windowsVerbatimArguments = true; // Tell node's spawn that the arguments are already escaped - } - - return parsed; -} - -function parse(command, args, options) { - // Normalize arguments, similar to nodejs - if (args && !Array.isArray(args)) { - options = args; - args = null; - } - - args = args ? args.slice(0) : []; // Clone array to avoid changing the original - options = Object.assign({}, options); // Clone object to avoid changing the original - - // Build our parsed object - const parsed = { - command, - args, - options, - file: undefined, - original: { - command, - args, - }, - }; - - // Delegate further parsing to shell or non-shell - return options.shell ? parsed : parseNonShell(parsed); -} - -module.exports = parse; - - -/***/ }), - -/***/ "../../node_modules/cross-spawn/lib/util/escape.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -// See http://www.robvanderwoude.com/escapechars.php -const metaCharsRegExp = /([()\][%!^"`<>&|;, *?])/g; - -function escapeCommand(arg) { - // Escape meta chars - arg = arg.replace(metaCharsRegExp, '^$1'); - - return arg; -} - -function escapeArgument(arg, doubleEscapeMetaChars) { - // Convert to string - arg = `${arg}`; - - // Algorithm below is based on https://qntm.org/cmd - - // Sequence of backslashes followed by a double quote: - // double up all the backslashes and escape the double quote - arg = arg.replace(/(\\*)"/g, '$1$1\\"'); - - // Sequence of backslashes followed by the end of the string - // (which will become a double quote later): - // double up all the backslashes - arg = arg.replace(/(\\*)$/, '$1$1'); - - // All other backslashes occur literally - - // Quote the whole thing: - arg = `"${arg}"`; - - // Escape meta chars - arg = arg.replace(metaCharsRegExp, '^$1'); - - // Double escape meta chars if necessary - if (doubleEscapeMetaChars) { - arg = arg.replace(metaCharsRegExp, '^$1'); - } - - return arg; -} - -module.exports.command = escapeCommand; -module.exports.argument = escapeArgument; - - -/***/ }), - -/***/ "../../node_modules/cross-spawn/lib/util/readShebang.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const fs = __webpack_require__("fs"); -const shebangCommand = __webpack_require__("../../node_modules/shebang-command/index.js"); - -function readShebang(command) { - // Read the first 150 bytes from the file - const size = 150; - const buffer = Buffer.alloc(size); - - let fd; - - try { - fd = fs.openSync(command, 'r'); - fs.readSync(fd, buffer, 0, size, 0); - fs.closeSync(fd); - } catch (e) { /* Empty */ } - - // Attempt to extract shebang (null is returned if not a shebang) - return shebangCommand(buffer.toString()); -} - -module.exports = readShebang; - - -/***/ }), - -/***/ "../../node_modules/cross-spawn/lib/util/resolveCommand.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const path = __webpack_require__("path"); -const which = __webpack_require__("../../node_modules/which/which.js"); -const getPathKey = __webpack_require__("../../node_modules/cross-spawn/node_modules/path-key/index.js"); - -function resolveCommandAttempt(parsed, withoutPathExt) { - const env = parsed.options.env || process.env; - const cwd = process.cwd(); - const hasCustomCwd = parsed.options.cwd != null; - // Worker threads do not have process.chdir() - const shouldSwitchCwd = hasCustomCwd && process.chdir !== undefined && !process.chdir.disabled; - - // If a custom `cwd` was specified, we need to change the process cwd - // because `which` will do stat calls but does not support a custom cwd - if (shouldSwitchCwd) { - try { - process.chdir(parsed.options.cwd); - } catch (err) { - /* Empty */ - } - } - - let resolved; - - try { - resolved = which.sync(parsed.command, { - path: env[getPathKey({ env })], - pathExt: withoutPathExt ? path.delimiter : undefined, - }); - } catch (e) { - /* Empty */ - } finally { - if (shouldSwitchCwd) { - process.chdir(cwd); - } - } - - // If we successfully resolved, ensure that an absolute path is returned - // Note that when a custom `cwd` was used, we need to resolve to an absolute path based on it - if (resolved) { - resolved = path.resolve(hasCustomCwd ? parsed.options.cwd : '', resolved); - } - - return resolved; -} - -function resolveCommand(parsed) { - return resolveCommandAttempt(parsed) || resolveCommandAttempt(parsed, true); -} - -module.exports = resolveCommand; - - -/***/ }), - -/***/ "../../node_modules/cross-spawn/node_modules/path-key/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const pathKey = (options = {}) => { - const environment = options.env || process.env; - const platform = options.platform || process.platform; - - if (platform !== 'win32') { - return 'PATH'; - } - - return Object.keys(environment).find(key => key.toUpperCase() === 'PATH') || 'Path'; -}; - -module.exports = pathKey; -// TODO: Remove this for the next major release -module.exports.default = pathKey; - - -/***/ }), - -/***/ "../../node_modules/debug/node_modules/ms/index.js": -/***/ (function(module, exports) { - -/** - * Helpers. - */ - -var s = 1000; -var m = s * 60; -var h = m * 60; -var d = h * 24; -var y = d * 365.25; - -/** - * Parse or format the given `val`. - * - * Options: - * - * - `long` verbose formatting [false] - * - * @param {String|Number} val - * @param {Object} [options] - * @throws {Error} throw an error if val is not a non-empty string or a number - * @return {String|Number} - * @api public - */ - -module.exports = function(val, options) { - options = options || {}; - var type = typeof val; - if (type === 'string' && val.length > 0) { - return parse(val); - } else if (type === 'number' && isNaN(val) === false) { - return options.long ? fmtLong(val) : fmtShort(val); - } - throw new Error( - 'val is not a non-empty string or a valid number. val=' + - JSON.stringify(val) - ); -}; - -/** - * Parse the given `str` and return milliseconds. - * - * @param {String} str - * @return {Number} - * @api private - */ - -function parse(str) { - str = String(str); - if (str.length > 100) { - return; - } - var match = /^((?:\d+)?\.?\d+) *(milliseconds?|msecs?|ms|seconds?|secs?|s|minutes?|mins?|m|hours?|hrs?|h|days?|d|years?|yrs?|y)?$/i.exec( - str - ); - if (!match) { - return; - } - var n = parseFloat(match[1]); - var type = (match[2] || 'ms').toLowerCase(); - switch (type) { - case 'years': - case 'year': - case 'yrs': - case 'yr': - case 'y': - return n * y; - case 'days': - case 'day': - case 'd': - return n * d; - case 'hours': - case 'hour': - case 'hrs': - case 'hr': - case 'h': - return n * h; - case 'minutes': - case 'minute': - case 'mins': - case 'min': - case 'm': - return n * m; - case 'seconds': - case 'second': - case 'secs': - case 'sec': - case 's': - return n * s; - case 'milliseconds': - case 'millisecond': - case 'msecs': - case 'msec': - case 'ms': - return n; - default: - return undefined; - } -} - -/** - * Short format for `ms`. - * - * @param {Number} ms - * @return {String} - * @api private - */ - -function fmtShort(ms) { - if (ms >= d) { - return Math.round(ms / d) + 'd'; - } - if (ms >= h) { - return Math.round(ms / h) + 'h'; - } - if (ms >= m) { - return Math.round(ms / m) + 'm'; - } - if (ms >= s) { - return Math.round(ms / s) + 's'; - } - return ms + 'ms'; -} - -/** - * Long format for `ms`. - * - * @param {Number} ms - * @return {String} - * @api private - */ - -function fmtLong(ms) { - return plural(ms, d, 'day') || - plural(ms, h, 'hour') || - plural(ms, m, 'minute') || - plural(ms, s, 'second') || - ms + ' ms'; -} - -/** - * Pluralization helper. - */ - -function plural(ms, n, name) { - if (ms < n) { - return; - } - if (ms < n * 1.5) { - return Math.floor(ms / n) + ' ' + name; - } - return Math.ceil(ms / n) + ' ' + name + 's'; -} - - -/***/ }), - -/***/ "../../node_modules/debug/src/browser.js": -/***/ (function(module, exports, __webpack_require__) { - -/** - * This is the web browser implementation of `debug()`. - * - * Expose `debug()` as the module. - */ - -exports = module.exports = __webpack_require__("../../node_modules/debug/src/debug.js"); -exports.log = log; -exports.formatArgs = formatArgs; -exports.save = save; -exports.load = load; -exports.useColors = useColors; -exports.storage = 'undefined' != typeof chrome - && 'undefined' != typeof chrome.storage - ? chrome.storage.local - : localstorage(); - -/** - * Colors. - */ - -exports.colors = [ - 'lightseagreen', - 'forestgreen', - 'goldenrod', - 'dodgerblue', - 'darkorchid', - 'crimson' -]; - -/** - * Currently only WebKit-based Web Inspectors, Firefox >= v31, - * and the Firebug extension (any Firefox version) are known - * to support "%c" CSS customizations. - * - * TODO: add a `localStorage` variable to explicitly enable/disable colors - */ - -function useColors() { - // NB: In an Electron preload script, document will be defined but not fully - // initialized. Since we know we're in Chrome, we'll just detect this case - // explicitly - if (typeof window !== 'undefined' && window.process && window.process.type === 'renderer') { - return true; - } - - // is webkit? http://stackoverflow.com/a/16459606/376773 - // document is undefined in react-native: https://github.com/facebook/react-native/pull/1632 - return (typeof document !== 'undefined' && document.documentElement && document.documentElement.style && document.documentElement.style.WebkitAppearance) || - // is firebug? http://stackoverflow.com/a/398120/376773 - (typeof window !== 'undefined' && window.console && (window.console.firebug || (window.console.exception && window.console.table))) || - // is firefox >= v31? - // https://developer.mozilla.org/en-US/docs/Tools/Web_Console#Styling_messages - (typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/firefox\/(\d+)/) && parseInt(RegExp.$1, 10) >= 31) || - // double check webkit in userAgent just in case we are in a worker - (typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/applewebkit\/(\d+)/)); -} - -/** - * Map %j to `JSON.stringify()`, since no Web Inspectors do that by default. - */ - -exports.formatters.j = function(v) { - try { - return JSON.stringify(v); - } catch (err) { - return '[UnexpectedJSONParseError]: ' + err.message; - } -}; - - -/** - * Colorize log arguments if enabled. - * - * @api public - */ - -function formatArgs(args) { - var useColors = this.useColors; - - args[0] = (useColors ? '%c' : '') - + this.namespace - + (useColors ? ' %c' : ' ') - + args[0] - + (useColors ? '%c ' : ' ') - + '+' + exports.humanize(this.diff); - - if (!useColors) return; - - var c = 'color: ' + this.color; - args.splice(1, 0, c, 'color: inherit') - - // the final "%c" is somewhat tricky, because there could be other - // arguments passed either before or after the %c, so we need to - // figure out the correct index to insert the CSS into - var index = 0; - var lastC = 0; - args[0].replace(/%[a-zA-Z%]/g, function(match) { - if ('%%' === match) return; - index++; - if ('%c' === match) { - // we only are interested in the *last* %c - // (the user may have provided their own) - lastC = index; - } - }); - - args.splice(lastC, 0, c); -} - -/** - * Invokes `console.log()` when available. - * No-op when `console.log` is not a "function". - * - * @api public - */ - -function log() { - // this hackery is required for IE8/9, where - // the `console.log` function doesn't have 'apply' - return 'object' === typeof console - && console.log - && Function.prototype.apply.call(console.log, console, arguments); -} - -/** - * Save `namespaces`. - * - * @param {String} namespaces - * @api private - */ - -function save(namespaces) { - try { - if (null == namespaces) { - exports.storage.removeItem('debug'); - } else { - exports.storage.debug = namespaces; - } - } catch(e) {} -} - -/** - * Load `namespaces`. - * - * @return {String} returns the previously persisted debug modes - * @api private - */ - -function load() { - var r; - try { - r = exports.storage.debug; - } catch(e) {} - - // If debug isn't set in LS, and we're in Electron, try to load $DEBUG - if (!r && typeof process !== 'undefined' && 'env' in process) { - r = process.env.DEBUG; - } - - return r; -} - -/** - * Enable namespaces listed in `localStorage.debug` initially. - */ - -exports.enable(load()); - -/** - * Localstorage attempts to return the localstorage. - * - * This is necessary because safari throws - * when a user disables cookies/localstorage - * and you attempt to access it. - * - * @return {LocalStorage} - * @api private - */ - -function localstorage() { - try { - return window.localStorage; - } catch (e) {} -} - - -/***/ }), - -/***/ "../../node_modules/debug/src/debug.js": -/***/ (function(module, exports, __webpack_require__) { - - -/** - * This is the common logic for both the Node.js and web browser - * implementations of `debug()`. - * - * Expose `debug()` as the module. - */ - -exports = module.exports = createDebug.debug = createDebug['default'] = createDebug; -exports.coerce = coerce; -exports.disable = disable; -exports.enable = enable; -exports.enabled = enabled; -exports.humanize = __webpack_require__("../../node_modules/debug/node_modules/ms/index.js"); - -/** - * The currently active debug mode names, and names to skip. - */ - -exports.names = []; -exports.skips = []; - -/** - * Map of special "%n" handling functions, for the debug "format" argument. - * - * Valid key names are a single, lower or upper-case letter, i.e. "n" and "N". - */ - -exports.formatters = {}; - -/** - * Previous log timestamp. - */ - -var prevTime; - -/** - * Select a color. - * @param {String} namespace - * @return {Number} - * @api private - */ - -function selectColor(namespace) { - var hash = 0, i; - - for (i in namespace) { - hash = ((hash << 5) - hash) + namespace.charCodeAt(i); - hash |= 0; // Convert to 32bit integer - } - - return exports.colors[Math.abs(hash) % exports.colors.length]; -} - -/** - * Create a debugger with the given `namespace`. - * - * @param {String} namespace - * @return {Function} - * @api public - */ - -function createDebug(namespace) { - - function debug() { - // disabled? - if (!debug.enabled) return; - - var self = debug; - - // set `diff` timestamp - var curr = +new Date(); - var ms = curr - (prevTime || curr); - self.diff = ms; - self.prev = prevTime; - self.curr = curr; - prevTime = curr; - - // turn the `arguments` into a proper Array - var args = new Array(arguments.length); - for (var i = 0; i < args.length; i++) { - args[i] = arguments[i]; - } - - args[0] = exports.coerce(args[0]); - - if ('string' !== typeof args[0]) { - // anything else let's inspect with %O - args.unshift('%O'); - } - - // apply any `formatters` transformations - var index = 0; - args[0] = args[0].replace(/%([a-zA-Z%])/g, function(match, format) { - // if we encounter an escaped % then don't increase the array index - if (match === '%%') return match; - index++; - var formatter = exports.formatters[format]; - if ('function' === typeof formatter) { - var val = args[index]; - match = formatter.call(self, val); - - // now we need to remove `args[index]` since it's inlined in the `format` - args.splice(index, 1); - index--; - } - return match; - }); - - // apply env-specific formatting (colors, etc.) - exports.formatArgs.call(self, args); - - var logFn = debug.log || exports.log || console.log.bind(console); - logFn.apply(self, args); - } - - debug.namespace = namespace; - debug.enabled = exports.enabled(namespace); - debug.useColors = exports.useColors(); - debug.color = selectColor(namespace); - - // env-specific initialization logic for debug instances - if ('function' === typeof exports.init) { - exports.init(debug); - } - - return debug; -} - -/** - * Enables a debug mode by namespaces. This can include modes - * separated by a colon and wildcards. - * - * @param {String} namespaces - * @api public - */ - -function enable(namespaces) { - exports.save(namespaces); - - exports.names = []; - exports.skips = []; - - var split = (typeof namespaces === 'string' ? namespaces : '').split(/[\s,]+/); - var len = split.length; - - for (var i = 0; i < len; i++) { - if (!split[i]) continue; // ignore empty strings - namespaces = split[i].replace(/\*/g, '.*?'); - if (namespaces[0] === '-') { - exports.skips.push(new RegExp('^' + namespaces.substr(1) + '$')); - } else { - exports.names.push(new RegExp('^' + namespaces + '$')); - } - } -} - -/** - * Disable debug output. - * - * @api public - */ - -function disable() { - exports.enable(''); -} - -/** - * Returns true if the given mode name is enabled, false otherwise. - * - * @param {String} name - * @return {Boolean} - * @api public - */ - -function enabled(name) { - var i, len; - for (i = 0, len = exports.skips.length; i < len; i++) { - if (exports.skips[i].test(name)) { - return false; - } - } - for (i = 0, len = exports.names.length; i < len; i++) { - if (exports.names[i].test(name)) { - return true; - } - } - return false; -} - -/** - * Coerce `val`. - * - * @param {Mixed} val - * @return {Mixed} - * @api private - */ - -function coerce(val) { - if (val instanceof Error) return val.stack || val.message; - return val; -} - - -/***/ }), - -/***/ "../../node_modules/debug/src/index.js": -/***/ (function(module, exports, __webpack_require__) { - -/** - * Detect Electron renderer process, which is node, but we should - * treat as a browser. - */ - -if (typeof process !== 'undefined' && process.type === 'renderer') { - module.exports = __webpack_require__("../../node_modules/debug/src/browser.js"); -} else { - module.exports = __webpack_require__("../../node_modules/debug/src/node.js"); -} - - -/***/ }), - -/***/ "../../node_modules/debug/src/node.js": -/***/ (function(module, exports, __webpack_require__) { - -/** - * Module dependencies. - */ - -var tty = __webpack_require__("tty"); -var util = __webpack_require__("util"); - -/** - * This is the Node.js implementation of `debug()`. - * - * Expose `debug()` as the module. - */ - -exports = module.exports = __webpack_require__("../../node_modules/debug/src/debug.js"); -exports.init = init; -exports.log = log; -exports.formatArgs = formatArgs; -exports.save = save; -exports.load = load; -exports.useColors = useColors; - -/** - * Colors. - */ - -exports.colors = [6, 2, 3, 4, 5, 1]; - -/** - * Build up the default `inspectOpts` object from the environment variables. - * - * $ DEBUG_COLORS=no DEBUG_DEPTH=10 DEBUG_SHOW_HIDDEN=enabled node script.js - */ - -exports.inspectOpts = Object.keys(process.env).filter(function (key) { - return /^debug_/i.test(key); -}).reduce(function (obj, key) { - // camel-case - var prop = key - .substring(6) - .toLowerCase() - .replace(/_([a-z])/g, function (_, k) { return k.toUpperCase() }); - - // coerce string value into JS value - var val = process.env[key]; - if (/^(yes|on|true|enabled)$/i.test(val)) val = true; - else if (/^(no|off|false|disabled)$/i.test(val)) val = false; - else if (val === 'null') val = null; - else val = Number(val); - - obj[prop] = val; - return obj; -}, {}); - -/** - * The file descriptor to write the `debug()` calls to. - * Set the `DEBUG_FD` env variable to override with another value. i.e.: - * - * $ DEBUG_FD=3 node script.js 3>debug.log - */ - -var fd = parseInt(process.env.DEBUG_FD, 10) || 2; - -if (1 !== fd && 2 !== fd) { - util.deprecate(function(){}, 'except for stderr(2) and stdout(1), any other usage of DEBUG_FD is deprecated. Override debug.log if you want to use a different log function (https://git.io/debug_fd)')() -} - -var stream = 1 === fd ? process.stdout : - 2 === fd ? process.stderr : - createWritableStdioStream(fd); - -/** - * Is stdout a TTY? Colored output is enabled when `true`. - */ - -function useColors() { - return 'colors' in exports.inspectOpts - ? Boolean(exports.inspectOpts.colors) - : tty.isatty(fd); -} - -/** - * Map %o to `util.inspect()`, all on a single line. - */ - -exports.formatters.o = function(v) { - this.inspectOpts.colors = this.useColors; - return util.inspect(v, this.inspectOpts) - .split('\n').map(function(str) { - return str.trim() - }).join(' '); -}; - -/** - * Map %o to `util.inspect()`, allowing multiple lines if needed. - */ - -exports.formatters.O = function(v) { - this.inspectOpts.colors = this.useColors; - return util.inspect(v, this.inspectOpts); -}; - -/** - * Adds ANSI color escape codes if enabled. - * - * @api public - */ - -function formatArgs(args) { - var name = this.namespace; - var useColors = this.useColors; - - if (useColors) { - var c = this.color; - var prefix = ' \u001b[3' + c + ';1m' + name + ' ' + '\u001b[0m'; - - args[0] = prefix + args[0].split('\n').join('\n' + prefix); - args.push('\u001b[3' + c + 'm+' + exports.humanize(this.diff) + '\u001b[0m'); - } else { - args[0] = new Date().toUTCString() - + ' ' + name + ' ' + args[0]; - } -} - -/** - * Invokes `util.format()` with the specified arguments and writes to `stream`. - */ - -function log() { - return stream.write(util.format.apply(util, arguments) + '\n'); -} - -/** - * Save `namespaces`. - * - * @param {String} namespaces - * @api private - */ - -function save(namespaces) { - if (null == namespaces) { - // If you set a process.env field to null or undefined, it gets cast to the - // string 'null' or 'undefined'. Just delete instead. - delete process.env.DEBUG; - } else { - process.env.DEBUG = namespaces; - } -} - -/** - * Load `namespaces`. - * - * @return {String} returns the previously persisted debug modes - * @api private - */ - -function load() { - return process.env.DEBUG; -} - -/** - * Copied from `node/src/node.js`. - * - * XXX: It's lame that node doesn't expose this API out-of-the-box. It also - * relies on the undocumented `tty_wrap.guessHandleType()` which is also lame. - */ - -function createWritableStdioStream (fd) { - var stream; - var tty_wrap = process.binding('tty_wrap'); - - // Note stream._type is used for test-module-load-list.js - - switch (tty_wrap.guessHandleType(fd)) { - case 'TTY': - stream = new tty.WriteStream(fd); - stream._type = 'tty'; - - // Hack to have stream not keep the event loop alive. - // See https://github.com/joyent/node/issues/1726 - if (stream._handle && stream._handle.unref) { - stream._handle.unref(); - } - break; - - case 'FILE': - var fs = __webpack_require__("fs"); - stream = new fs.SyncWriteStream(fd, { autoClose: false }); - stream._type = 'fs'; - break; - - case 'PIPE': - case 'TCP': - var net = __webpack_require__("net"); - stream = new net.Socket({ - fd: fd, - readable: false, - writable: true - }); - - // FIXME Should probably have an option in net.Socket to create a - // stream from an existing fd which is writable only. But for now - // we'll just add this hack and set the `readable` member to false. - // Test: ./node test/fixtures/echo.js < /etc/passwd - stream.readable = false; - stream.read = null; - stream._type = 'pipe'; - - // FIXME Hack to have stream not keep the event loop alive. - // See https://github.com/joyent/node/issues/1726 - if (stream._handle && stream._handle.unref) { - stream._handle.unref(); - } - break; - - default: - // Probably an error on in uv_guess_handle() - throw new Error('Implement me. Unknown stream file type!'); - } - - // For supporting legacy API we put the FD here. - stream.fd = fd; - - stream._isStdio = true; - - return stream; -} - -/** - * Init logic for `debug` instances. - * - * Create a new `inspectOpts` object in case `useColors` is set - * differently for a particular `debug` instance. - */ - -function init (debug) { - debug.inspectOpts = {}; - - var keys = Object.keys(exports.inspectOpts); - for (var i = 0; i < keys.length; i++) { - debug.inspectOpts[keys[i]] = exports.inspectOpts[keys[i]]; - } -} - -/** - * Enable namespaces listed in `process.env.DEBUG` initially. - */ - -exports.enable(load()); - - -/***/ }), - -/***/ "../../node_modules/dedent/dist/dedent.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -function dedent(strings) { - - var raw = void 0; - if (typeof strings === "string") { - // dedent can be used as a plain function - raw = [strings]; - } else { - raw = strings.raw; - } - - // first, perform interpolation - var result = ""; - for (var i = 0; i < raw.length; i++) { - result += raw[i]. - // join lines when there is a suppressed newline - replace(/\\\n[ \t]*/g, ""). - - // handle escaped backticks - replace(/\\`/g, "`"); - - if (i < (arguments.length <= 1 ? 0 : arguments.length - 1)) { - result += arguments.length <= i + 1 ? undefined : arguments[i + 1]; - } - } - - // now strip indentation - var lines = result.split("\n"); - var mindent = null; - lines.forEach(function (l) { - var m = l.match(/^(\s+)\S+/); - if (m) { - var indent = m[1].length; - if (!mindent) { - // this is the first indented line - mindent = indent; - } else { - mindent = Math.min(mindent, indent); - } - } - }); - - if (mindent !== null) { - result = lines.map(function (l) { - return l[0] === " " ? l.slice(mindent) : l; - }).join("\n"); - } - - // dedent eats leading and trailing whitespace too - result = result.trim(); - - // handle escaped newlines at the end to ensure they don't get stripped too - return result.replace(/\\n/g, "\n"); -} - -if (true) { - module.exports = dedent; -} - - -/***/ }), - -/***/ "../../node_modules/defaults/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var clone = __webpack_require__("../../node_modules/clone/clone.js"); - -module.exports = function(options, defaults) { - options = options || {}; - - Object.keys(defaults).forEach(function(key) { - if (typeof options[key] === 'undefined') { - options[key] = clone(defaults[key]); - } - }); - - return options; -}; - -/***/ }), - -/***/ "../../node_modules/del/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {promisify} = __webpack_require__("util"); -const path = __webpack_require__("path"); -const globby = __webpack_require__("../../node_modules/del/node_modules/globby/index.js"); -const isGlob = __webpack_require__("../../node_modules/is-glob/index.js"); -const slash = __webpack_require__("../../node_modules/slash/index.js"); -const gracefulFs = __webpack_require__("../../node_modules/graceful-fs/graceful-fs.js"); -const isPathCwd = __webpack_require__("../../node_modules/is-path-cwd/index.js"); -const isPathInside = __webpack_require__("../../node_modules/is-path-inside/index.js"); -const rimraf = __webpack_require__("../../node_modules/rimraf/rimraf.js"); -const pMap = __webpack_require__("../../node_modules/del/node_modules/p-map/index.js"); - -const rimrafP = promisify(rimraf); - -const rimrafOptions = { - glob: false, - unlink: gracefulFs.unlink, - unlinkSync: gracefulFs.unlinkSync, - chmod: gracefulFs.chmod, - chmodSync: gracefulFs.chmodSync, - stat: gracefulFs.stat, - statSync: gracefulFs.statSync, - lstat: gracefulFs.lstat, - lstatSync: gracefulFs.lstatSync, - rmdir: gracefulFs.rmdir, - rmdirSync: gracefulFs.rmdirSync, - readdir: gracefulFs.readdir, - readdirSync: gracefulFs.readdirSync -}; - -function safeCheck(file, cwd) { - if (isPathCwd(file)) { - throw new Error('Cannot delete the current working directory. Can be overridden with the `force` option.'); - } - - if (!isPathInside(file, cwd)) { - throw new Error('Cannot delete files/directories outside the current working directory. Can be overridden with the `force` option.'); - } -} - -function normalizePatterns(patterns) { - patterns = Array.isArray(patterns) ? patterns : [patterns]; - - patterns = patterns.map(pattern => { - if (process.platform === 'win32' && isGlob(pattern) === false) { - return slash(pattern); - } - - return pattern; - }); - - return patterns; -} - -module.exports = async (patterns, {force, dryRun, cwd = process.cwd(), ...options} = {}) => { - options = { - expandDirectories: false, - onlyFiles: false, - followSymbolicLinks: false, - cwd, - ...options - }; - - patterns = normalizePatterns(patterns); - - const files = (await globby(patterns, options)) - .sort((a, b) => b.localeCompare(a)); - - const mapper = async file => { - file = path.resolve(cwd, file); - - if (!force) { - safeCheck(file, cwd); - } - - if (!dryRun) { - await rimrafP(file, rimrafOptions); - } - - return file; - }; - - const removedFiles = await pMap(files, mapper, options); - - removedFiles.sort((a, b) => a.localeCompare(b)); - - return removedFiles; -}; - -module.exports.sync = (patterns, {force, dryRun, cwd = process.cwd(), ...options} = {}) => { - options = { - expandDirectories: false, - onlyFiles: false, - followSymbolicLinks: false, - cwd, - ...options - }; - - patterns = normalizePatterns(patterns); - - const files = globby.sync(patterns, options) - .sort((a, b) => b.localeCompare(a)); - - const removedFiles = files.map(file => { - file = path.resolve(cwd, file); - - if (!force) { - safeCheck(file, cwd); - } - - if (!dryRun) { - rimraf.sync(file, rimrafOptions); - } - - return file; - }); - - removedFiles.sort((a, b) => a.localeCompare(b)); - - return removedFiles; -}; - - -/***/ }), - -/***/ "../../node_modules/del/node_modules/aggregate-error/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const indentString = __webpack_require__("../../node_modules/del/node_modules/indent-string/index.js"); -const cleanStack = __webpack_require__("../../node_modules/clean-stack/index.js"); - -const cleanInternalStack = stack => stack.replace(/\s+at .*aggregate-error\/index.js:\d+:\d+\)?/g, ''); - -class AggregateError extends Error { - constructor(errors) { - if (!Array.isArray(errors)) { - throw new TypeError(`Expected input to be an Array, got ${typeof errors}`); - } - - errors = [...errors].map(error => { - if (error instanceof Error) { - return error; - } - - if (error !== null && typeof error === 'object') { - // Handle plain error objects with message property and/or possibly other metadata - return Object.assign(new Error(error.message), error); - } - - return new Error(error); - }); - - let message = errors - .map(error => { - // The `stack` property is not standardized, so we can't assume it exists - return typeof error.stack === 'string' ? cleanInternalStack(cleanStack(error.stack)) : String(error); - }) - .join('\n'); - message = '\n' + indentString(message, 4); - super(message); - - this.name = 'AggregateError'; - - Object.defineProperty(this, '_errors', {value: errors}); - } - - * [Symbol.iterator]() { - for (const error of this._errors) { - yield error; - } - } -} - -module.exports = AggregateError; - - -/***/ }), - -/***/ "../../node_modules/del/node_modules/globby/gitignore.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {promisify} = __webpack_require__("util"); -const fs = __webpack_require__("fs"); -const path = __webpack_require__("path"); -const fastGlob = __webpack_require__("../../node_modules/fast-glob/out/index.js"); -const gitIgnore = __webpack_require__("../../node_modules/ignore/index.js"); -const slash = __webpack_require__("../../node_modules/slash/index.js"); - -const DEFAULT_IGNORE = [ - '**/node_modules/**', - '**/flow-typed/**', - '**/coverage/**', - '**/.git' -]; - -const readFileP = promisify(fs.readFile); - -const mapGitIgnorePatternTo = base => ignore => { - if (ignore.startsWith('!')) { - return '!' + path.posix.join(base, ignore.slice(1)); - } - - return path.posix.join(base, ignore); -}; - -const parseGitIgnore = (content, options) => { - const base = slash(path.relative(options.cwd, path.dirname(options.fileName))); - - return content - .split(/\r?\n/) - .filter(Boolean) - .filter(line => !line.startsWith('#')) - .map(mapGitIgnorePatternTo(base)); -}; - -const reduceIgnore = files => { - return files.reduce((ignores, file) => { - ignores.add(parseGitIgnore(file.content, { - cwd: file.cwd, - fileName: file.filePath - })); - return ignores; - }, gitIgnore()); -}; - -const ensureAbsolutePathForCwd = (cwd, p) => { - if (path.isAbsolute(p)) { - if (p.startsWith(cwd)) { - return p; - } - - throw new Error(`Path ${p} is not in cwd ${cwd}`); - } - - return path.join(cwd, p); -}; - -const getIsIgnoredPredecate = (ignores, cwd) => { - return p => ignores.ignores(slash(path.relative(cwd, ensureAbsolutePathForCwd(cwd, p)))); -}; - -const getFile = async (file, cwd) => { - const filePath = path.join(cwd, file); - const content = await readFileP(filePath, 'utf8'); - - return { - cwd, - filePath, - content - }; -}; - -const getFileSync = (file, cwd) => { - const filePath = path.join(cwd, file); - const content = fs.readFileSync(filePath, 'utf8'); - - return { - cwd, - filePath, - content - }; -}; - -const normalizeOptions = ({ - ignore = [], - cwd = slash(process.cwd()) -} = {}) => { - return {ignore, cwd}; -}; - -module.exports = async options => { - options = normalizeOptions(options); - - const paths = await fastGlob('**/.gitignore', { - ignore: DEFAULT_IGNORE.concat(options.ignore), - cwd: options.cwd - }); - - const files = await Promise.all(paths.map(file => getFile(file, options.cwd))); - const ignores = reduceIgnore(files); - - return getIsIgnoredPredecate(ignores, options.cwd); -}; - -module.exports.sync = options => { - options = normalizeOptions(options); - - const paths = fastGlob.sync('**/.gitignore', { - ignore: DEFAULT_IGNORE.concat(options.ignore), - cwd: options.cwd - }); - - const files = paths.map(file => getFileSync(file, options.cwd)); - const ignores = reduceIgnore(files); - - return getIsIgnoredPredecate(ignores, options.cwd); -}; - - -/***/ }), - -/***/ "../../node_modules/del/node_modules/globby/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const fs = __webpack_require__("fs"); -const arrayUnion = __webpack_require__("../../node_modules/array-union/index.js"); -const merge2 = __webpack_require__("../../node_modules/merge2/index.js"); -const glob = __webpack_require__("../../node_modules/glob/glob.js"); -const fastGlob = __webpack_require__("../../node_modules/fast-glob/out/index.js"); -const dirGlob = __webpack_require__("../../node_modules/dir-glob/index.js"); -const gitignore = __webpack_require__("../../node_modules/del/node_modules/globby/gitignore.js"); -const {FilterStream, UniqueStream} = __webpack_require__("../../node_modules/del/node_modules/globby/stream-utils.js"); - -const DEFAULT_FILTER = () => false; - -const isNegative = pattern => pattern[0] === '!'; - -const assertPatternsInput = patterns => { - if (!patterns.every(pattern => typeof pattern === 'string')) { - throw new TypeError('Patterns must be a string or an array of strings'); - } -}; - -const checkCwdOption = (options = {}) => { - if (!options.cwd) { - return; - } - - let stat; - try { - stat = fs.statSync(options.cwd); - } catch (_) { - return; - } - - if (!stat.isDirectory()) { - throw new Error('The `cwd` option must be a path to a directory'); - } -}; - -const getPathString = p => p.stats instanceof fs.Stats ? p.path : p; - -const generateGlobTasks = (patterns, taskOptions) => { - patterns = arrayUnion([].concat(patterns)); - assertPatternsInput(patterns); - checkCwdOption(taskOptions); - - const globTasks = []; - - taskOptions = { - ignore: [], - expandDirectories: true, - ...taskOptions - }; - - for (const [index, pattern] of patterns.entries()) { - if (isNegative(pattern)) { - continue; - } - - const ignore = patterns - .slice(index) - .filter(isNegative) - .map(pattern => pattern.slice(1)); - - const options = { - ...taskOptions, - ignore: taskOptions.ignore.concat(ignore) - }; - - globTasks.push({pattern, options}); - } - - return globTasks; -}; - -const globDirs = (task, fn) => { - let options = {}; - if (task.options.cwd) { - options.cwd = task.options.cwd; - } - - if (Array.isArray(task.options.expandDirectories)) { - options = { - ...options, - files: task.options.expandDirectories - }; - } else if (typeof task.options.expandDirectories === 'object') { - options = { - ...options, - ...task.options.expandDirectories - }; - } - - return fn(task.pattern, options); -}; - -const getPattern = (task, fn) => task.options.expandDirectories ? globDirs(task, fn) : [task.pattern]; - -const getFilterSync = options => { - return options && options.gitignore ? - gitignore.sync({cwd: options.cwd, ignore: options.ignore}) : - DEFAULT_FILTER; -}; - -const globToTask = task => glob => { - const {options} = task; - if (options.ignore && Array.isArray(options.ignore) && options.expandDirectories) { - options.ignore = dirGlob.sync(options.ignore); - } - - return { - pattern: glob, - options - }; -}; - -module.exports = async (patterns, options) => { - const globTasks = generateGlobTasks(patterns, options); - - const getFilter = async () => { - return options && options.gitignore ? - gitignore({cwd: options.cwd, ignore: options.ignore}) : - DEFAULT_FILTER; - }; - - const getTasks = async () => { - const tasks = await Promise.all(globTasks.map(async task => { - const globs = await getPattern(task, dirGlob); - return Promise.all(globs.map(globToTask(task))); - })); - - return arrayUnion(...tasks); - }; - - const [filter, tasks] = await Promise.all([getFilter(), getTasks()]); - const paths = await Promise.all(tasks.map(task => fastGlob(task.pattern, task.options))); - - return arrayUnion(...paths).filter(path_ => !filter(getPathString(path_))); -}; - -module.exports.sync = (patterns, options) => { - const globTasks = generateGlobTasks(patterns, options); - - const tasks = globTasks.reduce((tasks, task) => { - const newTask = getPattern(task, dirGlob.sync).map(globToTask(task)); - return tasks.concat(newTask); - }, []); - - const filter = getFilterSync(options); - - return tasks.reduce( - (matches, task) => arrayUnion(matches, fastGlob.sync(task.pattern, task.options)), - [] - ).filter(path_ => !filter(path_)); -}; - -module.exports.stream = (patterns, options) => { - const globTasks = generateGlobTasks(patterns, options); - - const tasks = globTasks.reduce((tasks, task) => { - const newTask = getPattern(task, dirGlob.sync).map(globToTask(task)); - return tasks.concat(newTask); - }, []); - - const filter = getFilterSync(options); - const filterStream = new FilterStream(p => !filter(p)); - const uniqueStream = new UniqueStream(); - - return merge2(tasks.map(task => fastGlob.stream(task.pattern, task.options))) - .pipe(filterStream) - .pipe(uniqueStream); -}; - -module.exports.generateGlobTasks = generateGlobTasks; - -module.exports.hasMagic = (patterns, options) => [] - .concat(patterns) - .some(pattern => glob.hasMagic(pattern, options)); - -module.exports.gitignore = gitignore; - - -/***/ }), - -/***/ "../../node_modules/del/node_modules/globby/stream-utils.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {Transform} = __webpack_require__("stream"); - -class ObjectTransform extends Transform { - constructor() { - super({ - objectMode: true - }); - } -} - -class FilterStream extends ObjectTransform { - constructor(filter) { - super(); - this._filter = filter; - } - - _transform(data, encoding, callback) { - if (this._filter(data)) { - this.push(data); - } - - callback(); - } -} - -class UniqueStream extends ObjectTransform { - constructor() { - super(); - this._pushed = new Set(); - } - - _transform(data, encoding, callback) { - if (!this._pushed.has(data)) { - this.push(data); - this._pushed.add(data); - } - - callback(); - } -} - -module.exports = { - FilterStream, - UniqueStream -}; - - -/***/ }), - -/***/ "../../node_modules/del/node_modules/indent-string/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = (string, count = 1, options) => { - options = { - indent: ' ', - includeEmptyLines: false, - ...options - }; - - if (typeof string !== 'string') { - throw new TypeError( - `Expected \`input\` to be a \`string\`, got \`${typeof string}\`` - ); - } - - if (typeof count !== 'number') { - throw new TypeError( - `Expected \`count\` to be a \`number\`, got \`${typeof count}\`` - ); - } - - if (typeof options.indent !== 'string') { - throw new TypeError( - `Expected \`options.indent\` to be a \`string\`, got \`${typeof options.indent}\`` - ); - } - - if (count === 0) { - return string; - } - - const regex = options.includeEmptyLines ? /^/gm : /^(?!\s*$)/gm; - - return string.replace(regex, options.indent.repeat(count)); -}; - - -/***/ }), - -/***/ "../../node_modules/del/node_modules/p-map/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const AggregateError = __webpack_require__("../../node_modules/del/node_modules/aggregate-error/index.js"); - -module.exports = async ( - iterable, - mapper, - { - concurrency = Infinity, - stopOnError = true - } = {} -) => { - return new Promise((resolve, reject) => { - if (typeof mapper !== 'function') { - throw new TypeError('Mapper function is required'); - } - - if (!(typeof concurrency === 'number' && concurrency >= 1)) { - throw new TypeError(`Expected \`concurrency\` to be a number from 1 and up, got \`${concurrency}\` (${typeof concurrency})`); - } - - const ret = []; - const errors = []; - const iterator = iterable[Symbol.iterator](); - let isRejected = false; - let isIterableDone = false; - let resolvingCount = 0; - let currentIndex = 0; - - const next = () => { - if (isRejected) { - return; - } - - const nextItem = iterator.next(); - const i = currentIndex; - currentIndex++; - - if (nextItem.done) { - isIterableDone = true; - - if (resolvingCount === 0) { - if (!stopOnError && errors.length !== 0) { - reject(new AggregateError(errors)); - } else { - resolve(ret); - } - } - - return; - } - - resolvingCount++; - - (async () => { - try { - const element = await nextItem.value; - ret[i] = await mapper(element, i); - resolvingCount--; - next(); - } catch (error) { - if (stopOnError) { - isRejected = true; - reject(error); - } else { - errors.push(error); - resolvingCount--; - next(); - } - } - })(); - }; - - for (let i = 0; i < concurrency; i++) { - next(); - - if (isIterableDone) { - break; - } - } - }); -}; - - -/***/ }), - -/***/ "../../node_modules/delayed-stream/lib/delayed_stream.js": -/***/ (function(module, exports, __webpack_require__) { - -var Stream = __webpack_require__("stream").Stream; -var util = __webpack_require__("util"); - -module.exports = DelayedStream; -function DelayedStream() { - this.source = null; - this.dataSize = 0; - this.maxDataSize = 1024 * 1024; - this.pauseStream = true; - - this._maxDataSizeExceeded = false; - this._released = false; - this._bufferedEvents = []; -} -util.inherits(DelayedStream, Stream); - -DelayedStream.create = function(source, options) { - var delayedStream = new this(); - - options = options || {}; - for (var option in options) { - delayedStream[option] = options[option]; - } - - delayedStream.source = source; - - var realEmit = source.emit; - source.emit = function() { - delayedStream._handleEmit(arguments); - return realEmit.apply(source, arguments); - }; - - source.on('error', function() {}); - if (delayedStream.pauseStream) { - source.pause(); - } - - return delayedStream; -}; - -Object.defineProperty(DelayedStream.prototype, 'readable', { - configurable: true, - enumerable: true, - get: function() { - return this.source.readable; - } -}); - -DelayedStream.prototype.setEncoding = function() { - return this.source.setEncoding.apply(this.source, arguments); -}; - -DelayedStream.prototype.resume = function() { - if (!this._released) { - this.release(); - } - - this.source.resume(); -}; - -DelayedStream.prototype.pause = function() { - this.source.pause(); -}; - -DelayedStream.prototype.release = function() { - this._released = true; - - this._bufferedEvents.forEach(function(args) { - this.emit.apply(this, args); - }.bind(this)); - this._bufferedEvents = []; -}; - -DelayedStream.prototype.pipe = function() { - var r = Stream.prototype.pipe.apply(this, arguments); - this.resume(); - return r; -}; - -DelayedStream.prototype._handleEmit = function(args) { - if (this._released) { - this.emit.apply(this, args); - return; - } - - if (args[0] === 'data') { - this.dataSize += args[1].length; - this._checkIfMaxDataSizeExceeded(); - } - - this._bufferedEvents.push(args); -}; - -DelayedStream.prototype._checkIfMaxDataSizeExceeded = function() { - if (this._maxDataSizeExceeded) { - return; - } - - if (this.dataSize <= this.maxDataSize) { - return; - } - - this._maxDataSizeExceeded = true; - var message = - 'DelayedStream#maxDataSize of ' + this.maxDataSize + ' bytes exceeded.' - this.emit('error', new Error(message)); -}; - - -/***/ }), - -/***/ "../../node_modules/detect-indent/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -// Detect either spaces or tabs but not both to properly handle tabs for indentation and spaces for alignment -const INDENT_REGEX = /^(?:( )+|\t+)/; - -const INDENT_TYPE_SPACE = 'space'; -const INDENT_TYPE_TAB = 'tab'; - -// Make a Map that counts how many indents/unindents have occurred for a given size and how many lines follow a given indentation. -// The key is a concatenation of the indentation type (s = space and t = tab) and the size of the indents/unindents. -// -// indents = { -// t3: [1, 0], -// t4: [1, 5], -// s5: [1, 0], -// s12: [1, 0], -// } -function makeIndentsMap(string, ignoreSingleSpaces) { - const indents = new Map(); - - // Remember the size of previous line's indentation - let previousSize = 0; - let previousIndentType; - - // Indents key (ident type + size of the indents/unindents) - let key; - - for (const line of string.split(/\n/g)) { - if (!line) { - // Ignore empty lines - continue; - } - - let indent; - let indentType; - let weight; - let entry; - const matches = line.match(INDENT_REGEX); - - if (matches === null) { - previousSize = 0; - previousIndentType = ''; - } else { - indent = matches[0].length; - - if (matches[1]) { - indentType = INDENT_TYPE_SPACE; - } else { - indentType = INDENT_TYPE_TAB; - } - - // Ignore single space unless it's the only indent detected to prevent common false positives - if (ignoreSingleSpaces && indentType === INDENT_TYPE_SPACE && indent === 1) { - continue; - } - - if (indentType !== previousIndentType) { - previousSize = 0; - } - - previousIndentType = indentType; - - weight = 0; - - const indentDifference = indent - previousSize; - previousSize = indent; - - // Previous line have same indent? - if (indentDifference === 0) { - weight++; - // We use the key from previous loop - } else { - const absoluteIndentDifference = indentDifference > 0 ? indentDifference : -indentDifference; - key = encodeIndentsKey(indentType, absoluteIndentDifference); - } - - // Update the stats - entry = indents.get(key); - - if (entry === undefined) { - entry = [1, 0]; // Init - } else { - entry = [++entry[0], entry[1] + weight]; - } - - indents.set(key, entry); - } - } - - return indents; -} - -// Encode the indent type and amount as a string (e.g. 's4') for use as a compound key in the indents Map. -function encodeIndentsKey(indentType, indentAmount) { - const typeCharacter = indentType === INDENT_TYPE_SPACE ? 's' : 't'; - return typeCharacter + String(indentAmount); -} - -// Extract the indent type and amount from a key of the indents Map. -function decodeIndentsKey(indentsKey) { - const keyHasTypeSpace = indentsKey[0] === 's'; - const type = keyHasTypeSpace ? INDENT_TYPE_SPACE : INDENT_TYPE_TAB; - - const amount = Number(indentsKey.slice(1)); - - return {type, amount}; -} - -// Return the key (e.g. 's4') from the indents Map that represents the most common indent, -// or return undefined if there are no indents. -function getMostUsedKey(indents) { - let result; - let maxUsed = 0; - let maxWeight = 0; - - for (const [key, [usedCount, weight]] of indents) { - if (usedCount > maxUsed || (usedCount === maxUsed && weight > maxWeight)) { - maxUsed = usedCount; - maxWeight = weight; - result = key; - } - } - - return result; -} - -function makeIndentString(type, amount) { - const indentCharacter = type === INDENT_TYPE_SPACE ? ' ' : '\t'; - return indentCharacter.repeat(amount); -} - -module.exports = string => { - if (typeof string !== 'string') { - throw new TypeError('Expected a string'); - } - - // Identify indents while skipping single space indents to avoid common edge cases (e.g. code comments) - // If no indents are identified, run again and include all indents for comprehensive detection - let indents = makeIndentsMap(string, true); - if (indents.size === 0) { - indents = makeIndentsMap(string, false); - } - - const keyOfMostUsedIndent = getMostUsedKey(indents); - - let type; - let amount = 0; - let indent = ''; - - if (keyOfMostUsedIndent !== undefined) { - ({type, amount} = decodeIndentsKey(keyOfMostUsedIndent)); - indent = makeIndentString(type, amount); - } - - return { - amount, - type, - indent - }; -}; - - -/***/ }), - -/***/ "../../node_modules/detect-newline/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const detectNewline = string => { - if (typeof string !== 'string') { - throw new TypeError('Expected a string'); - } - - const newlines = string.match(/(?:\r?\n)/g) || []; - - if (newlines.length === 0) { - return; - } - - const crlf = newlines.filter(newline => newline === '\r\n').length; - const lf = newlines.length - crlf; - - return crlf > lf ? '\r\n' : '\n'; -}; - -module.exports = detectNewline; -module.exports.graceful = string => (typeof string === 'string' && detectNewline(string)) || '\n'; - - -/***/ }), - -/***/ "../../node_modules/dir-glob/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); -const pathType = __webpack_require__("../../node_modules/path-type/index.js"); - -const getExtensions = extensions => extensions.length > 1 ? `{${extensions.join(',')}}` : extensions[0]; - -const getPath = (filepath, cwd) => { - const pth = filepath[0] === '!' ? filepath.slice(1) : filepath; - return path.isAbsolute(pth) ? pth : path.join(cwd, pth); -}; - -const addExtensions = (file, extensions) => { - if (path.extname(file)) { - return `**/${file}`; - } - - return `**/${file}.${getExtensions(extensions)}`; -}; - -const getGlob = (directory, options) => { - if (options.files && !Array.isArray(options.files)) { - throw new TypeError(`Expected \`files\` to be of type \`Array\` but received type \`${typeof options.files}\``); - } - - if (options.extensions && !Array.isArray(options.extensions)) { - throw new TypeError(`Expected \`extensions\` to be of type \`Array\` but received type \`${typeof options.extensions}\``); - } - - if (options.files && options.extensions) { - return options.files.map(x => path.posix.join(directory, addExtensions(x, options.extensions))); - } - - if (options.files) { - return options.files.map(x => path.posix.join(directory, `**/${x}`)); - } - - if (options.extensions) { - return [path.posix.join(directory, `**/*.${getExtensions(options.extensions)}`)]; - } - - return [path.posix.join(directory, '**')]; -}; - -module.exports = async (input, options) => { - options = { - cwd: process.cwd(), - ...options - }; - - if (typeof options.cwd !== 'string') { - throw new TypeError(`Expected \`cwd\` to be of type \`string\` but received type \`${typeof options.cwd}\``); - } - - const globs = await Promise.all([].concat(input).map(async x => { - const isDirectory = await pathType.isDirectory(getPath(x, options.cwd)); - return isDirectory ? getGlob(x, options) : x; - })); - - return [].concat.apply([], globs); // eslint-disable-line prefer-spread -}; - -module.exports.sync = (input, options) => { - options = { - cwd: process.cwd(), - ...options - }; - - if (typeof options.cwd !== 'string') { - throw new TypeError(`Expected \`cwd\` to be of type \`string\` but received type \`${typeof options.cwd}\``); - } - - const globs = [].concat(input).map(x => pathType.isDirectorySync(getPath(x, options.cwd)) ? getGlob(x, options) : x); - - return [].concat.apply([], globs); // eslint-disable-line prefer-spread -}; - - -/***/ }), - -/***/ "../../node_modules/duplexer/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var Stream = __webpack_require__("stream") -var writeMethods = ["write", "end", "destroy"] -var readMethods = ["resume", "pause"] -var readEvents = ["data", "close"] -var slice = Array.prototype.slice - -module.exports = duplex - -function forEach (arr, fn) { - if (arr.forEach) { - return arr.forEach(fn) - } - - for (var i = 0; i < arr.length; i++) { - fn(arr[i], i) - } -} - -function duplex(writer, reader) { - var stream = new Stream() - var ended = false - - forEach(writeMethods, proxyWriter) - - forEach(readMethods, proxyReader) - - forEach(readEvents, proxyStream) - - reader.on("end", handleEnd) - - writer.on("drain", function() { - stream.emit("drain") - }) - - writer.on("error", reemit) - reader.on("error", reemit) - - stream.writable = writer.writable - stream.readable = reader.readable - - return stream - - function proxyWriter(methodName) { - stream[methodName] = method - - function method() { - return writer[methodName].apply(writer, arguments) - } - } - - function proxyReader(methodName) { - stream[methodName] = method - - function method() { - stream.emit(methodName) - var func = reader[methodName] - if (func) { - return func.apply(reader, arguments) - } - reader.emit(methodName) - } - } - - function proxyStream(methodName) { - reader.on(methodName, reemit) - - function reemit() { - var args = slice.call(arguments) - args.unshift(methodName) - stream.emit.apply(stream, args) - } - } - - function handleEnd() { - if (ended) { - return - } - ended = true - var args = slice.call(arguments) - args.unshift("end") - stream.emit.apply(stream, args) - } - - function reemit(err) { - stream.emit("error", err) - } -} - - -/***/ }), - -/***/ "../../node_modules/end-of-stream/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var once = __webpack_require__("../../node_modules/once/once.js"); - -var noop = function() {}; - -var isRequest = function(stream) { - return stream.setHeader && typeof stream.abort === 'function'; -}; - -var isChildProcess = function(stream) { - return stream.stdio && Array.isArray(stream.stdio) && stream.stdio.length === 3 -}; - -var eos = function(stream, opts, callback) { - if (typeof opts === 'function') return eos(stream, null, opts); - if (!opts) opts = {}; - - callback = once(callback || noop); - - var ws = stream._writableState; - var rs = stream._readableState; - var readable = opts.readable || (opts.readable !== false && stream.readable); - var writable = opts.writable || (opts.writable !== false && stream.writable); - var cancelled = false; - - var onlegacyfinish = function() { - if (!stream.writable) onfinish(); - }; - - var onfinish = function() { - writable = false; - if (!readable) callback.call(stream); - }; - - var onend = function() { - readable = false; - if (!writable) callback.call(stream); - }; - - var onexit = function(exitCode) { - callback.call(stream, exitCode ? new Error('exited with error code: ' + exitCode) : null); - }; - - var onerror = function(err) { - callback.call(stream, err); - }; - - var onclose = function() { - process.nextTick(onclosenexttick); - }; - - var onclosenexttick = function() { - if (cancelled) return; - if (readable && !(rs && (rs.ended && !rs.destroyed))) return callback.call(stream, new Error('premature close')); - if (writable && !(ws && (ws.ended && !ws.destroyed))) return callback.call(stream, new Error('premature close')); - }; - - var onrequest = function() { - stream.req.on('finish', onfinish); - }; - - if (isRequest(stream)) { - stream.on('complete', onfinish); - stream.on('abort', onclose); - if (stream.req) onrequest(); - else stream.on('request', onrequest); - } else if (writable && !ws) { // legacy streams - stream.on('end', onlegacyfinish); - stream.on('close', onlegacyfinish); - } - - if (isChildProcess(stream)) stream.on('exit', onexit); - - stream.on('end', onend); - stream.on('finish', onfinish); - if (opts.error !== false) stream.on('error', onerror); - stream.on('close', onclose); - - return function() { - cancelled = true; - stream.removeListener('complete', onfinish); - stream.removeListener('abort', onclose); - stream.removeListener('request', onrequest); - if (stream.req) stream.req.removeListener('finish', onfinish); - stream.removeListener('end', onlegacyfinish); - stream.removeListener('close', onlegacyfinish); - stream.removeListener('finish', onfinish); - stream.removeListener('exit', onexit); - stream.removeListener('end', onend); - stream.removeListener('error', onerror); - stream.removeListener('close', onclose); - }; -}; - -module.exports = eos; - - -/***/ }), - -/***/ "../../node_modules/error-ex/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var util = __webpack_require__("util"); -var isArrayish = __webpack_require__("../../node_modules/is-arrayish/index.js"); - -var errorEx = function errorEx(name, properties) { - if (!name || name.constructor !== String) { - properties = name || {}; - name = Error.name; - } - - var errorExError = function ErrorEXError(message) { - if (!this) { - return new ErrorEXError(message); - } - - message = message instanceof Error - ? message.message - : (message || this.message); - - Error.call(this, message); - Error.captureStackTrace(this, errorExError); - - this.name = name; - - Object.defineProperty(this, 'message', { - configurable: true, - enumerable: false, - get: function () { - var newMessage = message.split(/\r?\n/g); - - for (var key in properties) { - if (!properties.hasOwnProperty(key)) { - continue; - } - - var modifier = properties[key]; - - if ('message' in modifier) { - newMessage = modifier.message(this[key], newMessage) || newMessage; - if (!isArrayish(newMessage)) { - newMessage = [newMessage]; - } - } - } - - return newMessage.join('\n'); - }, - set: function (v) { - message = v; - } - }); - - var stackDescriptor = Object.getOwnPropertyDescriptor(this, 'stack'); - var stackGetter = stackDescriptor.get; - var stackValue = stackDescriptor.value; - delete stackDescriptor.value; - delete stackDescriptor.writable; - - stackDescriptor.get = function () { - var stack = (stackGetter) - ? stackGetter.call(this).split(/\r?\n+/g) - : stackValue.split(/\r?\n+/g); - - // starting in Node 7, the stack builder caches the message. - // just replace it. - stack[0] = this.name + ': ' + this.message; - - var lineCount = 1; - for (var key in properties) { - if (!properties.hasOwnProperty(key)) { - continue; - } - - var modifier = properties[key]; - - if ('line' in modifier) { - var line = modifier.line(this[key]); - if (line) { - stack.splice(lineCount++, 0, ' ' + line); - } - } - - if ('stack' in modifier) { - modifier.stack(this[key], stack); - } - } - - return stack.join('\n'); - }; - - Object.defineProperty(this, 'stack', stackDescriptor); - }; - - if (Object.setPrototypeOf) { - Object.setPrototypeOf(errorExError.prototype, Error.prototype); - Object.setPrototypeOf(errorExError, Error); - } else { - util.inherits(errorExError, Error); - } - - return errorExError; -}; - -errorEx.append = function (str, def) { - return { - message: function (v, message) { - v = v || def; - - if (v) { - message[0] += ' ' + str.replace('%s', v.toString()); - } - - return message; - } - }; -}; - -errorEx.line = function (str, def) { - return { - line: function (v) { - v = v || def; - - if (v) { - return str.replace('%s', v.toString()); - } - - return null; - } - }; -}; - -module.exports = errorEx; - - -/***/ }), - -/***/ "../../node_modules/escape-string-regexp/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var matchOperatorsRe = /[|\\{}()[\]^$+*?.]/g; - -module.exports = function (str) { - if (typeof str !== 'string') { - throw new TypeError('Expected a string'); - } - - return str.replace(matchOperatorsRe, '\\$&'); -}; - - -/***/ }), - -/***/ "../../node_modules/execa/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); -const childProcess = __webpack_require__("child_process"); -const crossSpawn = __webpack_require__("../../node_modules/cross-spawn/index.js"); -const stripFinalNewline = __webpack_require__("../../node_modules/strip-final-newline/index.js"); -const npmRunPath = __webpack_require__("../../node_modules/npm-run-path/index.js"); -const onetime = __webpack_require__("../../node_modules/onetime/index.js"); -const makeError = __webpack_require__("../../node_modules/execa/lib/error.js"); -const normalizeStdio = __webpack_require__("../../node_modules/execa/lib/stdio.js"); -const {spawnedKill, spawnedCancel, setupTimeout, setExitHandler} = __webpack_require__("../../node_modules/execa/lib/kill.js"); -const {handleInput, getSpawnedResult, makeAllStream, validateInputSync} = __webpack_require__("../../node_modules/execa/lib/stream.js"); -const {mergePromise, getSpawnedPromise} = __webpack_require__("../../node_modules/execa/lib/promise.js"); -const {joinCommand, parseCommand} = __webpack_require__("../../node_modules/execa/lib/command.js"); - -const DEFAULT_MAX_BUFFER = 1000 * 1000 * 100; - -const getEnv = ({env: envOption, extendEnv, preferLocal, localDir, execPath}) => { - const env = extendEnv ? {...process.env, ...envOption} : envOption; - - if (preferLocal) { - return npmRunPath.env({env, cwd: localDir, execPath}); - } - - return env; -}; - -const handleArguments = (file, args, options = {}) => { - const parsed = crossSpawn._parse(file, args, options); - file = parsed.command; - args = parsed.args; - options = parsed.options; - - options = { - maxBuffer: DEFAULT_MAX_BUFFER, - buffer: true, - stripFinalNewline: true, - extendEnv: true, - preferLocal: false, - localDir: options.cwd || process.cwd(), - execPath: process.execPath, - encoding: 'utf8', - reject: true, - cleanup: true, - all: false, - windowsHide: true, - ...options - }; - - options.env = getEnv(options); - - options.stdio = normalizeStdio(options); - - if (process.platform === 'win32' && path.basename(file, '.exe') === 'cmd') { - // #116 - args.unshift('/q'); - } - - return {file, args, options, parsed}; -}; - -const handleOutput = (options, value, error) => { - if (typeof value !== 'string' && !Buffer.isBuffer(value)) { - // When `execa.sync()` errors, we normalize it to '' to mimic `execa()` - return error === undefined ? undefined : ''; - } - - if (options.stripFinalNewline) { - return stripFinalNewline(value); - } - - return value; -}; - -const execa = (file, args, options) => { - const parsed = handleArguments(file, args, options); - const command = joinCommand(file, args); - - let spawned; - try { - spawned = childProcess.spawn(parsed.file, parsed.args, parsed.options); - } catch (error) { - // Ensure the returned error is always both a promise and a child process - const dummySpawned = new childProcess.ChildProcess(); - const errorPromise = Promise.reject(makeError({ - error, - stdout: '', - stderr: '', - all: '', - command, - parsed, - timedOut: false, - isCanceled: false, - killed: false - })); - return mergePromise(dummySpawned, errorPromise); - } - - const spawnedPromise = getSpawnedPromise(spawned); - const timedPromise = setupTimeout(spawned, parsed.options, spawnedPromise); - const processDone = setExitHandler(spawned, parsed.options, timedPromise); - - const context = {isCanceled: false}; - - spawned.kill = spawnedKill.bind(null, spawned.kill.bind(spawned)); - spawned.cancel = spawnedCancel.bind(null, spawned, context); - - const handlePromise = async () => { - const [{error, exitCode, signal, timedOut}, stdoutResult, stderrResult, allResult] = await getSpawnedResult(spawned, parsed.options, processDone); - const stdout = handleOutput(parsed.options, stdoutResult); - const stderr = handleOutput(parsed.options, stderrResult); - const all = handleOutput(parsed.options, allResult); - - if (error || exitCode !== 0 || signal !== null) { - const returnedError = makeError({ - error, - exitCode, - signal, - stdout, - stderr, - all, - command, - parsed, - timedOut, - isCanceled: context.isCanceled, - killed: spawned.killed - }); - - if (!parsed.options.reject) { - return returnedError; - } - - throw returnedError; - } - - return { - command, - exitCode: 0, - stdout, - stderr, - all, - failed: false, - timedOut: false, - isCanceled: false, - killed: false - }; - }; - - const handlePromiseOnce = onetime(handlePromise); - - crossSpawn._enoent.hookChildProcess(spawned, parsed.parsed); - - handleInput(spawned, parsed.options.input); - - spawned.all = makeAllStream(spawned, parsed.options); - - return mergePromise(spawned, handlePromiseOnce); -}; - -module.exports = execa; - -module.exports.sync = (file, args, options) => { - const parsed = handleArguments(file, args, options); - const command = joinCommand(file, args); - - validateInputSync(parsed.options); - - let result; - try { - result = childProcess.spawnSync(parsed.file, parsed.args, parsed.options); - } catch (error) { - throw makeError({ - error, - stdout: '', - stderr: '', - all: '', - command, - parsed, - timedOut: false, - isCanceled: false, - killed: false - }); - } - - const stdout = handleOutput(parsed.options, result.stdout, result.error); - const stderr = handleOutput(parsed.options, result.stderr, result.error); - - if (result.error || result.status !== 0 || result.signal !== null) { - const error = makeError({ - stdout, - stderr, - error: result.error, - signal: result.signal, - exitCode: result.status, - command, - parsed, - timedOut: result.error && result.error.code === 'ETIMEDOUT', - isCanceled: false, - killed: result.signal !== null - }); - - if (!parsed.options.reject) { - return error; - } - - throw error; - } - - return { - command, - exitCode: 0, - stdout, - stderr, - failed: false, - timedOut: false, - isCanceled: false, - killed: false - }; -}; - -module.exports.command = (command, options) => { - const [file, ...args] = parseCommand(command); - return execa(file, args, options); -}; - -module.exports.commandSync = (command, options) => { - const [file, ...args] = parseCommand(command); - return execa.sync(file, args, options); -}; - -module.exports.node = (scriptPath, args, options = {}) => { - if (args && !Array.isArray(args) && typeof args === 'object') { - options = args; - args = []; - } - - const stdio = normalizeStdio.node(options); - - const {nodePath = process.execPath, nodeOptions = process.execArgv} = options; - - return execa( - nodePath, - [ - ...nodeOptions, - scriptPath, - ...(Array.isArray(args) ? args : []) - ], - { - ...options, - stdin: undefined, - stdout: undefined, - stderr: undefined, - stdio, - shell: false - } - ); -}; - - -/***/ }), - -/***/ "../../node_modules/execa/lib/command.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const SPACES_REGEXP = / +/g; - -const joinCommand = (file, args = []) => { - if (!Array.isArray(args)) { - return file; - } - - return [file, ...args].join(' '); -}; - -// Allow spaces to be escaped by a backslash if not meant as a delimiter -const handleEscaping = (tokens, token, index) => { - if (index === 0) { - return [token]; - } - - const previousToken = tokens[tokens.length - 1]; - - if (previousToken.endsWith('\\')) { - return [...tokens.slice(0, -1), `${previousToken.slice(0, -1)} ${token}`]; - } - - return [...tokens, token]; -}; - -// Handle `execa.command()` -const parseCommand = command => { - return command - .trim() - .split(SPACES_REGEXP) - .reduce(handleEscaping, []); -}; - -module.exports = { - joinCommand, - parseCommand -}; - - -/***/ }), - -/***/ "../../node_modules/execa/lib/error.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {signalsByName} = __webpack_require__("../../node_modules/human-signals/build/src/main.js"); - -const getErrorPrefix = ({timedOut, timeout, errorCode, signal, signalDescription, exitCode, isCanceled}) => { - if (timedOut) { - return `timed out after ${timeout} milliseconds`; - } - - if (isCanceled) { - return 'was canceled'; - } - - if (errorCode !== undefined) { - return `failed with ${errorCode}`; - } - - if (signal !== undefined) { - return `was killed with ${signal} (${signalDescription})`; - } - - if (exitCode !== undefined) { - return `failed with exit code ${exitCode}`; - } - - return 'failed'; -}; - -const makeError = ({ - stdout, - stderr, - all, - error, - signal, - exitCode, - command, - timedOut, - isCanceled, - killed, - parsed: {options: {timeout}} -}) => { - // `signal` and `exitCode` emitted on `spawned.on('exit')` event can be `null`. - // We normalize them to `undefined` - exitCode = exitCode === null ? undefined : exitCode; - signal = signal === null ? undefined : signal; - const signalDescription = signal === undefined ? undefined : signalsByName[signal].description; - - const errorCode = error && error.code; - - const prefix = getErrorPrefix({timedOut, timeout, errorCode, signal, signalDescription, exitCode, isCanceled}); - const execaMessage = `Command ${prefix}: ${command}`; - const isError = Object.prototype.toString.call(error) === '[object Error]'; - const shortMessage = isError ? `${execaMessage}\n${error.message}` : execaMessage; - const message = [shortMessage, stderr, stdout].filter(Boolean).join('\n'); - - if (isError) { - error.originalMessage = error.message; - error.message = message; - } else { - error = new Error(message); - } - - error.shortMessage = shortMessage; - error.command = command; - error.exitCode = exitCode; - error.signal = signal; - error.signalDescription = signalDescription; - error.stdout = stdout; - error.stderr = stderr; - - if (all !== undefined) { - error.all = all; - } - - if ('bufferedData' in error) { - delete error.bufferedData; - } - - error.failed = true; - error.timedOut = Boolean(timedOut); - error.isCanceled = isCanceled; - error.killed = killed && !timedOut; - - return error; -}; - -module.exports = makeError; - - -/***/ }), - -/***/ "../../node_modules/execa/lib/kill.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const os = __webpack_require__("os"); -const onExit = __webpack_require__("../../node_modules/signal-exit/index.js"); - -const DEFAULT_FORCE_KILL_TIMEOUT = 1000 * 5; - -// Monkey-patches `childProcess.kill()` to add `forceKillAfterTimeout` behavior -const spawnedKill = (kill, signal = 'SIGTERM', options = {}) => { - const killResult = kill(signal); - setKillTimeout(kill, signal, options, killResult); - return killResult; -}; - -const setKillTimeout = (kill, signal, options, killResult) => { - if (!shouldForceKill(signal, options, killResult)) { - return; - } - - const timeout = getForceKillAfterTimeout(options); - const t = setTimeout(() => { - kill('SIGKILL'); - }, timeout); - - // Guarded because there's no `.unref()` when `execa` is used in the renderer - // process in Electron. This cannot be tested since we don't run tests in - // Electron. - // istanbul ignore else - if (t.unref) { - t.unref(); - } -}; - -const shouldForceKill = (signal, {forceKillAfterTimeout}, killResult) => { - return isSigterm(signal) && forceKillAfterTimeout !== false && killResult; -}; - -const isSigterm = signal => { - return signal === os.constants.signals.SIGTERM || - (typeof signal === 'string' && signal.toUpperCase() === 'SIGTERM'); -}; - -const getForceKillAfterTimeout = ({forceKillAfterTimeout = true}) => { - if (forceKillAfterTimeout === true) { - return DEFAULT_FORCE_KILL_TIMEOUT; - } - - if (!Number.isFinite(forceKillAfterTimeout) || forceKillAfterTimeout < 0) { - throw new TypeError(`Expected the \`forceKillAfterTimeout\` option to be a non-negative integer, got \`${forceKillAfterTimeout}\` (${typeof forceKillAfterTimeout})`); - } - - return forceKillAfterTimeout; -}; - -// `childProcess.cancel()` -const spawnedCancel = (spawned, context) => { - const killResult = spawned.kill(); - - if (killResult) { - context.isCanceled = true; - } -}; - -const timeoutKill = (spawned, signal, reject) => { - spawned.kill(signal); - reject(Object.assign(new Error('Timed out'), {timedOut: true, signal})); -}; - -// `timeout` option handling -const setupTimeout = (spawned, {timeout, killSignal = 'SIGTERM'}, spawnedPromise) => { - if (timeout === 0 || timeout === undefined) { - return spawnedPromise; - } - - if (!Number.isFinite(timeout) || timeout < 0) { - throw new TypeError(`Expected the \`timeout\` option to be a non-negative integer, got \`${timeout}\` (${typeof timeout})`); - } - - let timeoutId; - const timeoutPromise = new Promise((resolve, reject) => { - timeoutId = setTimeout(() => { - timeoutKill(spawned, killSignal, reject); - }, timeout); - }); - - const safeSpawnedPromise = spawnedPromise.finally(() => { - clearTimeout(timeoutId); - }); - - return Promise.race([timeoutPromise, safeSpawnedPromise]); -}; - -// `cleanup` option handling -const setExitHandler = async (spawned, {cleanup, detached}, timedPromise) => { - if (!cleanup || detached) { - return timedPromise; - } - - const removeExitHandler = onExit(() => { - spawned.kill(); - }); - - return timedPromise.finally(() => { - removeExitHandler(); - }); -}; - -module.exports = { - spawnedKill, - spawnedCancel, - setupTimeout, - setExitHandler -}; - - -/***/ }), - -/***/ "../../node_modules/execa/lib/promise.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const nativePromisePrototype = (async () => {})().constructor.prototype; -const descriptors = ['then', 'catch', 'finally'].map(property => [ - property, - Reflect.getOwnPropertyDescriptor(nativePromisePrototype, property) -]); - -// The return value is a mixin of `childProcess` and `Promise` -const mergePromise = (spawned, promise) => { - for (const [property, descriptor] of descriptors) { - // Starting the main `promise` is deferred to avoid consuming streams - const value = typeof promise === 'function' ? - (...args) => Reflect.apply(descriptor.value, promise(), args) : - descriptor.value.bind(promise); - - Reflect.defineProperty(spawned, property, {...descriptor, value}); - } - - return spawned; -}; - -// Use promises instead of `child_process` events -const getSpawnedPromise = spawned => { - return new Promise((resolve, reject) => { - spawned.on('exit', (exitCode, signal) => { - resolve({exitCode, signal}); - }); - - spawned.on('error', error => { - reject(error); - }); - - if (spawned.stdin) { - spawned.stdin.on('error', error => { - reject(error); - }); - } - }); -}; - -module.exports = { - mergePromise, - getSpawnedPromise -}; - - - -/***/ }), - -/***/ "../../node_modules/execa/lib/stdio.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const aliases = ['stdin', 'stdout', 'stderr']; - -const hasAlias = opts => aliases.some(alias => opts[alias] !== undefined); - -const normalizeStdio = opts => { - if (!opts) { - return; - } - - const {stdio} = opts; - - if (stdio === undefined) { - return aliases.map(alias => opts[alias]); - } - - if (hasAlias(opts)) { - throw new Error(`It's not possible to provide \`stdio\` in combination with one of ${aliases.map(alias => `\`${alias}\``).join(', ')}`); - } - - if (typeof stdio === 'string') { - return stdio; - } - - if (!Array.isArray(stdio)) { - throw new TypeError(`Expected \`stdio\` to be of type \`string\` or \`Array\`, got \`${typeof stdio}\``); - } - - const length = Math.max(stdio.length, aliases.length); - return Array.from({length}, (value, index) => stdio[index]); -}; - -module.exports = normalizeStdio; - -// `ipc` is pushed unless it is already present -module.exports.node = opts => { - const stdio = normalizeStdio(opts); - - if (stdio === 'ipc') { - return 'ipc'; - } - - if (stdio === undefined || typeof stdio === 'string') { - return [stdio, stdio, stdio, 'ipc']; - } - - if (stdio.includes('ipc')) { - return stdio; - } - - return [...stdio, 'ipc']; -}; - - -/***/ }), - -/***/ "../../node_modules/execa/lib/stream.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const isStream = __webpack_require__("../../node_modules/is-stream/index.js"); -const getStream = __webpack_require__("../../node_modules/get-stream/index.js"); -const mergeStream = __webpack_require__("../../node_modules/merge-stream/index.js"); - -// `input` option -const handleInput = (spawned, input) => { - // Checking for stdin is workaround for https://github.com/nodejs/node/issues/26852 - // TODO: Remove `|| spawned.stdin === undefined` once we drop support for Node.js <=12.2.0 - if (input === undefined || spawned.stdin === undefined) { - return; - } - - if (isStream(input)) { - input.pipe(spawned.stdin); - } else { - spawned.stdin.end(input); - } -}; - -// `all` interleaves `stdout` and `stderr` -const makeAllStream = (spawned, {all}) => { - if (!all || (!spawned.stdout && !spawned.stderr)) { - return; - } - - const mixed = mergeStream(); - - if (spawned.stdout) { - mixed.add(spawned.stdout); - } - - if (spawned.stderr) { - mixed.add(spawned.stderr); - } - - return mixed; -}; - -// On failure, `result.stdout|stderr|all` should contain the currently buffered stream -const getBufferedData = async (stream, streamPromise) => { - if (!stream) { - return; - } - - stream.destroy(); - - try { - return await streamPromise; - } catch (error) { - return error.bufferedData; - } -}; - -const getStreamPromise = (stream, {encoding, buffer, maxBuffer}) => { - if (!stream || !buffer) { - return; - } - - if (encoding) { - return getStream(stream, {encoding, maxBuffer}); - } - - return getStream.buffer(stream, {maxBuffer}); -}; - -// Retrieve result of child process: exit code, signal, error, streams (stdout/stderr/all) -const getSpawnedResult = async ({stdout, stderr, all}, {encoding, buffer, maxBuffer}, processDone) => { - const stdoutPromise = getStreamPromise(stdout, {encoding, buffer, maxBuffer}); - const stderrPromise = getStreamPromise(stderr, {encoding, buffer, maxBuffer}); - const allPromise = getStreamPromise(all, {encoding, buffer, maxBuffer: maxBuffer * 2}); - - try { - return await Promise.all([processDone, stdoutPromise, stderrPromise, allPromise]); - } catch (error) { - return Promise.all([ - {error, signal: error.signal, timedOut: error.timedOut}, - getBufferedData(stdout, stdoutPromise), - getBufferedData(stderr, stderrPromise), - getBufferedData(all, allPromise) - ]); - } -}; - -const validateInputSync = ({input}) => { - if (isStream(input)) { - throw new TypeError('The `input` option cannot be a stream in sync mode'); - } -}; - -module.exports = { - handleInput, - makeAllStream, - getSpawnedResult, - validateInputSync -}; - - - -/***/ }), - -/***/ "../../node_modules/fast-glob/node_modules/micromatch/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const util = __webpack_require__("util"); -const braces = __webpack_require__("../../node_modules/braces/index.js"); -const picomatch = __webpack_require__("../../node_modules/picomatch/index.js"); -const utils = __webpack_require__("../../node_modules/picomatch/lib/utils.js"); -const isEmptyString = val => val === '' || val === './'; - -/** - * Returns an array of strings that match one or more glob patterns. - * - * ```js - * const mm = require('micromatch'); - * // mm(list, patterns[, options]); - * - * console.log(mm(['a.js', 'a.txt'], ['*.js'])); - * //=> [ 'a.js' ] - * ``` - * @param {String|Array} `list` List of strings to match. - * @param {String|Array} `patterns` One or more glob patterns to use for matching. - * @param {Object} `options` See available [options](#options) - * @return {Array} Returns an array of matches - * @summary false - * @api public - */ - -const micromatch = (list, patterns, options) => { - patterns = [].concat(patterns); - list = [].concat(list); - - let omit = new Set(); - let keep = new Set(); - let items = new Set(); - let negatives = 0; - - let onResult = state => { - items.add(state.output); - if (options && options.onResult) { - options.onResult(state); - } - }; - - for (let i = 0; i < patterns.length; i++) { - let isMatch = picomatch(String(patterns[i]), { ...options, onResult }, true); - let negated = isMatch.state.negated || isMatch.state.negatedExtglob; - if (negated) negatives++; - - for (let item of list) { - let matched = isMatch(item, true); - - let match = negated ? !matched.isMatch : matched.isMatch; - if (!match) continue; - - if (negated) { - omit.add(matched.output); - } else { - omit.delete(matched.output); - keep.add(matched.output); - } - } - } - - let result = negatives === patterns.length ? [...items] : [...keep]; - let matches = result.filter(item => !omit.has(item)); - - if (options && matches.length === 0) { - if (options.failglob === true) { - throw new Error(`No matches found for "${patterns.join(', ')}"`); - } - - if (options.nonull === true || options.nullglob === true) { - return options.unescape ? patterns.map(p => p.replace(/\\/g, '')) : patterns; - } - } - - return matches; -}; - -/** - * Backwards compatibility - */ - -micromatch.match = micromatch; - -/** - * Returns a matcher function from the given glob `pattern` and `options`. - * The returned function takes a string to match as its only argument and returns - * true if the string is a match. - * - * ```js - * const mm = require('micromatch'); - * // mm.matcher(pattern[, options]); - * - * const isMatch = mm.matcher('*.!(*a)'); - * console.log(isMatch('a.a')); //=> false - * console.log(isMatch('a.b')); //=> true - * ``` - * @param {String} `pattern` Glob pattern - * @param {Object} `options` - * @return {Function} Returns a matcher function. - * @api public - */ - -micromatch.matcher = (pattern, options) => picomatch(pattern, options); - -/** - * Returns true if **any** of the given glob `patterns` match the specified `string`. - * - * ```js - * const mm = require('micromatch'); - * // mm.isMatch(string, patterns[, options]); - * - * console.log(mm.isMatch('a.a', ['b.*', '*.a'])); //=> true - * console.log(mm.isMatch('a.a', 'b.*')); //=> false - * ``` - * @param {String} `str` The string to test. - * @param {String|Array} `patterns` One or more glob patterns to use for matching. - * @param {Object} `[options]` See available [options](#options). - * @return {Boolean} Returns true if any patterns match `str` - * @api public - */ - -micromatch.isMatch = (str, patterns, options) => picomatch(patterns, options)(str); - -/** - * Backwards compatibility - */ - -micromatch.any = micromatch.isMatch; - -/** - * Returns a list of strings that _**do not match any**_ of the given `patterns`. - * - * ```js - * const mm = require('micromatch'); - * // mm.not(list, patterns[, options]); - * - * console.log(mm.not(['a.a', 'b.b', 'c.c'], '*.a')); - * //=> ['b.b', 'c.c'] - * ``` - * @param {Array} `list` Array of strings to match. - * @param {String|Array} `patterns` One or more glob pattern to use for matching. - * @param {Object} `options` See available [options](#options) for changing how matches are performed - * @return {Array} Returns an array of strings that **do not match** the given patterns. - * @api public - */ - -micromatch.not = (list, patterns, options = {}) => { - patterns = [].concat(patterns).map(String); - let result = new Set(); - let items = []; - - let onResult = state => { - if (options.onResult) options.onResult(state); - items.push(state.output); - }; - - let matches = micromatch(list, patterns, { ...options, onResult }); - - for (let item of items) { - if (!matches.includes(item)) { - result.add(item); - } - } - return [...result]; -}; - -/** - * Returns true if the given `string` contains the given pattern. Similar - * to [.isMatch](#isMatch) but the pattern can match any part of the string. - * - * ```js - * var mm = require('micromatch'); - * // mm.contains(string, pattern[, options]); - * - * console.log(mm.contains('aa/bb/cc', '*b')); - * //=> true - * console.log(mm.contains('aa/bb/cc', '*d')); - * //=> false - * ``` - * @param {String} `str` The string to match. - * @param {String|Array} `patterns` Glob pattern to use for matching. - * @param {Object} `options` See available [options](#options) for changing how matches are performed - * @return {Boolean} Returns true if any of the patterns matches any part of `str`. - * @api public - */ - -micromatch.contains = (str, pattern, options) => { - if (typeof str !== 'string') { - throw new TypeError(`Expected a string: "${util.inspect(str)}"`); - } - - if (Array.isArray(pattern)) { - return pattern.some(p => micromatch.contains(str, p, options)); - } - - if (typeof pattern === 'string') { - if (isEmptyString(str) || isEmptyString(pattern)) { - return false; - } - - if (str.includes(pattern) || (str.startsWith('./') && str.slice(2).includes(pattern))) { - return true; - } - } - - return micromatch.isMatch(str, pattern, { ...options, contains: true }); -}; - -/** - * Filter the keys of the given object with the given `glob` pattern - * and `options`. Does not attempt to match nested keys. If you need this feature, - * use [glob-object][] instead. - * - * ```js - * const mm = require('micromatch'); - * // mm.matchKeys(object, patterns[, options]); - * - * const obj = { aa: 'a', ab: 'b', ac: 'c' }; - * console.log(mm.matchKeys(obj, '*b')); - * //=> { ab: 'b' } - * ``` - * @param {Object} `object` The object with keys to filter. - * @param {String|Array} `patterns` One or more glob patterns to use for matching. - * @param {Object} `options` See available [options](#options) for changing how matches are performed - * @return {Object} Returns an object with only keys that match the given patterns. - * @api public - */ - -micromatch.matchKeys = (obj, patterns, options) => { - if (!utils.isObject(obj)) { - throw new TypeError('Expected the first argument to be an object'); - } - let keys = micromatch(Object.keys(obj), patterns, options); - let res = {}; - for (let key of keys) res[key] = obj[key]; - return res; -}; - -/** - * Returns true if some of the strings in the given `list` match any of the given glob `patterns`. - * - * ```js - * const mm = require('micromatch'); - * // mm.some(list, patterns[, options]); - * - * console.log(mm.some(['foo.js', 'bar.js'], ['*.js', '!foo.js'])); - * // true - * console.log(mm.some(['foo.js'], ['*.js', '!foo.js'])); - * // false - * ``` - * @param {String|Array} `list` The string or array of strings to test. Returns as soon as the first match is found. - * @param {String|Array} `patterns` One or more glob patterns to use for matching. - * @param {Object} `options` See available [options](#options) for changing how matches are performed - * @return {Boolean} Returns true if any `patterns` matches any of the strings in `list` - * @api public - */ - -micromatch.some = (list, patterns, options) => { - let items = [].concat(list); - - for (let pattern of [].concat(patterns)) { - let isMatch = picomatch(String(pattern), options); - if (items.some(item => isMatch(item))) { - return true; - } - } - return false; -}; - -/** - * Returns true if every string in the given `list` matches - * any of the given glob `patterns`. - * - * ```js - * const mm = require('micromatch'); - * // mm.every(list, patterns[, options]); - * - * console.log(mm.every('foo.js', ['foo.js'])); - * // true - * console.log(mm.every(['foo.js', 'bar.js'], ['*.js'])); - * // true - * console.log(mm.every(['foo.js', 'bar.js'], ['*.js', '!foo.js'])); - * // false - * console.log(mm.every(['foo.js'], ['*.js', '!foo.js'])); - * // false - * ``` - * @param {String|Array} `list` The string or array of strings to test. - * @param {String|Array} `patterns` One or more glob patterns to use for matching. - * @param {Object} `options` See available [options](#options) for changing how matches are performed - * @return {Boolean} Returns true if all `patterns` matches all of the strings in `list` - * @api public - */ - -micromatch.every = (list, patterns, options) => { - let items = [].concat(list); - - for (let pattern of [].concat(patterns)) { - let isMatch = picomatch(String(pattern), options); - if (!items.every(item => isMatch(item))) { - return false; - } - } - return true; -}; - -/** - * Returns true if **all** of the given `patterns` match - * the specified string. - * - * ```js - * const mm = require('micromatch'); - * // mm.all(string, patterns[, options]); - * - * console.log(mm.all('foo.js', ['foo.js'])); - * // true - * - * console.log(mm.all('foo.js', ['*.js', '!foo.js'])); - * // false - * - * console.log(mm.all('foo.js', ['*.js', 'foo.js'])); - * // true - * - * console.log(mm.all('foo.js', ['*.js', 'f*', '*o*', '*o.js'])); - * // true - * ``` - * @param {String|Array} `str` The string to test. - * @param {String|Array} `patterns` One or more glob patterns to use for matching. - * @param {Object} `options` See available [options](#options) for changing how matches are performed - * @return {Boolean} Returns true if any patterns match `str` - * @api public - */ - -micromatch.all = (str, patterns, options) => { - if (typeof str !== 'string') { - throw new TypeError(`Expected a string: "${util.inspect(str)}"`); - } - - return [].concat(patterns).every(p => picomatch(p, options)(str)); -}; - -/** - * Returns an array of matches captured by `pattern` in `string, or `null` if the pattern did not match. - * - * ```js - * const mm = require('micromatch'); - * // mm.capture(pattern, string[, options]); - * - * console.log(mm.capture('test/*.js', 'test/foo.js')); - * //=> ['foo'] - * console.log(mm.capture('test/*.js', 'foo/bar.css')); - * //=> null - * ``` - * @param {String} `glob` Glob pattern to use for matching. - * @param {String} `input` String to match - * @param {Object} `options` See available [options](#options) for changing how matches are performed - * @return {Array|null} Returns an array of captures if the input matches the glob pattern, otherwise `null`. - * @api public - */ - -micromatch.capture = (glob, input, options) => { - let posix = utils.isWindows(options); - let regex = picomatch.makeRe(String(glob), { ...options, capture: true }); - let match = regex.exec(posix ? utils.toPosixSlashes(input) : input); - - if (match) { - return match.slice(1).map(v => v === void 0 ? '' : v); - } -}; - -/** - * Create a regular expression from the given glob `pattern`. - * - * ```js - * const mm = require('micromatch'); - * // mm.makeRe(pattern[, options]); - * - * console.log(mm.makeRe('*.js')); - * //=> /^(?:(\.[\\\/])?(?!\.)(?=.)[^\/]*?\.js)$/ - * ``` - * @param {String} `pattern` A glob pattern to convert to regex. - * @param {Object} `options` - * @return {RegExp} Returns a regex created from the given pattern. - * @api public - */ - -micromatch.makeRe = (...args) => picomatch.makeRe(...args); - -/** - * Scan a glob pattern to separate the pattern into segments. Used - * by the [split](#split) method. - * - * ```js - * const mm = require('micromatch'); - * const state = mm.scan(pattern[, options]); - * ``` - * @param {String} `pattern` - * @param {Object} `options` - * @return {Object} Returns an object with - * @api public - */ - -micromatch.scan = (...args) => picomatch.scan(...args); - -/** - * Parse a glob pattern to create the source string for a regular - * expression. - * - * ```js - * const mm = require('micromatch'); - * const state = mm(pattern[, options]); - * ``` - * @param {String} `glob` - * @param {Object} `options` - * @return {Object} Returns an object with useful properties and output to be used as regex source string. - * @api public - */ - -micromatch.parse = (patterns, options) => { - let res = []; - for (let pattern of [].concat(patterns || [])) { - for (let str of braces(String(pattern), options)) { - res.push(picomatch.parse(str, options)); - } - } - return res; -}; - -/** - * Process the given brace `pattern`. - * - * ```js - * const { braces } = require('micromatch'); - * console.log(braces('foo/{a,b,c}/bar')); - * //=> [ 'foo/(a|b|c)/bar' ] - * - * console.log(braces('foo/{a,b,c}/bar', { expand: true })); - * //=> [ 'foo/a/bar', 'foo/b/bar', 'foo/c/bar' ] - * ``` - * @param {String} `pattern` String with brace pattern to process. - * @param {Object} `options` Any [options](#options) to change how expansion is performed. See the [braces][] library for all available options. - * @return {Array} - * @api public - */ - -micromatch.braces = (pattern, options) => { - if (typeof pattern !== 'string') throw new TypeError('Expected a string'); - if ((options && options.nobrace === true) || !/\{.*\}/.test(pattern)) { - return [pattern]; - } - return braces(pattern, options); -}; - -/** - * Expand braces - */ - -micromatch.braceExpand = (pattern, options) => { - if (typeof pattern !== 'string') throw new TypeError('Expected a string'); - return micromatch.braces(pattern, { ...options, expand: true }); -}; - -/** - * Expose micromatch - */ - -module.exports = micromatch; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const taskManager = __webpack_require__("../../node_modules/fast-glob/out/managers/tasks.js"); -const async_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/async.js"); -const stream_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/stream.js"); -const sync_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/sync.js"); -const settings_1 = __webpack_require__("../../node_modules/fast-glob/out/settings.js"); -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -async function FastGlob(source, options) { - assertPatternsInput(source); - const works = getWorks(source, async_1.default, options); - const result = await Promise.all(works); - return utils.array.flatten(result); -} -// https://github.com/typescript-eslint/typescript-eslint/issues/60 -// eslint-disable-next-line no-redeclare -(function (FastGlob) { - function sync(source, options) { - assertPatternsInput(source); - const works = getWorks(source, sync_1.default, options); - return utils.array.flatten(works); - } - FastGlob.sync = sync; - function stream(source, options) { - assertPatternsInput(source); - const works = getWorks(source, stream_1.default, options); - /** - * The stream returned by the provider cannot work with an asynchronous iterator. - * To support asynchronous iterators, regardless of the number of tasks, we always multiplex streams. - * This affects performance (+25%). I don't see best solution right now. - */ - return utils.stream.merge(works); - } - FastGlob.stream = stream; - function generateTasks(source, options) { - assertPatternsInput(source); - const patterns = [].concat(source); - const settings = new settings_1.default(options); - return taskManager.generate(patterns, settings); - } - FastGlob.generateTasks = generateTasks; - function isDynamicPattern(source, options) { - assertPatternsInput(source); - const settings = new settings_1.default(options); - return utils.pattern.isDynamicPattern(source, settings); - } - FastGlob.isDynamicPattern = isDynamicPattern; - function escapePath(source) { - assertPatternsInput(source); - return utils.path.escape(source); - } - FastGlob.escapePath = escapePath; -})(FastGlob || (FastGlob = {})); -function getWorks(source, _Provider, options) { - const patterns = [].concat(source); - const settings = new settings_1.default(options); - const tasks = taskManager.generate(patterns, settings); - const provider = new _Provider(settings); - return tasks.map(provider.read, provider); -} -function assertPatternsInput(input) { - const source = [].concat(input); - const isValidSource = source.every((item) => utils.string.isString(item) && !utils.string.isEmpty(item)); - if (!isValidSource) { - throw new TypeError('Patterns must be a string (non empty) or an array of strings'); - } -} -module.exports = FastGlob; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/managers/tasks.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.convertPatternGroupToTask = exports.convertPatternGroupsToTasks = exports.groupPatternsByBaseDirectory = exports.getNegativePatternsAsPositive = exports.getPositivePatterns = exports.convertPatternsToTasks = exports.generate = void 0; -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -function generate(patterns, settings) { - const positivePatterns = getPositivePatterns(patterns); - const negativePatterns = getNegativePatternsAsPositive(patterns, settings.ignore); - const staticPatterns = positivePatterns.filter((pattern) => utils.pattern.isStaticPattern(pattern, settings)); - const dynamicPatterns = positivePatterns.filter((pattern) => utils.pattern.isDynamicPattern(pattern, settings)); - const staticTasks = convertPatternsToTasks(staticPatterns, negativePatterns, /* dynamic */ false); - const dynamicTasks = convertPatternsToTasks(dynamicPatterns, negativePatterns, /* dynamic */ true); - return staticTasks.concat(dynamicTasks); -} -exports.generate = generate; -/** - * Returns tasks grouped by basic pattern directories. - * - * Patterns that can be found inside (`./`) and outside (`../`) the current directory are handled separately. - * This is necessary because directory traversal starts at the base directory and goes deeper. - */ -function convertPatternsToTasks(positive, negative, dynamic) { - const tasks = []; - const patternsOutsideCurrentDirectory = utils.pattern.getPatternsOutsideCurrentDirectory(positive); - const patternsInsideCurrentDirectory = utils.pattern.getPatternsInsideCurrentDirectory(positive); - const outsideCurrentDirectoryGroup = groupPatternsByBaseDirectory(patternsOutsideCurrentDirectory); - const insideCurrentDirectoryGroup = groupPatternsByBaseDirectory(patternsInsideCurrentDirectory); - tasks.push(...convertPatternGroupsToTasks(outsideCurrentDirectoryGroup, negative, dynamic)); - /* - * For the sake of reducing future accesses to the file system, we merge all tasks within the current directory - * into a global task, if at least one pattern refers to the root (`.`). In this case, the global task covers the rest. - */ - if ('.' in insideCurrentDirectoryGroup) { - tasks.push(convertPatternGroupToTask('.', patternsInsideCurrentDirectory, negative, dynamic)); - } - else { - tasks.push(...convertPatternGroupsToTasks(insideCurrentDirectoryGroup, negative, dynamic)); - } - return tasks; -} -exports.convertPatternsToTasks = convertPatternsToTasks; -function getPositivePatterns(patterns) { - return utils.pattern.getPositivePatterns(patterns); -} -exports.getPositivePatterns = getPositivePatterns; -function getNegativePatternsAsPositive(patterns, ignore) { - const negative = utils.pattern.getNegativePatterns(patterns).concat(ignore); - const positive = negative.map(utils.pattern.convertToPositivePattern); - return positive; -} -exports.getNegativePatternsAsPositive = getNegativePatternsAsPositive; -function groupPatternsByBaseDirectory(patterns) { - const group = {}; - return patterns.reduce((collection, pattern) => { - const base = utils.pattern.getBaseDirectory(pattern); - if (base in collection) { - collection[base].push(pattern); - } - else { - collection[base] = [pattern]; - } - return collection; - }, group); -} -exports.groupPatternsByBaseDirectory = groupPatternsByBaseDirectory; -function convertPatternGroupsToTasks(positive, negative, dynamic) { - return Object.keys(positive).map((base) => { - return convertPatternGroupToTask(base, positive[base], negative, dynamic); - }); -} -exports.convertPatternGroupsToTasks = convertPatternGroupsToTasks; -function convertPatternGroupToTask(base, positive, negative, dynamic) { - return { - dynamic, - positive, - negative, - base, - patterns: [].concat(positive, negative.map(utils.pattern.convertToNegativePattern)) - }; -} -exports.convertPatternGroupToTask = convertPatternGroupToTask; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/async.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const stream_1 = __webpack_require__("../../node_modules/fast-glob/out/readers/stream.js"); -const provider_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/provider.js"); -class ProviderAsync extends provider_1.default { - constructor() { - super(...arguments); - this._reader = new stream_1.default(this._settings); - } - read(task) { - const root = this._getRootDirectory(task); - const options = this._getReaderOptions(task); - const entries = []; - return new Promise((resolve, reject) => { - const stream = this.api(root, task, options); - stream.once('error', reject); - stream.on('data', (entry) => entries.push(options.transform(entry))); - stream.once('end', () => resolve(entries)); - }); - } - api(root, task, options) { - if (task.dynamic) { - return this._reader.dynamic(root, options); - } - return this._reader.static(task.patterns, options); - } -} -exports.default = ProviderAsync; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/filters/deep.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -const partial_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/matchers/partial.js"); -class DeepFilter { - constructor(_settings, _micromatchOptions) { - this._settings = _settings; - this._micromatchOptions = _micromatchOptions; - } - getFilter(basePath, positive, negative) { - const matcher = this._getMatcher(positive); - const negativeRe = this._getNegativePatternsRe(negative); - return (entry) => this._filter(basePath, entry, matcher, negativeRe); - } - _getMatcher(patterns) { - return new partial_1.default(patterns, this._settings, this._micromatchOptions); - } - _getNegativePatternsRe(patterns) { - const affectDepthOfReadingPatterns = patterns.filter(utils.pattern.isAffectDepthOfReadingPattern); - return utils.pattern.convertPatternsToRe(affectDepthOfReadingPatterns, this._micromatchOptions); - } - _filter(basePath, entry, matcher, negativeRe) { - if (this._isSkippedByDeep(basePath, entry.path)) { - return false; - } - if (this._isSkippedSymbolicLink(entry)) { - return false; - } - const filepath = utils.path.removeLeadingDotSegment(entry.path); - if (this._isSkippedByPositivePatterns(filepath, matcher)) { - return false; - } - return this._isSkippedByNegativePatterns(filepath, negativeRe); - } - _isSkippedByDeep(basePath, entryPath) { - /** - * Avoid unnecessary depth calculations when it doesn't matter. - */ - if (this._settings.deep === Infinity) { - return false; - } - return this._getEntryLevel(basePath, entryPath) >= this._settings.deep; - } - _getEntryLevel(basePath, entryPath) { - const entryPathDepth = entryPath.split('/').length; - if (basePath === '') { - return entryPathDepth; - } - const basePathDepth = basePath.split('/').length; - return entryPathDepth - basePathDepth; - } - _isSkippedSymbolicLink(entry) { - return !this._settings.followSymbolicLinks && entry.dirent.isSymbolicLink(); - } - _isSkippedByPositivePatterns(entryPath, matcher) { - return !this._settings.baseNameMatch && !matcher.match(entryPath); - } - _isSkippedByNegativePatterns(entryPath, patternsRe) { - return !utils.pattern.matchAny(entryPath, patternsRe); - } -} -exports.default = DeepFilter; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/filters/entry.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -class EntryFilter { - constructor(_settings, _micromatchOptions) { - this._settings = _settings; - this._micromatchOptions = _micromatchOptions; - this.index = new Map(); - } - getFilter(positive, negative) { - const positiveRe = utils.pattern.convertPatternsToRe(positive, this._micromatchOptions); - const negativeRe = utils.pattern.convertPatternsToRe(negative, this._micromatchOptions); - return (entry) => this._filter(entry, positiveRe, negativeRe); - } - _filter(entry, positiveRe, negativeRe) { - if (this._settings.unique && this._isDuplicateEntry(entry)) { - return false; - } - if (this._onlyFileFilter(entry) || this._onlyDirectoryFilter(entry)) { - return false; - } - if (this._isSkippedByAbsoluteNegativePatterns(entry.path, negativeRe)) { - return false; - } - const filepath = this._settings.baseNameMatch ? entry.name : entry.path; - const isMatched = this._isMatchToPatterns(filepath, positiveRe) && !this._isMatchToPatterns(entry.path, negativeRe); - if (this._settings.unique && isMatched) { - this._createIndexRecord(entry); - } - return isMatched; - } - _isDuplicateEntry(entry) { - return this.index.has(entry.path); - } - _createIndexRecord(entry) { - this.index.set(entry.path, undefined); - } - _onlyFileFilter(entry) { - return this._settings.onlyFiles && !entry.dirent.isFile(); - } - _onlyDirectoryFilter(entry) { - return this._settings.onlyDirectories && !entry.dirent.isDirectory(); - } - _isSkippedByAbsoluteNegativePatterns(entryPath, patternsRe) { - if (!this._settings.absolute) { - return false; - } - const fullpath = utils.path.makeAbsolute(this._settings.cwd, entryPath); - return utils.pattern.matchAny(fullpath, patternsRe); - } - _isMatchToPatterns(entryPath, patternsRe) { - const filepath = utils.path.removeLeadingDotSegment(entryPath); - return utils.pattern.matchAny(filepath, patternsRe); - } -} -exports.default = EntryFilter; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/filters/error.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -class ErrorFilter { - constructor(_settings) { - this._settings = _settings; - } - getFilter() { - return (error) => this._isNonFatalError(error); - } - _isNonFatalError(error) { - return utils.errno.isEnoentCodeError(error) || this._settings.suppressErrors; - } -} -exports.default = ErrorFilter; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/matchers/matcher.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -class Matcher { - constructor(_patterns, _settings, _micromatchOptions) { - this._patterns = _patterns; - this._settings = _settings; - this._micromatchOptions = _micromatchOptions; - this._storage = []; - this._fillStorage(); - } - _fillStorage() { - /** - * The original pattern may include `{,*,**,a/*}`, which will lead to problems with matching (unresolved level). - * So, before expand patterns with brace expansion into separated patterns. - */ - const patterns = utils.pattern.expandPatternsWithBraceExpansion(this._patterns); - for (const pattern of patterns) { - const segments = this._getPatternSegments(pattern); - const sections = this._splitSegmentsIntoSections(segments); - this._storage.push({ - complete: sections.length <= 1, - pattern, - segments, - sections - }); - } - } - _getPatternSegments(pattern) { - const parts = utils.pattern.getPatternParts(pattern, this._micromatchOptions); - return parts.map((part) => { - const dynamic = utils.pattern.isDynamicPattern(part, this._settings); - if (!dynamic) { - return { - dynamic: false, - pattern: part - }; - } - return { - dynamic: true, - pattern: part, - patternRe: utils.pattern.makeRe(part, this._micromatchOptions) - }; - }); - } - _splitSegmentsIntoSections(segments) { - return utils.array.splitWhen(segments, (segment) => segment.dynamic && utils.pattern.hasGlobStar(segment.pattern)); - } -} -exports.default = Matcher; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/matchers/partial.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const matcher_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/matchers/matcher.js"); -class PartialMatcher extends matcher_1.default { - match(filepath) { - const parts = filepath.split('/'); - const levels = parts.length; - const patterns = this._storage.filter((info) => !info.complete || info.segments.length > levels); - for (const pattern of patterns) { - const section = pattern.sections[0]; - /** - * In this case, the pattern has a globstar and we must read all directories unconditionally, - * but only if the level has reached the end of the first group. - * - * fixtures/{a,b}/** - * ^ true/false ^ always true - */ - if (!pattern.complete && levels > section.length) { - return true; - } - const match = parts.every((part, index) => { - const segment = pattern.segments[index]; - if (segment.dynamic && segment.patternRe.test(part)) { - return true; - } - if (!segment.dynamic && segment.pattern === part) { - return true; - } - return false; - }); - if (match) { - return true; - } - } - return false; - } -} -exports.default = PartialMatcher; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/provider.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const path = __webpack_require__("path"); -const deep_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/filters/deep.js"); -const entry_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/filters/entry.js"); -const error_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/filters/error.js"); -const entry_2 = __webpack_require__("../../node_modules/fast-glob/out/providers/transformers/entry.js"); -class Provider { - constructor(_settings) { - this._settings = _settings; - this.errorFilter = new error_1.default(this._settings); - this.entryFilter = new entry_1.default(this._settings, this._getMicromatchOptions()); - this.deepFilter = new deep_1.default(this._settings, this._getMicromatchOptions()); - this.entryTransformer = new entry_2.default(this._settings); - } - _getRootDirectory(task) { - return path.resolve(this._settings.cwd, task.base); - } - _getReaderOptions(task) { - const basePath = task.base === '.' ? '' : task.base; - return { - basePath, - pathSegmentSeparator: '/', - concurrency: this._settings.concurrency, - deepFilter: this.deepFilter.getFilter(basePath, task.positive, task.negative), - entryFilter: this.entryFilter.getFilter(task.positive, task.negative), - errorFilter: this.errorFilter.getFilter(), - followSymbolicLinks: this._settings.followSymbolicLinks, - fs: this._settings.fs, - stats: this._settings.stats, - throwErrorOnBrokenSymbolicLink: this._settings.throwErrorOnBrokenSymbolicLink, - transform: this.entryTransformer.getTransformer() - }; - } - _getMicromatchOptions() { - return { - dot: this._settings.dot, - matchBase: this._settings.baseNameMatch, - nobrace: !this._settings.braceExpansion, - nocase: !this._settings.caseSensitiveMatch, - noext: !this._settings.extglob, - noglobstar: !this._settings.globstar, - posix: true, - strictSlashes: false - }; - } -} -exports.default = Provider; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/stream.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const stream_1 = __webpack_require__("stream"); -const stream_2 = __webpack_require__("../../node_modules/fast-glob/out/readers/stream.js"); -const provider_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/provider.js"); -class ProviderStream extends provider_1.default { - constructor() { - super(...arguments); - this._reader = new stream_2.default(this._settings); - } - read(task) { - const root = this._getRootDirectory(task); - const options = this._getReaderOptions(task); - const source = this.api(root, task, options); - const destination = new stream_1.Readable({ objectMode: true, read: () => { } }); - source - .once('error', (error) => destination.emit('error', error)) - .on('data', (entry) => destination.emit('data', options.transform(entry))) - .once('end', () => destination.emit('end')); - destination - .once('close', () => source.destroy()); - return destination; - } - api(root, task, options) { - if (task.dynamic) { - return this._reader.dynamic(root, options); - } - return this._reader.static(task.patterns, options); - } -} -exports.default = ProviderStream; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const sync_1 = __webpack_require__("../../node_modules/fast-glob/out/readers/sync.js"); -const provider_1 = __webpack_require__("../../node_modules/fast-glob/out/providers/provider.js"); -class ProviderSync extends provider_1.default { - constructor() { - super(...arguments); - this._reader = new sync_1.default(this._settings); - } - read(task) { - const root = this._getRootDirectory(task); - const options = this._getReaderOptions(task); - const entries = this.api(root, task, options); - return entries.map(options.transform); - } - api(root, task, options) { - if (task.dynamic) { - return this._reader.dynamic(root, options); - } - return this._reader.static(task.patterns, options); - } -} -exports.default = ProviderSync; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/providers/transformers/entry.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -class EntryTransformer { - constructor(_settings) { - this._settings = _settings; - } - getTransformer() { - return (entry) => this._transform(entry); - } - _transform(entry) { - let filepath = entry.path; - if (this._settings.absolute) { - filepath = utils.path.makeAbsolute(this._settings.cwd, filepath); - filepath = utils.path.unixify(filepath); - } - if (this._settings.markDirectories && entry.dirent.isDirectory()) { - filepath += '/'; - } - if (!this._settings.objectMode) { - return filepath; - } - return Object.assign(Object.assign({}, entry), { path: filepath }); - } -} -exports.default = EntryTransformer; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/readers/reader.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const path = __webpack_require__("path"); -const fsStat = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/index.js"); -const utils = __webpack_require__("../../node_modules/fast-glob/out/utils/index.js"); -class Reader { - constructor(_settings) { - this._settings = _settings; - this._fsStatSettings = new fsStat.Settings({ - followSymbolicLink: this._settings.followSymbolicLinks, - fs: this._settings.fs, - throwErrorOnBrokenSymbolicLink: this._settings.followSymbolicLinks - }); - } - _getFullEntryPath(filepath) { - return path.resolve(this._settings.cwd, filepath); - } - _makeEntry(stats, pattern) { - const entry = { - name: pattern, - path: pattern, - dirent: utils.fs.createDirentFromStats(pattern, stats) - }; - if (this._settings.stats) { - entry.stats = stats; - } - return entry; - } - _isFatalError(error) { - return !utils.errno.isEnoentCodeError(error) && !this._settings.suppressErrors; - } -} -exports.default = Reader; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/readers/stream.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const stream_1 = __webpack_require__("stream"); -const fsStat = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/index.js"); -const fsWalk = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/index.js"); -const reader_1 = __webpack_require__("../../node_modules/fast-glob/out/readers/reader.js"); -class ReaderStream extends reader_1.default { - constructor() { - super(...arguments); - this._walkStream = fsWalk.walkStream; - this._stat = fsStat.stat; - } - dynamic(root, options) { - return this._walkStream(root, options); - } - static(patterns, options) { - const filepaths = patterns.map(this._getFullEntryPath, this); - const stream = new stream_1.PassThrough({ objectMode: true }); - stream._write = (index, _enc, done) => { - return this._getEntry(filepaths[index], patterns[index], options) - .then((entry) => { - if (entry !== null && options.entryFilter(entry)) { - stream.push(entry); - } - if (index === filepaths.length - 1) { - stream.end(); - } - done(); - }) - .catch(done); - }; - for (let i = 0; i < filepaths.length; i++) { - stream.write(i); - } - return stream; - } - _getEntry(filepath, pattern, options) { - return this._getStat(filepath) - .then((stats) => this._makeEntry(stats, pattern)) - .catch((error) => { - if (options.errorFilter(error)) { - return null; - } - throw error; - }); - } - _getStat(filepath) { - return new Promise((resolve, reject) => { - this._stat(filepath, this._fsStatSettings, (error, stats) => { - return error === null ? resolve(stats) : reject(error); - }); - }); - } -} -exports.default = ReaderStream; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/readers/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -const fsStat = __webpack_require__("../../node_modules/@nodelib/fs.stat/out/index.js"); -const fsWalk = __webpack_require__("../../node_modules/@nodelib/fs.walk/out/index.js"); -const reader_1 = __webpack_require__("../../node_modules/fast-glob/out/readers/reader.js"); -class ReaderSync extends reader_1.default { - constructor() { - super(...arguments); - this._walkSync = fsWalk.walkSync; - this._statSync = fsStat.statSync; - } - dynamic(root, options) { - return this._walkSync(root, options); - } - static(patterns, options) { - const entries = []; - for (const pattern of patterns) { - const filepath = this._getFullEntryPath(pattern); - const entry = this._getEntry(filepath, pattern, options); - if (entry === null || !options.entryFilter(entry)) { - continue; - } - entries.push(entry); - } - return entries; - } - _getEntry(filepath, pattern, options) { - try { - const stats = this._getStat(filepath); - return this._makeEntry(stats, pattern); - } - catch (error) { - if (options.errorFilter(error)) { - return null; - } - throw error; - } - } - _getStat(filepath) { - return this._statSync(filepath, this._fsStatSettings); - } -} -exports.default = ReaderSync; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/settings.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.DEFAULT_FILE_SYSTEM_ADAPTER = void 0; -const fs = __webpack_require__("fs"); -const os = __webpack_require__("os"); -/** - * The `os.cpus` method can return zero. We expect the number of cores to be greater than zero. - * https://github.com/nodejs/node/blob/7faeddf23a98c53896f8b574a6e66589e8fb1eb8/lib/os.js#L106-L107 - */ -const CPU_COUNT = Math.max(os.cpus().length, 1); -exports.DEFAULT_FILE_SYSTEM_ADAPTER = { - lstat: fs.lstat, - lstatSync: fs.lstatSync, - stat: fs.stat, - statSync: fs.statSync, - readdir: fs.readdir, - readdirSync: fs.readdirSync -}; -class Settings { - constructor(_options = {}) { - this._options = _options; - this.absolute = this._getValue(this._options.absolute, false); - this.baseNameMatch = this._getValue(this._options.baseNameMatch, false); - this.braceExpansion = this._getValue(this._options.braceExpansion, true); - this.caseSensitiveMatch = this._getValue(this._options.caseSensitiveMatch, true); - this.concurrency = this._getValue(this._options.concurrency, CPU_COUNT); - this.cwd = this._getValue(this._options.cwd, process.cwd()); - this.deep = this._getValue(this._options.deep, Infinity); - this.dot = this._getValue(this._options.dot, false); - this.extglob = this._getValue(this._options.extglob, true); - this.followSymbolicLinks = this._getValue(this._options.followSymbolicLinks, true); - this.fs = this._getFileSystemMethods(this._options.fs); - this.globstar = this._getValue(this._options.globstar, true); - this.ignore = this._getValue(this._options.ignore, []); - this.markDirectories = this._getValue(this._options.markDirectories, false); - this.objectMode = this._getValue(this._options.objectMode, false); - this.onlyDirectories = this._getValue(this._options.onlyDirectories, false); - this.onlyFiles = this._getValue(this._options.onlyFiles, true); - this.stats = this._getValue(this._options.stats, false); - this.suppressErrors = this._getValue(this._options.suppressErrors, false); - this.throwErrorOnBrokenSymbolicLink = this._getValue(this._options.throwErrorOnBrokenSymbolicLink, false); - this.unique = this._getValue(this._options.unique, true); - if (this.onlyDirectories) { - this.onlyFiles = false; - } - if (this.stats) { - this.objectMode = true; - } - } - _getValue(option, value) { - return option === undefined ? value : option; - } - _getFileSystemMethods(methods = {}) { - return Object.assign(Object.assign({}, exports.DEFAULT_FILE_SYSTEM_ADAPTER), methods); - } -} -exports.default = Settings; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/array.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.splitWhen = exports.flatten = void 0; -function flatten(items) { - return items.reduce((collection, item) => [].concat(collection, item), []); -} -exports.flatten = flatten; -function splitWhen(items, predicate) { - const result = [[]]; - let groupIndex = 0; - for (const item of items) { - if (predicate(item)) { - groupIndex++; - result[groupIndex] = []; - } - else { - result[groupIndex].push(item); - } - } - return result; -} -exports.splitWhen = splitWhen; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/errno.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.isEnoentCodeError = void 0; -function isEnoentCodeError(error) { - return error.code === 'ENOENT'; -} -exports.isEnoentCodeError = isEnoentCodeError; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/fs.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.createDirentFromStats = void 0; -class DirentFromStats { - constructor(name, stats) { - this.name = name; - this.isBlockDevice = stats.isBlockDevice.bind(stats); - this.isCharacterDevice = stats.isCharacterDevice.bind(stats); - this.isDirectory = stats.isDirectory.bind(stats); - this.isFIFO = stats.isFIFO.bind(stats); - this.isFile = stats.isFile.bind(stats); - this.isSocket = stats.isSocket.bind(stats); - this.isSymbolicLink = stats.isSymbolicLink.bind(stats); - } -} -function createDirentFromStats(name, stats) { - return new DirentFromStats(name, stats); -} -exports.createDirentFromStats = createDirentFromStats; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.string = exports.stream = exports.pattern = exports.path = exports.fs = exports.errno = exports.array = void 0; -const array = __webpack_require__("../../node_modules/fast-glob/out/utils/array.js"); -exports.array = array; -const errno = __webpack_require__("../../node_modules/fast-glob/out/utils/errno.js"); -exports.errno = errno; -const fs = __webpack_require__("../../node_modules/fast-glob/out/utils/fs.js"); -exports.fs = fs; -const path = __webpack_require__("../../node_modules/fast-glob/out/utils/path.js"); -exports.path = path; -const pattern = __webpack_require__("../../node_modules/fast-glob/out/utils/pattern.js"); -exports.pattern = pattern; -const stream = __webpack_require__("../../node_modules/fast-glob/out/utils/stream.js"); -exports.stream = stream; -const string = __webpack_require__("../../node_modules/fast-glob/out/utils/string.js"); -exports.string = string; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/path.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.removeLeadingDotSegment = exports.escape = exports.makeAbsolute = exports.unixify = void 0; -const path = __webpack_require__("path"); -const LEADING_DOT_SEGMENT_CHARACTERS_COUNT = 2; // ./ or .\\ -const UNESCAPED_GLOB_SYMBOLS_RE = /(\\?)([()*?[\]{|}]|^!|[!+@](?=\())/g; -/** - * Designed to work only with simple paths: `dir\\file`. - */ -function unixify(filepath) { - return filepath.replace(/\\/g, '/'); -} -exports.unixify = unixify; -function makeAbsolute(cwd, filepath) { - return path.resolve(cwd, filepath); -} -exports.makeAbsolute = makeAbsolute; -function escape(pattern) { - return pattern.replace(UNESCAPED_GLOB_SYMBOLS_RE, '\\$2'); -} -exports.escape = escape; -function removeLeadingDotSegment(entry) { - // We do not use `startsWith` because this is 10x slower than current implementation for some cases. - // eslint-disable-next-line @typescript-eslint/prefer-string-starts-ends-with - if (entry.charAt(0) === '.') { - const secondCharactery = entry.charAt(1); - if (secondCharactery === '/' || secondCharactery === '\\') { - return entry.slice(LEADING_DOT_SEGMENT_CHARACTERS_COUNT); - } - } - return entry; -} -exports.removeLeadingDotSegment = removeLeadingDotSegment; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/pattern.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.matchAny = exports.convertPatternsToRe = exports.makeRe = exports.getPatternParts = exports.expandBraceExpansion = exports.expandPatternsWithBraceExpansion = exports.isAffectDepthOfReadingPattern = exports.endsWithSlashGlobStar = exports.hasGlobStar = exports.getBaseDirectory = exports.isPatternRelatedToParentDirectory = exports.getPatternsOutsideCurrentDirectory = exports.getPatternsInsideCurrentDirectory = exports.getPositivePatterns = exports.getNegativePatterns = exports.isPositivePattern = exports.isNegativePattern = exports.convertToNegativePattern = exports.convertToPositivePattern = exports.isDynamicPattern = exports.isStaticPattern = void 0; -const path = __webpack_require__("path"); -const globParent = __webpack_require__("../../node_modules/glob-parent/index.js"); -const micromatch = __webpack_require__("../../node_modules/fast-glob/node_modules/micromatch/index.js"); -const GLOBSTAR = '**'; -const ESCAPE_SYMBOL = '\\'; -const COMMON_GLOB_SYMBOLS_RE = /[*?]|^!/; -const REGEX_CHARACTER_CLASS_SYMBOLS_RE = /\[.*]/; -const REGEX_GROUP_SYMBOLS_RE = /(?:^|[^!*+?@])\(.*\|.*\)/; -const GLOB_EXTENSION_SYMBOLS_RE = /[!*+?@]\(.*\)/; -const BRACE_EXPANSIONS_SYMBOLS_RE = /{.*(?:,|\.\.).*}/; -function isStaticPattern(pattern, options = {}) { - return !isDynamicPattern(pattern, options); -} -exports.isStaticPattern = isStaticPattern; -function isDynamicPattern(pattern, options = {}) { - /** - * A special case with an empty string is necessary for matching patterns that start with a forward slash. - * An empty string cannot be a dynamic pattern. - * For example, the pattern `/lib/*` will be spread into parts: '', 'lib', '*'. - */ - if (pattern === '') { - return false; - } - /** - * When the `caseSensitiveMatch` option is disabled, all patterns must be marked as dynamic, because we cannot check - * filepath directly (without read directory). - */ - if (options.caseSensitiveMatch === false || pattern.includes(ESCAPE_SYMBOL)) { - return true; - } - if (COMMON_GLOB_SYMBOLS_RE.test(pattern) || REGEX_CHARACTER_CLASS_SYMBOLS_RE.test(pattern) || REGEX_GROUP_SYMBOLS_RE.test(pattern)) { - return true; - } - if (options.extglob !== false && GLOB_EXTENSION_SYMBOLS_RE.test(pattern)) { - return true; - } - if (options.braceExpansion !== false && BRACE_EXPANSIONS_SYMBOLS_RE.test(pattern)) { - return true; - } - return false; -} -exports.isDynamicPattern = isDynamicPattern; -function convertToPositivePattern(pattern) { - return isNegativePattern(pattern) ? pattern.slice(1) : pattern; -} -exports.convertToPositivePattern = convertToPositivePattern; -function convertToNegativePattern(pattern) { - return '!' + pattern; -} -exports.convertToNegativePattern = convertToNegativePattern; -function isNegativePattern(pattern) { - return pattern.startsWith('!') && pattern[1] !== '('; -} -exports.isNegativePattern = isNegativePattern; -function isPositivePattern(pattern) { - return !isNegativePattern(pattern); -} -exports.isPositivePattern = isPositivePattern; -function getNegativePatterns(patterns) { - return patterns.filter(isNegativePattern); -} -exports.getNegativePatterns = getNegativePatterns; -function getPositivePatterns(patterns) { - return patterns.filter(isPositivePattern); -} -exports.getPositivePatterns = getPositivePatterns; -/** - * Returns patterns that can be applied inside the current directory. - * - * @example - * // ['./*', '*', 'a/*'] - * getPatternsInsideCurrentDirectory(['./*', '*', 'a/*', '../*', './../*']) - */ -function getPatternsInsideCurrentDirectory(patterns) { - return patterns.filter((pattern) => !isPatternRelatedToParentDirectory(pattern)); -} -exports.getPatternsInsideCurrentDirectory = getPatternsInsideCurrentDirectory; -/** - * Returns patterns to be expanded relative to (outside) the current directory. - * - * @example - * // ['../*', './../*'] - * getPatternsInsideCurrentDirectory(['./*', '*', 'a/*', '../*', './../*']) - */ -function getPatternsOutsideCurrentDirectory(patterns) { - return patterns.filter(isPatternRelatedToParentDirectory); -} -exports.getPatternsOutsideCurrentDirectory = getPatternsOutsideCurrentDirectory; -function isPatternRelatedToParentDirectory(pattern) { - return pattern.startsWith('..') || pattern.startsWith('./..'); -} -exports.isPatternRelatedToParentDirectory = isPatternRelatedToParentDirectory; -function getBaseDirectory(pattern) { - return globParent(pattern, { flipBackslashes: false }); -} -exports.getBaseDirectory = getBaseDirectory; -function hasGlobStar(pattern) { - return pattern.includes(GLOBSTAR); -} -exports.hasGlobStar = hasGlobStar; -function endsWithSlashGlobStar(pattern) { - return pattern.endsWith('/' + GLOBSTAR); -} -exports.endsWithSlashGlobStar = endsWithSlashGlobStar; -function isAffectDepthOfReadingPattern(pattern) { - const basename = path.basename(pattern); - return endsWithSlashGlobStar(pattern) || isStaticPattern(basename); -} -exports.isAffectDepthOfReadingPattern = isAffectDepthOfReadingPattern; -function expandPatternsWithBraceExpansion(patterns) { - return patterns.reduce((collection, pattern) => { - return collection.concat(expandBraceExpansion(pattern)); - }, []); -} -exports.expandPatternsWithBraceExpansion = expandPatternsWithBraceExpansion; -function expandBraceExpansion(pattern) { - return micromatch.braces(pattern, { - expand: true, - nodupes: true - }); -} -exports.expandBraceExpansion = expandBraceExpansion; -function getPatternParts(pattern, options) { - let { parts } = micromatch.scan(pattern, Object.assign(Object.assign({}, options), { parts: true })); - /** - * The scan method returns an empty array in some cases. - * See micromatch/picomatch#58 for more details. - */ - if (parts.length === 0) { - parts = [pattern]; - } - /** - * The scan method does not return an empty part for the pattern with a forward slash. - * This is another part of micromatch/picomatch#58. - */ - if (parts[0].startsWith('/')) { - parts[0] = parts[0].slice(1); - parts.unshift(''); - } - return parts; -} -exports.getPatternParts = getPatternParts; -function makeRe(pattern, options) { - return micromatch.makeRe(pattern, options); -} -exports.makeRe = makeRe; -function convertPatternsToRe(patterns, options) { - return patterns.map((pattern) => makeRe(pattern, options)); -} -exports.convertPatternsToRe = convertPatternsToRe; -function matchAny(entry, patternsRe) { - return patternsRe.some((patternRe) => patternRe.test(entry)); -} -exports.matchAny = matchAny; - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/stream.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.merge = void 0; -const merge2 = __webpack_require__("../../node_modules/merge2/index.js"); -function merge(streams) { - const mergedStream = merge2(streams); - streams.forEach((stream) => { - stream.once('error', (error) => mergedStream.emit('error', error)); - }); - mergedStream.once('close', () => propagateCloseEventToSources(streams)); - mergedStream.once('end', () => propagateCloseEventToSources(streams)); - return mergedStream; -} -exports.merge = merge; -function propagateCloseEventToSources(streams) { - streams.forEach((stream) => stream.emit('close')); -} - - -/***/ }), - -/***/ "../../node_modules/fast-glob/out/utils/string.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -Object.defineProperty(exports, "__esModule", { value: true }); -exports.isEmpty = exports.isString = void 0; -function isString(input) { - return typeof input === 'string'; -} -exports.isString = isString; -function isEmpty(input) { - return input === ''; -} -exports.isEmpty = isEmpty; - - -/***/ }), - -/***/ "../../node_modules/fastq/queue.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var reusify = __webpack_require__("../../node_modules/reusify/reusify.js") - -function fastqueue (context, worker, concurrency) { - if (typeof context === 'function') { - concurrency = worker - worker = context - context = null - } - - var cache = reusify(Task) - var queueHead = null - var queueTail = null - var _running = 0 - - var self = { - push: push, - drain: noop, - saturated: noop, - pause: pause, - paused: false, - concurrency: concurrency, - running: running, - resume: resume, - idle: idle, - length: length, - unshift: unshift, - empty: noop, - kill: kill, - killAndDrain: killAndDrain - } - - return self - - function running () { - return _running - } - - function pause () { - self.paused = true - } - - function length () { - var current = queueHead - var counter = 0 - - while (current) { - current = current.next - counter++ - } - - return counter - } - - function resume () { - if (!self.paused) return - self.paused = false - for (var i = 0; i < self.concurrency; i++) { - _running++ - release() - } - } - - function idle () { - return _running === 0 && self.length() === 0 - } - - function push (value, done) { - var current = cache.get() - - current.context = context - current.release = release - current.value = value - current.callback = done || noop - - if (_running === self.concurrency || self.paused) { - if (queueTail) { - queueTail.next = current - queueTail = current - } else { - queueHead = current - queueTail = current - self.saturated() - } - } else { - _running++ - worker.call(context, current.value, current.worked) - } - } - - function unshift (value, done) { - var current = cache.get() - - current.context = context - current.release = release - current.value = value - current.callback = done || noop - - if (_running === self.concurrency || self.paused) { - if (queueHead) { - current.next = queueHead - queueHead = current - } else { - queueHead = current - queueTail = current - self.saturated() - } - } else { - _running++ - worker.call(context, current.value, current.worked) - } - } - - function release (holder) { - if (holder) { - cache.release(holder) - } - var next = queueHead - if (next) { - if (!self.paused) { - if (queueTail === queueHead) { - queueTail = null - } - queueHead = next.next - next.next = null - worker.call(context, next.value, next.worked) - if (queueTail === null) { - self.empty() - } - } else { - _running-- - } - } else if (--_running === 0) { - self.drain() - } - } - - function kill () { - queueHead = null - queueTail = null - self.drain = noop - } - - function killAndDrain () { - queueHead = null - queueTail = null - self.drain() - self.drain = noop - } -} - -function noop () {} - -function Task () { - this.value = null - this.callback = noop - this.next = null - this.release = noop - this.context = null - - var self = this - - this.worked = function worked (err, result) { - var callback = self.callback - self.value = null - self.callback = noop - callback.call(self.context, err, result) - self.release(self) - } -} - -module.exports = fastqueue - - -/***/ }), - -/***/ "../../node_modules/fill-range/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/*! - * fill-range - * - * Copyright (c) 2014-present, Jon Schlinkert. - * Licensed under the MIT License. - */ - - - -const util = __webpack_require__("util"); -const toRegexRange = __webpack_require__("../../node_modules/to-regex-range/index.js"); - -const isObject = val => val !== null && typeof val === 'object' && !Array.isArray(val); - -const transform = toNumber => { - return value => toNumber === true ? Number(value) : String(value); -}; - -const isValidValue = value => { - return typeof value === 'number' || (typeof value === 'string' && value !== ''); -}; - -const isNumber = num => Number.isInteger(+num); - -const zeros = input => { - let value = `${input}`; - let index = -1; - if (value[0] === '-') value = value.slice(1); - if (value === '0') return false; - while (value[++index] === '0'); - return index > 0; -}; - -const stringify = (start, end, options) => { - if (typeof start === 'string' || typeof end === 'string') { - return true; - } - return options.stringify === true; -}; - -const pad = (input, maxLength, toNumber) => { - if (maxLength > 0) { - let dash = input[0] === '-' ? '-' : ''; - if (dash) input = input.slice(1); - input = (dash + input.padStart(dash ? maxLength - 1 : maxLength, '0')); - } - if (toNumber === false) { - return String(input); - } - return input; -}; - -const toMaxLen = (input, maxLength) => { - let negative = input[0] === '-' ? '-' : ''; - if (negative) { - input = input.slice(1); - maxLength--; - } - while (input.length < maxLength) input = '0' + input; - return negative ? ('-' + input) : input; -}; - -const toSequence = (parts, options) => { - parts.negatives.sort((a, b) => a < b ? -1 : a > b ? 1 : 0); - parts.positives.sort((a, b) => a < b ? -1 : a > b ? 1 : 0); - - let prefix = options.capture ? '' : '?:'; - let positives = ''; - let negatives = ''; - let result; - - if (parts.positives.length) { - positives = parts.positives.join('|'); - } - - if (parts.negatives.length) { - negatives = `-(${prefix}${parts.negatives.join('|')})`; - } - - if (positives && negatives) { - result = `${positives}|${negatives}`; - } else { - result = positives || negatives; - } - - if (options.wrap) { - return `(${prefix}${result})`; - } - - return result; -}; - -const toRange = (a, b, isNumbers, options) => { - if (isNumbers) { - return toRegexRange(a, b, { wrap: false, ...options }); - } - - let start = String.fromCharCode(a); - if (a === b) return start; - - let stop = String.fromCharCode(b); - return `[${start}-${stop}]`; -}; - -const toRegex = (start, end, options) => { - if (Array.isArray(start)) { - let wrap = options.wrap === true; - let prefix = options.capture ? '' : '?:'; - return wrap ? `(${prefix}${start.join('|')})` : start.join('|'); - } - return toRegexRange(start, end, options); -}; - -const rangeError = (...args) => { - return new RangeError('Invalid range arguments: ' + util.inspect(...args)); -}; - -const invalidRange = (start, end, options) => { - if (options.strictRanges === true) throw rangeError([start, end]); - return []; -}; - -const invalidStep = (step, options) => { - if (options.strictRanges === true) { - throw new TypeError(`Expected step "${step}" to be a number`); - } - return []; -}; - -const fillNumbers = (start, end, step = 1, options = {}) => { - let a = Number(start); - let b = Number(end); - - if (!Number.isInteger(a) || !Number.isInteger(b)) { - if (options.strictRanges === true) throw rangeError([start, end]); - return []; - } - - // fix negative zero - if (a === 0) a = 0; - if (b === 0) b = 0; - - let descending = a > b; - let startString = String(start); - let endString = String(end); - let stepString = String(step); - step = Math.max(Math.abs(step), 1); - - let padded = zeros(startString) || zeros(endString) || zeros(stepString); - let maxLen = padded ? Math.max(startString.length, endString.length, stepString.length) : 0; - let toNumber = padded === false && stringify(start, end, options) === false; - let format = options.transform || transform(toNumber); - - if (options.toRegex && step === 1) { - return toRange(toMaxLen(start, maxLen), toMaxLen(end, maxLen), true, options); - } - - let parts = { negatives: [], positives: [] }; - let push = num => parts[num < 0 ? 'negatives' : 'positives'].push(Math.abs(num)); - let range = []; - let index = 0; - - while (descending ? a >= b : a <= b) { - if (options.toRegex === true && step > 1) { - push(a); - } else { - range.push(pad(format(a, index), maxLen, toNumber)); - } - a = descending ? a - step : a + step; - index++; - } - - if (options.toRegex === true) { - return step > 1 - ? toSequence(parts, options) - : toRegex(range, null, { wrap: false, ...options }); - } - - return range; -}; - -const fillLetters = (start, end, step = 1, options = {}) => { - if ((!isNumber(start) && start.length > 1) || (!isNumber(end) && end.length > 1)) { - return invalidRange(start, end, options); - } - - - let format = options.transform || (val => String.fromCharCode(val)); - let a = `${start}`.charCodeAt(0); - let b = `${end}`.charCodeAt(0); - - let descending = a > b; - let min = Math.min(a, b); - let max = Math.max(a, b); - - if (options.toRegex && step === 1) { - return toRange(min, max, false, options); - } - - let range = []; - let index = 0; - - while (descending ? a >= b : a <= b) { - range.push(format(a, index)); - a = descending ? a - step : a + step; - index++; - } - - if (options.toRegex === true) { - return toRegex(range, null, { wrap: false, options }); - } - - return range; -}; - -const fill = (start, end, step, options = {}) => { - if (end == null && isValidValue(start)) { - return [start]; - } - - if (!isValidValue(start) || !isValidValue(end)) { - return invalidRange(start, end, options); - } - - if (typeof step === 'function') { - return fill(start, end, 1, { transform: step }); - } - - if (isObject(step)) { - return fill(start, end, 0, step); - } - - let opts = { ...options }; - if (opts.capture === true) opts.wrap = true; - step = step || opts.step || 1; - - if (!isNumber(step)) { - if (step != null && !isObject(step)) return invalidStep(step, opts); - return fill(start, end, 1, step); - } - - if (isNumber(start) && isNumber(end)) { - return fillNumbers(start, end, step, opts); - } - - return fillLetters(start, end, Math.max(Math.abs(step), 1), opts); -}; - -module.exports = fill; - - -/***/ }), - -/***/ "../../node_modules/follow-redirects/debug.js": -/***/ (function(module, exports, __webpack_require__) { - -var debug; - -module.exports = function () { - if (!debug) { - try { - /* eslint global-require: off */ - debug = __webpack_require__("../../node_modules/debug/src/index.js")("follow-redirects"); - } - catch (error) { /* */ } - if (typeof debug !== "function") { - debug = function () { /* */ }; - } - } - debug.apply(null, arguments); -}; - - -/***/ }), - -/***/ "../../node_modules/follow-redirects/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var url = __webpack_require__("url"); -var URL = url.URL; -var http = __webpack_require__("http"); -var https = __webpack_require__("https"); -var Writable = __webpack_require__("stream").Writable; -var assert = __webpack_require__("assert"); -var debug = __webpack_require__("../../node_modules/follow-redirects/debug.js"); - -// Create handlers that pass events from native requests -var events = ["abort", "aborted", "connect", "error", "socket", "timeout"]; -var eventHandlers = Object.create(null); -events.forEach(function (event) { - eventHandlers[event] = function (arg1, arg2, arg3) { - this._redirectable.emit(event, arg1, arg2, arg3); - }; -}); - -// Error types with codes -var RedirectionError = createErrorType( - "ERR_FR_REDIRECTION_FAILURE", - "Redirected request failed" -); -var TooManyRedirectsError = createErrorType( - "ERR_FR_TOO_MANY_REDIRECTS", - "Maximum number of redirects exceeded" -); -var MaxBodyLengthExceededError = createErrorType( - "ERR_FR_MAX_BODY_LENGTH_EXCEEDED", - "Request body larger than maxBodyLength limit" -); -var WriteAfterEndError = createErrorType( - "ERR_STREAM_WRITE_AFTER_END", - "write after end" -); - -// An HTTP(S) request that can be redirected -function RedirectableRequest(options, responseCallback) { - // Initialize the request - Writable.call(this); - this._sanitizeOptions(options); - this._options = options; - this._ended = false; - this._ending = false; - this._redirectCount = 0; - this._redirects = []; - this._requestBodyLength = 0; - this._requestBodyBuffers = []; - - // Attach a callback if passed - if (responseCallback) { - this.on("response", responseCallback); - } - - // React to responses of native requests - var self = this; - this._onNativeResponse = function (response) { - self._processResponse(response); - }; - - // Perform the first request - this._performRequest(); -} -RedirectableRequest.prototype = Object.create(Writable.prototype); - -RedirectableRequest.prototype.abort = function () { - abortRequest(this._currentRequest); - this.emit("abort"); -}; - -// Writes buffered data to the current native request -RedirectableRequest.prototype.write = function (data, encoding, callback) { - // Writing is not allowed if end has been called - if (this._ending) { - throw new WriteAfterEndError(); - } - - // Validate input and shift parameters if necessary - if (!(typeof data === "string" || typeof data === "object" && ("length" in data))) { - throw new TypeError("data should be a string, Buffer or Uint8Array"); - } - if (typeof encoding === "function") { - callback = encoding; - encoding = null; - } - - // Ignore empty buffers, since writing them doesn't invoke the callback - // https://github.com/nodejs/node/issues/22066 - if (data.length === 0) { - if (callback) { - callback(); - } - return; - } - // Only write when we don't exceed the maximum body length - if (this._requestBodyLength + data.length <= this._options.maxBodyLength) { - this._requestBodyLength += data.length; - this._requestBodyBuffers.push({ data: data, encoding: encoding }); - this._currentRequest.write(data, encoding, callback); - } - // Error when we exceed the maximum body length - else { - this.emit("error", new MaxBodyLengthExceededError()); - this.abort(); - } -}; - -// Ends the current native request -RedirectableRequest.prototype.end = function (data, encoding, callback) { - // Shift parameters if necessary - if (typeof data === "function") { - callback = data; - data = encoding = null; - } - else if (typeof encoding === "function") { - callback = encoding; - encoding = null; - } - - // Write data if needed and end - if (!data) { - this._ended = this._ending = true; - this._currentRequest.end(null, null, callback); - } - else { - var self = this; - var currentRequest = this._currentRequest; - this.write(data, encoding, function () { - self._ended = true; - currentRequest.end(null, null, callback); - }); - this._ending = true; - } -}; - -// Sets a header value on the current native request -RedirectableRequest.prototype.setHeader = function (name, value) { - this._options.headers[name] = value; - this._currentRequest.setHeader(name, value); -}; - -// Clears a header value on the current native request -RedirectableRequest.prototype.removeHeader = function (name) { - delete this._options.headers[name]; - this._currentRequest.removeHeader(name); -}; - -// Global timeout for all underlying requests -RedirectableRequest.prototype.setTimeout = function (msecs, callback) { - var self = this; - - // Destroys the socket on timeout - function destroyOnTimeout(socket) { - socket.setTimeout(msecs); - socket.removeListener("timeout", socket.destroy); - socket.addListener("timeout", socket.destroy); - } - - // Sets up a timer to trigger a timeout event - function startTimer(socket) { - if (self._timeout) { - clearTimeout(self._timeout); - } - self._timeout = setTimeout(function () { - self.emit("timeout"); - clearTimer(); - }, msecs); - destroyOnTimeout(socket); - } - - // Stops a timeout from triggering - function clearTimer() { - // Clear the timeout - if (self._timeout) { - clearTimeout(self._timeout); - self._timeout = null; - } - - // Clean up all attached listeners - self.removeListener("abort", clearTimer); - self.removeListener("error", clearTimer); - self.removeListener("response", clearTimer); - if (callback) { - self.removeListener("timeout", callback); - } - if (!self.socket) { - self._currentRequest.removeListener("socket", startTimer); - } - } - - // Attach callback if passed - if (callback) { - this.on("timeout", callback); - } - - // Start the timer if or when the socket is opened - if (this.socket) { - startTimer(this.socket); - } - else { - this._currentRequest.once("socket", startTimer); - } - - // Clean up on events - this.on("socket", destroyOnTimeout); - this.on("abort", clearTimer); - this.on("error", clearTimer); - this.on("response", clearTimer); - - return this; -}; - -// Proxy all other public ClientRequest methods -[ - "flushHeaders", "getHeader", - "setNoDelay", "setSocketKeepAlive", -].forEach(function (method) { - RedirectableRequest.prototype[method] = function (a, b) { - return this._currentRequest[method](a, b); - }; -}); - -// Proxy all public ClientRequest properties -["aborted", "connection", "socket"].forEach(function (property) { - Object.defineProperty(RedirectableRequest.prototype, property, { - get: function () { return this._currentRequest[property]; }, - }); -}); - -RedirectableRequest.prototype._sanitizeOptions = function (options) { - // Ensure headers are always present - if (!options.headers) { - options.headers = {}; - } - - // Since http.request treats host as an alias of hostname, - // but the url module interprets host as hostname plus port, - // eliminate the host property to avoid confusion. - if (options.host) { - // Use hostname if set, because it has precedence - if (!options.hostname) { - options.hostname = options.host; - } - delete options.host; - } - - // Complete the URL object when necessary - if (!options.pathname && options.path) { - var searchPos = options.path.indexOf("?"); - if (searchPos < 0) { - options.pathname = options.path; - } - else { - options.pathname = options.path.substring(0, searchPos); - options.search = options.path.substring(searchPos); - } - } -}; - - -// Executes the next native request (initial or redirect) -RedirectableRequest.prototype._performRequest = function () { - // Load the native protocol - var protocol = this._options.protocol; - var nativeProtocol = this._options.nativeProtocols[protocol]; - if (!nativeProtocol) { - this.emit("error", new TypeError("Unsupported protocol " + protocol)); - return; - } - - // If specified, use the agent corresponding to the protocol - // (HTTP and HTTPS use different types of agents) - if (this._options.agents) { - var scheme = protocol.slice(0, -1); - this._options.agent = this._options.agents[scheme]; - } - - // Create the native request - var request = this._currentRequest = - nativeProtocol.request(this._options, this._onNativeResponse); - this._currentUrl = url.format(this._options); - - // Set up event handlers - request._redirectable = this; - for (var e = 0; e < events.length; e++) { - request.on(events[e], eventHandlers[events[e]]); - } - - // End a redirected request - // (The first request must be ended explicitly with RedirectableRequest#end) - if (this._isRedirect) { - // Write the request entity and end. - var i = 0; - var self = this; - var buffers = this._requestBodyBuffers; - (function writeNext(error) { - // Only write if this request has not been redirected yet - /* istanbul ignore else */ - if (request === self._currentRequest) { - // Report any write errors - /* istanbul ignore if */ - if (error) { - self.emit("error", error); - } - // Write the next buffer if there are still left - else if (i < buffers.length) { - var buffer = buffers[i++]; - /* istanbul ignore else */ - if (!request.finished) { - request.write(buffer.data, buffer.encoding, writeNext); - } - } - // End the request if `end` has been called on us - else if (self._ended) { - request.end(); - } - } - }()); - } -}; - -// Processes a response from the current native request -RedirectableRequest.prototype._processResponse = function (response) { - // Store the redirected response - var statusCode = response.statusCode; - if (this._options.trackRedirects) { - this._redirects.push({ - url: this._currentUrl, - headers: response.headers, - statusCode: statusCode, - }); - } - - // RFC7231§6.4: The 3xx (Redirection) class of status code indicates - // that further action needs to be taken by the user agent in order to - // fulfill the request. If a Location header field is provided, - // the user agent MAY automatically redirect its request to the URI - // referenced by the Location field value, - // even if the specific status code is not understood. - - // If the response is not a redirect; return it as-is - var location = response.headers.location; - if (!location || this._options.followRedirects === false || - statusCode < 300 || statusCode >= 400) { - response.responseUrl = this._currentUrl; - response.redirects = this._redirects; - this.emit("response", response); - - // Clean up - this._requestBodyBuffers = []; - return; - } - - // The response is a redirect, so abort the current request - abortRequest(this._currentRequest); - // Discard the remainder of the response to avoid waiting for data - response.destroy(); - - // RFC7231§6.4: A client SHOULD detect and intervene - // in cyclical redirections (i.e., "infinite" redirection loops). - if (++this._redirectCount > this._options.maxRedirects) { - this.emit("error", new TooManyRedirectsError()); - return; - } - - // Store the request headers if applicable - var requestHeaders; - var beforeRedirect = this._options.beforeRedirect; - if (beforeRedirect) { - requestHeaders = Object.assign({ - // The Host header was set by nativeProtocol.request - Host: response.req.getHeader("host"), - }, this._options.headers); - } - - // RFC7231§6.4: Automatic redirection needs to done with - // care for methods not known to be safe, […] - // RFC7231§6.4.2–3: For historical reasons, a user agent MAY change - // the request method from POST to GET for the subsequent request. - var method = this._options.method; - if ((statusCode === 301 || statusCode === 302) && this._options.method === "POST" || - // RFC7231§6.4.4: The 303 (See Other) status code indicates that - // the server is redirecting the user agent to a different resource […] - // A user agent can perform a retrieval request targeting that URI - // (a GET or HEAD request if using HTTP) […] - (statusCode === 303) && !/^(?:GET|HEAD)$/.test(this._options.method)) { - this._options.method = "GET"; - // Drop a possible entity and headers related to it - this._requestBodyBuffers = []; - removeMatchingHeaders(/^content-/i, this._options.headers); - } - - // Drop the Host header, as the redirect might lead to a different host - var currentHostHeader = removeMatchingHeaders(/^host$/i, this._options.headers); - - // If the redirect is relative, carry over the host of the last request - var currentUrlParts = url.parse(this._currentUrl); - var currentHost = currentHostHeader || currentUrlParts.host; - var currentUrl = /^\w+:/.test(location) ? this._currentUrl : - url.format(Object.assign(currentUrlParts, { host: currentHost })); - - // Determine the URL of the redirection - var redirectUrl; - try { - redirectUrl = url.resolve(currentUrl, location); - } - catch (cause) { - this.emit("error", new RedirectionError(cause)); - return; - } - - // Create the redirected request - debug("redirecting to", redirectUrl); - this._isRedirect = true; - var redirectUrlParts = url.parse(redirectUrl); - Object.assign(this._options, redirectUrlParts); - - // Drop confidential headers when redirecting to a less secure protocol - // or to a different domain that is not a superdomain - if (redirectUrlParts.protocol !== currentUrlParts.protocol && - redirectUrlParts.protocol !== "https:" || - redirectUrlParts.host !== currentHost && - !isSubdomain(redirectUrlParts.host, currentHost)) { - removeMatchingHeaders(/^(?:authorization|cookie)$/i, this._options.headers); - } - - // Evaluate the beforeRedirect callback - if (typeof beforeRedirect === "function") { - var responseDetails = { - headers: response.headers, - statusCode: statusCode, - }; - var requestDetails = { - url: currentUrl, - method: method, - headers: requestHeaders, - }; - try { - beforeRedirect(this._options, responseDetails, requestDetails); - } - catch (err) { - this.emit("error", err); - return; - } - this._sanitizeOptions(this._options); - } - - // Perform the redirected request - try { - this._performRequest(); - } - catch (cause) { - this.emit("error", new RedirectionError(cause)); - } -}; - -// Wraps the key/value object of protocols with redirect functionality -function wrap(protocols) { - // Default settings - var exports = { - maxRedirects: 21, - maxBodyLength: 10 * 1024 * 1024, - }; - - // Wrap each protocol - var nativeProtocols = {}; - Object.keys(protocols).forEach(function (scheme) { - var protocol = scheme + ":"; - var nativeProtocol = nativeProtocols[protocol] = protocols[scheme]; - var wrappedProtocol = exports[scheme] = Object.create(nativeProtocol); - - // Executes a request, following redirects - function request(input, options, callback) { - // Parse parameters - if (typeof input === "string") { - var urlStr = input; - try { - input = urlToOptions(new URL(urlStr)); - } - catch (err) { - /* istanbul ignore next */ - input = url.parse(urlStr); - } - } - else if (URL && (input instanceof URL)) { - input = urlToOptions(input); - } - else { - callback = options; - options = input; - input = { protocol: protocol }; - } - if (typeof options === "function") { - callback = options; - options = null; - } - - // Set defaults - options = Object.assign({ - maxRedirects: exports.maxRedirects, - maxBodyLength: exports.maxBodyLength, - }, input, options); - options.nativeProtocols = nativeProtocols; - - assert.equal(options.protocol, protocol, "protocol mismatch"); - debug("options", options); - return new RedirectableRequest(options, callback); - } - - // Executes a GET request, following redirects - function get(input, options, callback) { - var wrappedRequest = wrappedProtocol.request(input, options, callback); - wrappedRequest.end(); - return wrappedRequest; - } - - // Expose the properties on the wrapped protocol - Object.defineProperties(wrappedProtocol, { - request: { value: request, configurable: true, enumerable: true, writable: true }, - get: { value: get, configurable: true, enumerable: true, writable: true }, - }); - }); - return exports; -} - -/* istanbul ignore next */ -function noop() { /* empty */ } - -// from https://github.com/nodejs/node/blob/master/lib/internal/url.js -function urlToOptions(urlObject) { - var options = { - protocol: urlObject.protocol, - hostname: urlObject.hostname.startsWith("[") ? - /* istanbul ignore next */ - urlObject.hostname.slice(1, -1) : - urlObject.hostname, - hash: urlObject.hash, - search: urlObject.search, - pathname: urlObject.pathname, - path: urlObject.pathname + urlObject.search, - href: urlObject.href, - }; - if (urlObject.port !== "") { - options.port = Number(urlObject.port); - } - return options; -} - -function removeMatchingHeaders(regex, headers) { - var lastValue; - for (var header in headers) { - if (regex.test(header)) { - lastValue = headers[header]; - delete headers[header]; - } - } - return (lastValue === null || typeof lastValue === "undefined") ? - undefined : String(lastValue).trim(); -} - -function createErrorType(code, defaultMessage) { - function CustomError(cause) { - Error.captureStackTrace(this, this.constructor); - if (!cause) { - this.message = defaultMessage; - } - else { - this.message = defaultMessage + ": " + cause.message; - this.cause = cause; - } - } - CustomError.prototype = new Error(); - CustomError.prototype.constructor = CustomError; - CustomError.prototype.name = "Error [" + code + "]"; - CustomError.prototype.code = code; - return CustomError; -} - -function abortRequest(request) { - for (var e = 0; e < events.length; e++) { - request.removeListener(events[e], eventHandlers[events[e]]); - } - request.on("error", noop); - request.abort(); -} - -function isSubdomain(subdomain, domain) { - const dot = subdomain.length - domain.length - 1; - return dot > 0 && subdomain[dot] === "." && subdomain.endsWith(domain); -} - -// Exports -module.exports = wrap({ http: http, https: https }); -module.exports.wrap = wrap; - - -/***/ }), - -/***/ "../../node_modules/form-data/lib/form_data.js": -/***/ (function(module, exports, __webpack_require__) { - -var CombinedStream = __webpack_require__("../../node_modules/combined-stream/lib/combined_stream.js"); -var util = __webpack_require__("util"); -var path = __webpack_require__("path"); -var http = __webpack_require__("http"); -var https = __webpack_require__("https"); -var parseUrl = __webpack_require__("url").parse; -var fs = __webpack_require__("fs"); -var Stream = __webpack_require__("stream").Stream; -var mime = __webpack_require__("../../node_modules/mime-types/index.js"); -var asynckit = __webpack_require__("../../node_modules/asynckit/index.js"); -var populate = __webpack_require__("../../node_modules/form-data/lib/populate.js"); - -// Public API -module.exports = FormData; - -// make it a Stream -util.inherits(FormData, CombinedStream); - -/** - * Create readable "multipart/form-data" streams. - * Can be used to submit forms - * and file uploads to other web applications. - * - * @constructor - * @param {Object} options - Properties to be added/overriden for FormData and CombinedStream - */ -function FormData(options) { - if (!(this instanceof FormData)) { - return new FormData(options); - } - - this._overheadLength = 0; - this._valueLength = 0; - this._valuesToMeasure = []; - - CombinedStream.call(this); - - options = options || {}; - for (var option in options) { - this[option] = options[option]; - } -} - -FormData.LINE_BREAK = '\r\n'; -FormData.DEFAULT_CONTENT_TYPE = 'application/octet-stream'; - -FormData.prototype.append = function(field, value, options) { - - options = options || {}; - - // allow filename as single option - if (typeof options == 'string') { - options = {filename: options}; - } - - var append = CombinedStream.prototype.append.bind(this); - - // all that streamy business can't handle numbers - if (typeof value == 'number') { - value = '' + value; - } - - // https://github.com/felixge/node-form-data/issues/38 - if (util.isArray(value)) { - // Please convert your array into string - // the way web server expects it - this._error(new Error('Arrays are not supported.')); - return; - } - - var header = this._multiPartHeader(field, value, options); - var footer = this._multiPartFooter(); - - append(header); - append(value); - append(footer); - - // pass along options.knownLength - this._trackLength(header, value, options); -}; - -FormData.prototype._trackLength = function(header, value, options) { - var valueLength = 0; - - // used w/ getLengthSync(), when length is known. - // e.g. for streaming directly from a remote server, - // w/ a known file a size, and not wanting to wait for - // incoming file to finish to get its size. - if (options.knownLength != null) { - valueLength += +options.knownLength; - } else if (Buffer.isBuffer(value)) { - valueLength = value.length; - } else if (typeof value === 'string') { - valueLength = Buffer.byteLength(value); - } - - this._valueLength += valueLength; - - // @check why add CRLF? does this account for custom/multiple CRLFs? - this._overheadLength += - Buffer.byteLength(header) + - FormData.LINE_BREAK.length; - - // empty or either doesn't have path or not an http response or not a stream - if (!value || ( !value.path && !(value.readable && value.hasOwnProperty('httpVersion')) && !(value instanceof Stream))) { - return; - } - - // no need to bother with the length - if (!options.knownLength) { - this._valuesToMeasure.push(value); - } -}; - -FormData.prototype._lengthRetriever = function(value, callback) { - - if (value.hasOwnProperty('fd')) { - - // take read range into a account - // `end` = Infinity –> read file till the end - // - // TODO: Looks like there is bug in Node fs.createReadStream - // it doesn't respect `end` options without `start` options - // Fix it when node fixes it. - // https://github.com/joyent/node/issues/7819 - if (value.end != undefined && value.end != Infinity && value.start != undefined) { - - // when end specified - // no need to calculate range - // inclusive, starts with 0 - callback(null, value.end + 1 - (value.start ? value.start : 0)); - - // not that fast snoopy - } else { - // still need to fetch file size from fs - fs.stat(value.path, function(err, stat) { - - var fileSize; - - if (err) { - callback(err); - return; - } - - // update final size based on the range options - fileSize = stat.size - (value.start ? value.start : 0); - callback(null, fileSize); - }); - } - - // or http response - } else if (value.hasOwnProperty('httpVersion')) { - callback(null, +value.headers['content-length']); - - // or request stream http://github.com/mikeal/request - } else if (value.hasOwnProperty('httpModule')) { - // wait till response come back - value.on('response', function(response) { - value.pause(); - callback(null, +response.headers['content-length']); - }); - value.resume(); - - // something else - } else { - callback('Unknown stream'); - } -}; - -FormData.prototype._multiPartHeader = function(field, value, options) { - // custom header specified (as string)? - // it becomes responsible for boundary - // (e.g. to handle extra CRLFs on .NET servers) - if (typeof options.header == 'string') { - return options.header; - } - - var contentDisposition = this._getContentDisposition(value, options); - var contentType = this._getContentType(value, options); - - var contents = ''; - var headers = { - // add custom disposition as third element or keep it two elements if not - 'Content-Disposition': ['form-data', 'name="' + field + '"'].concat(contentDisposition || []), - // if no content type. allow it to be empty array - 'Content-Type': [].concat(contentType || []) - }; - - // allow custom headers. - if (typeof options.header == 'object') { - populate(headers, options.header); - } - - var header; - for (var prop in headers) { - if (!headers.hasOwnProperty(prop)) continue; - header = headers[prop]; - - // skip nullish headers. - if (header == null) { - continue; - } - - // convert all headers to arrays. - if (!Array.isArray(header)) { - header = [header]; - } - - // add non-empty headers. - if (header.length) { - contents += prop + ': ' + header.join('; ') + FormData.LINE_BREAK; - } - } - - return '--' + this.getBoundary() + FormData.LINE_BREAK + contents + FormData.LINE_BREAK; -}; - -FormData.prototype._getContentDisposition = function(value, options) { - - var filename - , contentDisposition - ; - - if (typeof options.filepath === 'string') { - // custom filepath for relative paths - filename = path.normalize(options.filepath).replace(/\\/g, '/'); - } else if (options.filename || value.name || value.path) { - // custom filename take precedence - // formidable and the browser add a name property - // fs- and request- streams have path property - filename = path.basename(options.filename || value.name || value.path); - } else if (value.readable && value.hasOwnProperty('httpVersion')) { - // or try http response - filename = path.basename(value.client._httpMessage.path || ''); - } - - if (filename) { - contentDisposition = 'filename="' + filename + '"'; - } - - return contentDisposition; -}; - -FormData.prototype._getContentType = function(value, options) { - - // use custom content-type above all - var contentType = options.contentType; - - // or try `name` from formidable, browser - if (!contentType && value.name) { - contentType = mime.lookup(value.name); - } - - // or try `path` from fs-, request- streams - if (!contentType && value.path) { - contentType = mime.lookup(value.path); - } - - // or if it's http-reponse - if (!contentType && value.readable && value.hasOwnProperty('httpVersion')) { - contentType = value.headers['content-type']; - } - - // or guess it from the filepath or filename - if (!contentType && (options.filepath || options.filename)) { - contentType = mime.lookup(options.filepath || options.filename); - } - - // fallback to the default content type if `value` is not simple value - if (!contentType && typeof value == 'object') { - contentType = FormData.DEFAULT_CONTENT_TYPE; - } - - return contentType; -}; - -FormData.prototype._multiPartFooter = function() { - return function(next) { - var footer = FormData.LINE_BREAK; - - var lastPart = (this._streams.length === 0); - if (lastPart) { - footer += this._lastBoundary(); - } - - next(footer); - }.bind(this); -}; - -FormData.prototype._lastBoundary = function() { - return '--' + this.getBoundary() + '--' + FormData.LINE_BREAK; -}; - -FormData.prototype.getHeaders = function(userHeaders) { - var header; - var formHeaders = { - 'content-type': 'multipart/form-data; boundary=' + this.getBoundary() - }; - - for (header in userHeaders) { - if (userHeaders.hasOwnProperty(header)) { - formHeaders[header.toLowerCase()] = userHeaders[header]; - } - } - - return formHeaders; -}; - -FormData.prototype.setBoundary = function(boundary) { - this._boundary = boundary; -}; - -FormData.prototype.getBoundary = function() { - if (!this._boundary) { - this._generateBoundary(); - } - - return this._boundary; -}; - -FormData.prototype.getBuffer = function() { - var dataBuffer = new Buffer.alloc( 0 ); - var boundary = this.getBoundary(); - - // Create the form content. Add Line breaks to the end of data. - for (var i = 0, len = this._streams.length; i < len; i++) { - if (typeof this._streams[i] !== 'function') { - - // Add content to the buffer. - if(Buffer.isBuffer(this._streams[i])) { - dataBuffer = Buffer.concat( [dataBuffer, this._streams[i]]); - }else { - dataBuffer = Buffer.concat( [dataBuffer, Buffer.from(this._streams[i])]); - } - - // Add break after content. - if (typeof this._streams[i] !== 'string' || this._streams[i].substring( 2, boundary.length + 2 ) !== boundary) { - dataBuffer = Buffer.concat( [dataBuffer, Buffer.from(FormData.LINE_BREAK)] ); - } - } - } - - // Add the footer and return the Buffer object. - return Buffer.concat( [dataBuffer, Buffer.from(this._lastBoundary())] ); -}; - -FormData.prototype._generateBoundary = function() { - // This generates a 50 character boundary similar to those used by Firefox. - // They are optimized for boyer-moore parsing. - var boundary = '--------------------------'; - for (var i = 0; i < 24; i++) { - boundary += Math.floor(Math.random() * 10).toString(16); - } - - this._boundary = boundary; -}; - -// Note: getLengthSync DOESN'T calculate streams length -// As workaround one can calculate file size manually -// and add it as knownLength option -FormData.prototype.getLengthSync = function() { - var knownLength = this._overheadLength + this._valueLength; - - // Don't get confused, there are 3 "internal" streams for each keyval pair - // so it basically checks if there is any value added to the form - if (this._streams.length) { - knownLength += this._lastBoundary().length; - } - - // https://github.com/form-data/form-data/issues/40 - if (!this.hasKnownLength()) { - // Some async length retrievers are present - // therefore synchronous length calculation is false. - // Please use getLength(callback) to get proper length - this._error(new Error('Cannot calculate proper length in synchronous way.')); - } - - return knownLength; -}; - -// Public API to check if length of added values is known -// https://github.com/form-data/form-data/issues/196 -// https://github.com/form-data/form-data/issues/262 -FormData.prototype.hasKnownLength = function() { - var hasKnownLength = true; - - if (this._valuesToMeasure.length) { - hasKnownLength = false; - } - - return hasKnownLength; -}; - -FormData.prototype.getLength = function(cb) { - var knownLength = this._overheadLength + this._valueLength; - - if (this._streams.length) { - knownLength += this._lastBoundary().length; - } - - if (!this._valuesToMeasure.length) { - process.nextTick(cb.bind(this, null, knownLength)); - return; - } - - asynckit.parallel(this._valuesToMeasure, this._lengthRetriever, function(err, values) { - if (err) { - cb(err); - return; - } - - values.forEach(function(length) { - knownLength += length; - }); - - cb(null, knownLength); - }); -}; - -FormData.prototype.submit = function(params, cb) { - var request - , options - , defaults = {method: 'post'} - ; - - // parse provided url if it's string - // or treat it as options object - if (typeof params == 'string') { - - params = parseUrl(params); - options = populate({ - port: params.port, - path: params.pathname, - host: params.hostname, - protocol: params.protocol - }, defaults); - - // use custom params - } else { - - options = populate(params, defaults); - // if no port provided use default one - if (!options.port) { - options.port = options.protocol == 'https:' ? 443 : 80; - } - } - - // put that good code in getHeaders to some use - options.headers = this.getHeaders(params.headers); - - // https if specified, fallback to http in any other case - if (options.protocol == 'https:') { - request = https.request(options); - } else { - request = http.request(options); - } - - // get content length and fire away - this.getLength(function(err, length) { - if (err && err !== 'Unknown stream') { - this._error(err); - return; - } - - // add content length - if (length) { - request.setHeader('Content-Length', length); - } - - this.pipe(request); - if (cb) { - var onResponse; - - var callback = function (error, responce) { - request.removeListener('error', callback); - request.removeListener('response', onResponse); - - return cb.call(this, error, responce); - }; - - onResponse = callback.bind(this, null); - - request.on('error', callback); - request.on('response', onResponse); - } - }.bind(this)); - - return request; -}; - -FormData.prototype._error = function(err) { - if (!this.error) { - this.error = err; - this.pause(); - this.emit('error', err); - } -}; - -FormData.prototype.toString = function () { - return '[object FormData]'; -}; - - -/***/ }), - -/***/ "../../node_modules/form-data/lib/populate.js": -/***/ (function(module, exports) { - -// populates missing values -module.exports = function(dst, src) { - - Object.keys(src).forEach(function(prop) - { - dst[prop] = dst[prop] || src[prop]; - }); - - return dst; -}; - - -/***/ }), - -/***/ "../../node_modules/fs.realpath/index.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = realpath -realpath.realpath = realpath -realpath.sync = realpathSync -realpath.realpathSync = realpathSync -realpath.monkeypatch = monkeypatch -realpath.unmonkeypatch = unmonkeypatch - -var fs = __webpack_require__("fs") -var origRealpath = fs.realpath -var origRealpathSync = fs.realpathSync - -var version = process.version -var ok = /^v[0-5]\./.test(version) -var old = __webpack_require__("../../node_modules/fs.realpath/old.js") - -function newError (er) { - return er && er.syscall === 'realpath' && ( - er.code === 'ELOOP' || - er.code === 'ENOMEM' || - er.code === 'ENAMETOOLONG' - ) -} - -function realpath (p, cache, cb) { - if (ok) { - return origRealpath(p, cache, cb) - } - - if (typeof cache === 'function') { - cb = cache - cache = null - } - origRealpath(p, cache, function (er, result) { - if (newError(er)) { - old.realpath(p, cache, cb) - } else { - cb(er, result) - } - }) -} - -function realpathSync (p, cache) { - if (ok) { - return origRealpathSync(p, cache) - } - - try { - return origRealpathSync(p, cache) - } catch (er) { - if (newError(er)) { - return old.realpathSync(p, cache) - } else { - throw er - } - } -} - -function monkeypatch () { - fs.realpath = realpath - fs.realpathSync = realpathSync -} - -function unmonkeypatch () { - fs.realpath = origRealpath - fs.realpathSync = origRealpathSync -} - - -/***/ }), - -/***/ "../../node_modules/fs.realpath/old.js": -/***/ (function(module, exports, __webpack_require__) { - -// Copyright Joyent, Inc. and other Node contributors. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. - -var pathModule = __webpack_require__("path"); -var isWindows = process.platform === 'win32'; -var fs = __webpack_require__("fs"); - -// JavaScript implementation of realpath, ported from node pre-v6 - -var DEBUG = process.env.NODE_DEBUG && /fs/.test(process.env.NODE_DEBUG); - -function rethrow() { - // Only enable in debug mode. A backtrace uses ~1000 bytes of heap space and - // is fairly slow to generate. - var callback; - if (DEBUG) { - var backtrace = new Error; - callback = debugCallback; - } else - callback = missingCallback; - - return callback; - - function debugCallback(err) { - if (err) { - backtrace.message = err.message; - err = backtrace; - missingCallback(err); - } - } - - function missingCallback(err) { - if (err) { - if (process.throwDeprecation) - throw err; // Forgot a callback but don't know where? Use NODE_DEBUG=fs - else if (!process.noDeprecation) { - var msg = 'fs: missing callback ' + (err.stack || err.message); - if (process.traceDeprecation) - console.trace(msg); - else - console.error(msg); - } - } - } -} - -function maybeCallback(cb) { - return typeof cb === 'function' ? cb : rethrow(); -} - -var normalize = pathModule.normalize; - -// Regexp that finds the next partion of a (partial) path -// result is [base_with_slash, base], e.g. ['somedir/', 'somedir'] -if (isWindows) { - var nextPartRe = /(.*?)(?:[\/\\]+|$)/g; -} else { - var nextPartRe = /(.*?)(?:[\/]+|$)/g; -} - -// Regex to find the device root, including trailing slash. E.g. 'c:\\'. -if (isWindows) { - var splitRootRe = /^(?:[a-zA-Z]:|[\\\/]{2}[^\\\/]+[\\\/][^\\\/]+)?[\\\/]*/; -} else { - var splitRootRe = /^[\/]*/; -} - -exports.realpathSync = function realpathSync(p, cache) { - // make p is absolute - p = pathModule.resolve(p); - - if (cache && Object.prototype.hasOwnProperty.call(cache, p)) { - return cache[p]; - } - - var original = p, - seenLinks = {}, - knownHard = {}; - - // current character position in p - var pos; - // the partial path so far, including a trailing slash if any - var current; - // the partial path without a trailing slash (except when pointing at a root) - var base; - // the partial path scanned in the previous round, with slash - var previous; - - start(); - - function start() { - // Skip over roots - var m = splitRootRe.exec(p); - pos = m[0].length; - current = m[0]; - base = m[0]; - previous = ''; - - // On windows, check that the root exists. On unix there is no need. - if (isWindows && !knownHard[base]) { - fs.lstatSync(base); - knownHard[base] = true; - } - } - - // walk down the path, swapping out linked pathparts for their real - // values - // NB: p.length changes. - while (pos < p.length) { - // find the next part - nextPartRe.lastIndex = pos; - var result = nextPartRe.exec(p); - previous = current; - current += result[0]; - base = previous + result[1]; - pos = nextPartRe.lastIndex; - - // continue if not a symlink - if (knownHard[base] || (cache && cache[base] === base)) { - continue; - } - - var resolvedLink; - if (cache && Object.prototype.hasOwnProperty.call(cache, base)) { - // some known symbolic link. no need to stat again. - resolvedLink = cache[base]; - } else { - var stat = fs.lstatSync(base); - if (!stat.isSymbolicLink()) { - knownHard[base] = true; - if (cache) cache[base] = base; - continue; - } - - // read the link if it wasn't read before - // dev/ino always return 0 on windows, so skip the check. - var linkTarget = null; - if (!isWindows) { - var id = stat.dev.toString(32) + ':' + stat.ino.toString(32); - if (seenLinks.hasOwnProperty(id)) { - linkTarget = seenLinks[id]; - } - } - if (linkTarget === null) { - fs.statSync(base); - linkTarget = fs.readlinkSync(base); - } - resolvedLink = pathModule.resolve(previous, linkTarget); - // track this, if given a cache. - if (cache) cache[base] = resolvedLink; - if (!isWindows) seenLinks[id] = linkTarget; - } - - // resolve the link, then start over - p = pathModule.resolve(resolvedLink, p.slice(pos)); - start(); - } - - if (cache) cache[original] = p; - - return p; -}; - - -exports.realpath = function realpath(p, cache, cb) { - if (typeof cb !== 'function') { - cb = maybeCallback(cache); - cache = null; - } - - // make p is absolute - p = pathModule.resolve(p); - - if (cache && Object.prototype.hasOwnProperty.call(cache, p)) { - return process.nextTick(cb.bind(null, null, cache[p])); - } - - var original = p, - seenLinks = {}, - knownHard = {}; - - // current character position in p - var pos; - // the partial path so far, including a trailing slash if any - var current; - // the partial path without a trailing slash (except when pointing at a root) - var base; - // the partial path scanned in the previous round, with slash - var previous; - - start(); - - function start() { - // Skip over roots - var m = splitRootRe.exec(p); - pos = m[0].length; - current = m[0]; - base = m[0]; - previous = ''; - - // On windows, check that the root exists. On unix there is no need. - if (isWindows && !knownHard[base]) { - fs.lstat(base, function(err) { - if (err) return cb(err); - knownHard[base] = true; - LOOP(); - }); - } else { - process.nextTick(LOOP); - } - } - - // walk down the path, swapping out linked pathparts for their real - // values - function LOOP() { - // stop if scanned past end of path - if (pos >= p.length) { - if (cache) cache[original] = p; - return cb(null, p); - } - - // find the next part - nextPartRe.lastIndex = pos; - var result = nextPartRe.exec(p); - previous = current; - current += result[0]; - base = previous + result[1]; - pos = nextPartRe.lastIndex; - - // continue if not a symlink - if (knownHard[base] || (cache && cache[base] === base)) { - return process.nextTick(LOOP); - } - - if (cache && Object.prototype.hasOwnProperty.call(cache, base)) { - // known symbolic link. no need to stat again. - return gotResolvedLink(cache[base]); - } - - return fs.lstat(base, gotStat); - } - - function gotStat(err, stat) { - if (err) return cb(err); - - // if not a symlink, skip to the next path part - if (!stat.isSymbolicLink()) { - knownHard[base] = true; - if (cache) cache[base] = base; - return process.nextTick(LOOP); - } - - // stat & read the link if not read before - // call gotTarget as soon as the link target is known - // dev/ino always return 0 on windows, so skip the check. - if (!isWindows) { - var id = stat.dev.toString(32) + ':' + stat.ino.toString(32); - if (seenLinks.hasOwnProperty(id)) { - return gotTarget(null, seenLinks[id], base); - } - } - fs.stat(base, function(err) { - if (err) return cb(err); - - fs.readlink(base, function(err, target) { - if (!isWindows) seenLinks[id] = target; - gotTarget(err, target); - }); - }); - } - - function gotTarget(err, target, base) { - if (err) return cb(err); - - var resolvedLink = pathModule.resolve(previous, target); - if (cache) cache[base] = resolvedLink; - gotResolvedLink(resolvedLink); - } - - function gotResolvedLink(resolvedLink) { - // resolve the link, then start over - p = pathModule.resolve(resolvedLink, p.slice(pos)); - start(); - } -}; - - -/***/ }), - -/***/ "../../node_modules/function-bind/implementation.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -/* eslint no-invalid-this: 1 */ - -var ERROR_MESSAGE = 'Function.prototype.bind called on incompatible '; -var slice = Array.prototype.slice; -var toStr = Object.prototype.toString; -var funcType = '[object Function]'; - -module.exports = function bind(that) { - var target = this; - if (typeof target !== 'function' || toStr.call(target) !== funcType) { - throw new TypeError(ERROR_MESSAGE + target); - } - var args = slice.call(arguments, 1); - - var bound; - var binder = function () { - if (this instanceof bound) { - var result = target.apply( - this, - args.concat(slice.call(arguments)) - ); - if (Object(result) === result) { - return result; - } - return this; - } else { - return target.apply( - that, - args.concat(slice.call(arguments)) - ); - } - }; - - var boundLength = Math.max(0, target.length - args.length); - var boundArgs = []; - for (var i = 0; i < boundLength; i++) { - boundArgs.push('$' + i); - } - - bound = Function('binder', 'return function (' + boundArgs.join(',') + '){ return binder.apply(this,arguments); }')(binder); - - if (target.prototype) { - var Empty = function Empty() {}; - Empty.prototype = target.prototype; - bound.prototype = new Empty(); - Empty.prototype = null; - } - - return bound; -}; - - -/***/ }), - -/***/ "../../node_modules/function-bind/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var implementation = __webpack_require__("../../node_modules/function-bind/implementation.js"); - -module.exports = Function.prototype.bind || implementation; - - -/***/ }), - -/***/ "../../node_modules/get-stream/buffer-stream.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {PassThrough: PassThroughStream} = __webpack_require__("stream"); - -module.exports = options => { - options = {...options}; - - const {array} = options; - let {encoding} = options; - const isBuffer = encoding === 'buffer'; - let objectMode = false; - - if (array) { - objectMode = !(encoding || isBuffer); - } else { - encoding = encoding || 'utf8'; - } - - if (isBuffer) { - encoding = null; - } - - const stream = new PassThroughStream({objectMode}); - - if (encoding) { - stream.setEncoding(encoding); - } - - let length = 0; - const chunks = []; - - stream.on('data', chunk => { - chunks.push(chunk); - - if (objectMode) { - length = chunks.length; - } else { - length += chunk.length; - } - }); - - stream.getBufferedValue = () => { - if (array) { - return chunks; - } - - return isBuffer ? Buffer.concat(chunks, length) : chunks.join(''); - }; - - stream.getBufferedLength = () => length; - - return stream; -}; - - -/***/ }), - -/***/ "../../node_modules/get-stream/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const pump = __webpack_require__("../../node_modules/pump/index.js"); -const bufferStream = __webpack_require__("../../node_modules/get-stream/buffer-stream.js"); - -class MaxBufferError extends Error { - constructor() { - super('maxBuffer exceeded'); - this.name = 'MaxBufferError'; - } -} - -async function getStream(inputStream, options) { - if (!inputStream) { - return Promise.reject(new Error('Expected a stream')); - } - - options = { - maxBuffer: Infinity, - ...options - }; - - const {maxBuffer} = options; - - let stream; - await new Promise((resolve, reject) => { - const rejectPromise = error => { - if (error) { // A null check - error.bufferedData = stream.getBufferedValue(); - } - - reject(error); - }; - - stream = pump(inputStream, bufferStream(options), error => { - if (error) { - rejectPromise(error); - return; - } - - resolve(); - }); - - stream.on('data', () => { - if (stream.getBufferedLength() > maxBuffer) { - rejectPromise(new MaxBufferError()); - } - }); - }); - - return stream.getBufferedValue(); -} - -module.exports = getStream; -// TODO: Remove this for the next major release -module.exports.default = getStream; -module.exports.buffer = (stream, options) => getStream(stream, {...options, encoding: 'buffer'}); -module.exports.array = (stream, options) => getStream(stream, {...options, array: true}); -module.exports.MaxBufferError = MaxBufferError; - - -/***/ }), - -/***/ "../../node_modules/getopts/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const EMPTYARR = [] -const SHORTSPLIT = /$|[!-@[-`{-~][\s\S]*/g -const isArray = Array.isArray - -const parseValue = function(any) { - if (any === "") return "" - if (any === "false") return false - const maybe = Number(any) - return maybe * 0 === 0 ? maybe : any -} - -const parseAlias = function(aliases) { - let out = {}, - key, - alias, - prev, - len, - any, - i, - k - - for (key in aliases) { - any = aliases[key] - alias = out[key] = isArray(any) ? any : [any] - - for (i = 0, len = alias.length; i < len; i++) { - prev = out[alias[i]] = [key] - - for (k = 0; k < len; k++) { - if (i !== k) prev.push(alias[k]) - } - } - } - - return out -} - -const parseDefault = function(aliases, defaults) { - let out = {}, - key, - alias, - value, - len, - i - - for (key in defaults) { - value = defaults[key] - alias = aliases[key] - - out[key] = value - - if (alias === undefined) { - aliases[key] = EMPTYARR - } else { - for (i = 0, len = alias.length; i < len; i++) { - out[alias[i]] = value - } - } - } - - return out -} - -const parseOptions = function(aliases, options, value) { - let out = {}, - key, - alias, - len, - end, - i, - k - - if (options !== undefined) { - for (i = 0, len = options.length; i < len; i++) { - key = options[i] - alias = aliases[key] - - out[key] = value - - if (alias === undefined) { - aliases[key] = EMPTYARR - } else { - for (k = 0, end = alias.length; k < end; k++) { - out[alias[k]] = value - } - } - } - } - - return out -} - -const write = function(out, key, value, aliases, unknown) { - let i, - prev, - alias = aliases[key], - len = alias === undefined ? -1 : alias.length - - if (len >= 0 || unknown === undefined || unknown(key)) { - prev = out[key] - - if (prev === undefined) { - out[key] = value - } else { - if (isArray(prev)) { - prev.push(value) - } else { - out[key] = [prev, value] - } - } - - for (i = 0; i < len; i++) { - out[alias[i]] = out[key] - } - } -} - -const getopts = function(argv, opts) { - let unknown = (opts = opts || {}).unknown, - aliases = parseAlias(opts.alias), - strings = parseOptions(aliases, opts.string, ""), - values = parseDefault(aliases, opts.default), - bools = parseOptions(aliases, opts.boolean, false), - stopEarly = opts.stopEarly, - _ = [], - out = { _ }, - i = 0, - k = 0, - len = argv.length, - key, - arg, - end, - match, - value - - for (; i < len; i++) { - arg = argv[i] - - if (arg[0] !== "-" || arg === "-") { - if (stopEarly) while (i < len) _.push(argv[i++]) - else _.push(arg) - } else if (arg === "--") { - while (++i < len) _.push(argv[i]) - } else if (arg[1] === "-") { - end = arg.indexOf("=", 2) - if (arg[2] === "n" && arg[3] === "o" && arg[4] === "-") { - key = arg.slice(5, end >= 0 ? end : undefined) - value = false - } else if (end >= 0) { - key = arg.slice(2, end) - value = - bools[key] !== undefined || - (strings[key] === undefined - ? parseValue(arg.slice(end + 1)) - : arg.slice(end + 1)) - } else { - key = arg.slice(2) - value = - bools[key] !== undefined || - (len === i + 1 || argv[i + 1][0] === "-" - ? strings[key] === undefined - ? true - : "" - : strings[key] === undefined - ? parseValue(argv[++i]) - : argv[++i]) - } - write(out, key, value, aliases, unknown) - } else { - SHORTSPLIT.lastIndex = 2 - match = SHORTSPLIT.exec(arg) - end = match.index - value = match[0] - - for (k = 1; k < end; k++) { - write( - out, - (key = arg[k]), - k + 1 < end - ? strings[key] === undefined || - arg.substring(k + 1, (k = end)) + value - : value === "" - ? len === i + 1 || argv[i + 1][0] === "-" - ? strings[key] === undefined || "" - : bools[key] !== undefined || - (strings[key] === undefined ? parseValue(argv[++i]) : argv[++i]) - : bools[key] !== undefined || - (strings[key] === undefined ? parseValue(value) : value), - aliases, - unknown - ) - } - } - } - - for (key in values) if (out[key] === undefined) out[key] = values[key] - for (key in bools) if (out[key] === undefined) out[key] = false - for (key in strings) if (out[key] === undefined) out[key] = "" - - return out -} - -module.exports = getopts - - -/***/ }), - -/***/ "../../node_modules/git-hooks-list/index.json": -/***/ (function(module) { - -module.exports = JSON.parse("[\"applypatch-msg\",\"pre-applypatch\",\"post-applypatch\",\"pre-commit\",\"pre-merge-commit\",\"prepare-commit-msg\",\"commit-msg\",\"post-commit\",\"pre-rebase\",\"post-checkout\",\"post-merge\",\"pre-push\",\"pre-receive\",\"update\",\"post-receive\",\"post-update\",\"push-to-checkout\",\"pre-auto-gc\",\"post-rewrite\",\"sendemail-validate\",\"fsmonitor-watchman\",\"p4-pre-submit\",\"post-index-change\"]"); - -/***/ }), - -/***/ "../../node_modules/glob-parent/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var isGlob = __webpack_require__("../../node_modules/is-glob/index.js"); -var pathPosixDirname = __webpack_require__("path").posix.dirname; -var isWin32 = __webpack_require__("os").platform() === 'win32'; - -var slash = '/'; -var backslash = /\\/g; -var enclosure = /[\{\[].*[\}\]]$/; -var globby = /(^|[^\\])([\{\[]|\([^\)]+$)/; -var escaped = /\\([\!\*\?\|\[\]\(\)\{\}])/g; - -/** - * @param {string} str - * @param {Object} opts - * @param {boolean} [opts.flipBackslashes=true] - * @returns {string} - */ -module.exports = function globParent(str, opts) { - var options = Object.assign({ flipBackslashes: true }, opts); - - // flip windows path separators - if (options.flipBackslashes && isWin32 && str.indexOf(slash) < 0) { - str = str.replace(backslash, slash); - } - - // special case for strings ending in enclosure containing path separator - if (enclosure.test(str)) { - str += slash; - } - - // preserves full path in case of trailing path separator - str += 'a'; - - // remove path parts that are globby - do { - str = pathPosixDirname(str); - } while (isGlob(str) || globby.test(str)); - - // remove escape chars and return result - return str.replace(escaped, '$1'); -}; - - -/***/ }), - -/***/ "../../node_modules/glob/common.js": -/***/ (function(module, exports, __webpack_require__) { - -exports.setopts = setopts -exports.ownProp = ownProp -exports.makeAbs = makeAbs -exports.finish = finish -exports.mark = mark -exports.isIgnored = isIgnored -exports.childrenIgnored = childrenIgnored - -function ownProp (obj, field) { - return Object.prototype.hasOwnProperty.call(obj, field) -} - -var fs = __webpack_require__("fs") -var path = __webpack_require__("path") -var minimatch = __webpack_require__("../../node_modules/minimatch/minimatch.js") -var isAbsolute = __webpack_require__("../../node_modules/path-is-absolute/index.js") -var Minimatch = minimatch.Minimatch - -function alphasort (a, b) { - return a.localeCompare(b, 'en') -} - -function setupIgnores (self, options) { - self.ignore = options.ignore || [] - - if (!Array.isArray(self.ignore)) - self.ignore = [self.ignore] - - if (self.ignore.length) { - self.ignore = self.ignore.map(ignoreMap) - } -} - -// ignore patterns are always in dot:true mode. -function ignoreMap (pattern) { - var gmatcher = null - if (pattern.slice(-3) === '/**') { - var gpattern = pattern.replace(/(\/\*\*)+$/, '') - gmatcher = new Minimatch(gpattern, { dot: true }) - } - - return { - matcher: new Minimatch(pattern, { dot: true }), - gmatcher: gmatcher - } -} - -function setopts (self, pattern, options) { - if (!options) - options = {} - - // base-matching: just use globstar for that. - if (options.matchBase && -1 === pattern.indexOf("/")) { - if (options.noglobstar) { - throw new Error("base matching requires globstar") - } - pattern = "**/" + pattern - } - - self.silent = !!options.silent - self.pattern = pattern - self.strict = options.strict !== false - self.realpath = !!options.realpath - self.realpathCache = options.realpathCache || Object.create(null) - self.follow = !!options.follow - self.dot = !!options.dot - self.mark = !!options.mark - self.nodir = !!options.nodir - if (self.nodir) - self.mark = true - self.sync = !!options.sync - self.nounique = !!options.nounique - self.nonull = !!options.nonull - self.nosort = !!options.nosort - self.nocase = !!options.nocase - self.stat = !!options.stat - self.noprocess = !!options.noprocess - self.absolute = !!options.absolute - self.fs = options.fs || fs - - self.maxLength = options.maxLength || Infinity - self.cache = options.cache || Object.create(null) - self.statCache = options.statCache || Object.create(null) - self.symlinks = options.symlinks || Object.create(null) - - setupIgnores(self, options) - - self.changedCwd = false - var cwd = process.cwd() - if (!ownProp(options, "cwd")) - self.cwd = cwd - else { - self.cwd = path.resolve(options.cwd) - self.changedCwd = self.cwd !== cwd - } - - self.root = options.root || path.resolve(self.cwd, "/") - self.root = path.resolve(self.root) - if (process.platform === "win32") - self.root = self.root.replace(/\\/g, "/") - - // TODO: is an absolute `cwd` supposed to be resolved against `root`? - // e.g. { cwd: '/test', root: __dirname } === path.join(__dirname, '/test') - self.cwdAbs = isAbsolute(self.cwd) ? self.cwd : makeAbs(self, self.cwd) - if (process.platform === "win32") - self.cwdAbs = self.cwdAbs.replace(/\\/g, "/") - self.nomount = !!options.nomount - - // disable comments and negation in Minimatch. - // Note that they are not supported in Glob itself anyway. - options.nonegate = true - options.nocomment = true - - self.minimatch = new Minimatch(pattern, options) - self.options = self.minimatch.options -} - -function finish (self) { - var nou = self.nounique - var all = nou ? [] : Object.create(null) - - for (var i = 0, l = self.matches.length; i < l; i ++) { - var matches = self.matches[i] - if (!matches || Object.keys(matches).length === 0) { - if (self.nonull) { - // do like the shell, and spit out the literal glob - var literal = self.minimatch.globSet[i] - if (nou) - all.push(literal) - else - all[literal] = true - } - } else { - // had matches - var m = Object.keys(matches) - if (nou) - all.push.apply(all, m) - else - m.forEach(function (m) { - all[m] = true - }) - } - } - - if (!nou) - all = Object.keys(all) - - if (!self.nosort) - all = all.sort(alphasort) - - // at *some* point we statted all of these - if (self.mark) { - for (var i = 0; i < all.length; i++) { - all[i] = self._mark(all[i]) - } - if (self.nodir) { - all = all.filter(function (e) { - var notDir = !(/\/$/.test(e)) - var c = self.cache[e] || self.cache[makeAbs(self, e)] - if (notDir && c) - notDir = c !== 'DIR' && !Array.isArray(c) - return notDir - }) - } - } - - if (self.ignore.length) - all = all.filter(function(m) { - return !isIgnored(self, m) - }) - - self.found = all -} - -function mark (self, p) { - var abs = makeAbs(self, p) - var c = self.cache[abs] - var m = p - if (c) { - var isDir = c === 'DIR' || Array.isArray(c) - var slash = p.slice(-1) === '/' - - if (isDir && !slash) - m += '/' - else if (!isDir && slash) - m = m.slice(0, -1) - - if (m !== p) { - var mabs = makeAbs(self, m) - self.statCache[mabs] = self.statCache[abs] - self.cache[mabs] = self.cache[abs] - } - } - - return m -} - -// lotta situps... -function makeAbs (self, f) { - var abs = f - if (f.charAt(0) === '/') { - abs = path.join(self.root, f) - } else if (isAbsolute(f) || f === '') { - abs = f - } else if (self.changedCwd) { - abs = path.resolve(self.cwd, f) - } else { - abs = path.resolve(f) - } - - if (process.platform === 'win32') - abs = abs.replace(/\\/g, '/') - - return abs -} - - -// Return true, if pattern ends with globstar '**', for the accompanying parent directory. -// Ex:- If node_modules/** is the pattern, add 'node_modules' to ignore list along with it's contents -function isIgnored (self, path) { - if (!self.ignore.length) - return false - - return self.ignore.some(function(item) { - return item.matcher.match(path) || !!(item.gmatcher && item.gmatcher.match(path)) - }) -} - -function childrenIgnored (self, path) { - if (!self.ignore.length) - return false - - return self.ignore.some(function(item) { - return !!(item.gmatcher && item.gmatcher.match(path)) - }) -} - - -/***/ }), - -/***/ "../../node_modules/glob/glob.js": -/***/ (function(module, exports, __webpack_require__) { - -// Approach: -// -// 1. Get the minimatch set -// 2. For each pattern in the set, PROCESS(pattern, false) -// 3. Store matches per-set, then uniq them -// -// PROCESS(pattern, inGlobStar) -// Get the first [n] items from pattern that are all strings -// Join these together. This is PREFIX. -// If there is no more remaining, then stat(PREFIX) and -// add to matches if it succeeds. END. -// -// If inGlobStar and PREFIX is symlink and points to dir -// set ENTRIES = [] -// else readdir(PREFIX) as ENTRIES -// If fail, END -// -// with ENTRIES -// If pattern[n] is GLOBSTAR -// // handle the case where the globstar match is empty -// // by pruning it out, and testing the resulting pattern -// PROCESS(pattern[0..n] + pattern[n+1 .. $], false) -// // handle other cases. -// for ENTRY in ENTRIES (not dotfiles) -// // attach globstar + tail onto the entry -// // Mark that this entry is a globstar match -// PROCESS(pattern[0..n] + ENTRY + pattern[n .. $], true) -// -// else // not globstar -// for ENTRY in ENTRIES (not dotfiles, unless pattern[n] is dot) -// Test ENTRY against pattern[n] -// If fails, continue -// If passes, PROCESS(pattern[0..n] + item + pattern[n+1 .. $]) -// -// Caveat: -// Cache all stats and readdirs results to minimize syscall. Since all -// we ever care about is existence and directory-ness, we can just keep -// `true` for files, and [children,...] for directories, or `false` for -// things that don't exist. - -module.exports = glob - -var rp = __webpack_require__("../../node_modules/fs.realpath/index.js") -var minimatch = __webpack_require__("../../node_modules/minimatch/minimatch.js") -var Minimatch = minimatch.Minimatch -var inherits = __webpack_require__("../../node_modules/inherits/inherits.js") -var EE = __webpack_require__("events").EventEmitter -var path = __webpack_require__("path") -var assert = __webpack_require__("assert") -var isAbsolute = __webpack_require__("../../node_modules/path-is-absolute/index.js") -var globSync = __webpack_require__("../../node_modules/glob/sync.js") -var common = __webpack_require__("../../node_modules/glob/common.js") -var setopts = common.setopts -var ownProp = common.ownProp -var inflight = __webpack_require__("../../node_modules/inflight/inflight.js") -var util = __webpack_require__("util") -var childrenIgnored = common.childrenIgnored -var isIgnored = common.isIgnored - -var once = __webpack_require__("../../node_modules/once/once.js") - -function glob (pattern, options, cb) { - if (typeof options === 'function') cb = options, options = {} - if (!options) options = {} - - if (options.sync) { - if (cb) - throw new TypeError('callback provided to sync glob') - return globSync(pattern, options) - } - - return new Glob(pattern, options, cb) -} - -glob.sync = globSync -var GlobSync = glob.GlobSync = globSync.GlobSync - -// old api surface -glob.glob = glob - -function extend (origin, add) { - if (add === null || typeof add !== 'object') { - return origin - } - - var keys = Object.keys(add) - var i = keys.length - while (i--) { - origin[keys[i]] = add[keys[i]] - } - return origin -} - -glob.hasMagic = function (pattern, options_) { - var options = extend({}, options_) - options.noprocess = true - - var g = new Glob(pattern, options) - var set = g.minimatch.set - - if (!pattern) - return false - - if (set.length > 1) - return true - - for (var j = 0; j < set[0].length; j++) { - if (typeof set[0][j] !== 'string') - return true - } - - return false -} - -glob.Glob = Glob -inherits(Glob, EE) -function Glob (pattern, options, cb) { - if (typeof options === 'function') { - cb = options - options = null - } - - if (options && options.sync) { - if (cb) - throw new TypeError('callback provided to sync glob') - return new GlobSync(pattern, options) - } - - if (!(this instanceof Glob)) - return new Glob(pattern, options, cb) - - setopts(this, pattern, options) - this._didRealPath = false - - // process each pattern in the minimatch set - var n = this.minimatch.set.length - - // The matches are stored as {: true,...} so that - // duplicates are automagically pruned. - // Later, we do an Object.keys() on these. - // Keep them as a list so we can fill in when nonull is set. - this.matches = new Array(n) - - if (typeof cb === 'function') { - cb = once(cb) - this.on('error', cb) - this.on('end', function (matches) { - cb(null, matches) - }) - } - - var self = this - this._processing = 0 - - this._emitQueue = [] - this._processQueue = [] - this.paused = false - - if (this.noprocess) - return this - - if (n === 0) - return done() - - var sync = true - for (var i = 0; i < n; i ++) { - this._process(this.minimatch.set[i], i, false, done) - } - sync = false - - function done () { - --self._processing - if (self._processing <= 0) { - if (sync) { - process.nextTick(function () { - self._finish() - }) - } else { - self._finish() - } - } - } -} - -Glob.prototype._finish = function () { - assert(this instanceof Glob) - if (this.aborted) - return - - if (this.realpath && !this._didRealpath) - return this._realpath() - - common.finish(this) - this.emit('end', this.found) -} - -Glob.prototype._realpath = function () { - if (this._didRealpath) - return - - this._didRealpath = true - - var n = this.matches.length - if (n === 0) - return this._finish() - - var self = this - for (var i = 0; i < this.matches.length; i++) - this._realpathSet(i, next) - - function next () { - if (--n === 0) - self._finish() - } -} - -Glob.prototype._realpathSet = function (index, cb) { - var matchset = this.matches[index] - if (!matchset) - return cb() - - var found = Object.keys(matchset) - var self = this - var n = found.length - - if (n === 0) - return cb() - - var set = this.matches[index] = Object.create(null) - found.forEach(function (p, i) { - // If there's a problem with the stat, then it means that - // one or more of the links in the realpath couldn't be - // resolved. just return the abs value in that case. - p = self._makeAbs(p) - rp.realpath(p, self.realpathCache, function (er, real) { - if (!er) - set[real] = true - else if (er.syscall === 'stat') - set[p] = true - else - self.emit('error', er) // srsly wtf right here - - if (--n === 0) { - self.matches[index] = set - cb() - } - }) - }) -} - -Glob.prototype._mark = function (p) { - return common.mark(this, p) -} - -Glob.prototype._makeAbs = function (f) { - return common.makeAbs(this, f) -} - -Glob.prototype.abort = function () { - this.aborted = true - this.emit('abort') -} - -Glob.prototype.pause = function () { - if (!this.paused) { - this.paused = true - this.emit('pause') - } -} - -Glob.prototype.resume = function () { - if (this.paused) { - this.emit('resume') - this.paused = false - if (this._emitQueue.length) { - var eq = this._emitQueue.slice(0) - this._emitQueue.length = 0 - for (var i = 0; i < eq.length; i ++) { - var e = eq[i] - this._emitMatch(e[0], e[1]) - } - } - if (this._processQueue.length) { - var pq = this._processQueue.slice(0) - this._processQueue.length = 0 - for (var i = 0; i < pq.length; i ++) { - var p = pq[i] - this._processing-- - this._process(p[0], p[1], p[2], p[3]) - } - } - } -} - -Glob.prototype._process = function (pattern, index, inGlobStar, cb) { - assert(this instanceof Glob) - assert(typeof cb === 'function') - - if (this.aborted) - return - - this._processing++ - if (this.paused) { - this._processQueue.push([pattern, index, inGlobStar, cb]) - return - } - - //console.error('PROCESS %d', this._processing, pattern) - - // Get the first [n] parts of pattern that are all strings. - var n = 0 - while (typeof pattern[n] === 'string') { - n ++ - } - // now n is the index of the first one that is *not* a string. - - // see if there's anything else - var prefix - switch (n) { - // if not, then this is rather simple - case pattern.length: - this._processSimple(pattern.join('/'), index, cb) - return - - case 0: - // pattern *starts* with some non-trivial item. - // going to readdir(cwd), but not include the prefix in matches. - prefix = null - break - - default: - // pattern has some string bits in the front. - // whatever it starts with, whether that's 'absolute' like /foo/bar, - // or 'relative' like '../baz' - prefix = pattern.slice(0, n).join('/') - break - } - - var remain = pattern.slice(n) - - // get the list of entries. - var read - if (prefix === null) - read = '.' - else if (isAbsolute(prefix) || isAbsolute(pattern.join('/'))) { - if (!prefix || !isAbsolute(prefix)) - prefix = '/' + prefix - read = prefix - } else - read = prefix - - var abs = this._makeAbs(read) - - //if ignored, skip _processing - if (childrenIgnored(this, read)) - return cb() - - var isGlobStar = remain[0] === minimatch.GLOBSTAR - if (isGlobStar) - this._processGlobStar(prefix, read, abs, remain, index, inGlobStar, cb) - else - this._processReaddir(prefix, read, abs, remain, index, inGlobStar, cb) -} - -Glob.prototype._processReaddir = function (prefix, read, abs, remain, index, inGlobStar, cb) { - var self = this - this._readdir(abs, inGlobStar, function (er, entries) { - return self._processReaddir2(prefix, read, abs, remain, index, inGlobStar, entries, cb) - }) -} - -Glob.prototype._processReaddir2 = function (prefix, read, abs, remain, index, inGlobStar, entries, cb) { - - // if the abs isn't a dir, then nothing can match! - if (!entries) - return cb() - - // It will only match dot entries if it starts with a dot, or if - // dot is set. Stuff like @(.foo|.bar) isn't allowed. - var pn = remain[0] - var negate = !!this.minimatch.negate - var rawGlob = pn._glob - var dotOk = this.dot || rawGlob.charAt(0) === '.' - - var matchedEntries = [] - for (var i = 0; i < entries.length; i++) { - var e = entries[i] - if (e.charAt(0) !== '.' || dotOk) { - var m - if (negate && !prefix) { - m = !e.match(pn) - } else { - m = e.match(pn) - } - if (m) - matchedEntries.push(e) - } - } - - //console.error('prd2', prefix, entries, remain[0]._glob, matchedEntries) - - var len = matchedEntries.length - // If there are no matched entries, then nothing matches. - if (len === 0) - return cb() - - // if this is the last remaining pattern bit, then no need for - // an additional stat *unless* the user has specified mark or - // stat explicitly. We know they exist, since readdir returned - // them. - - if (remain.length === 1 && !this.mark && !this.stat) { - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - if (prefix) { - if (prefix !== '/') - e = prefix + '/' + e - else - e = prefix + e - } - - if (e.charAt(0) === '/' && !this.nomount) { - e = path.join(this.root, e) - } - this._emitMatch(index, e) - } - // This was the last one, and no stats were needed - return cb() - } - - // now test all matched entries as stand-ins for that part - // of the pattern. - remain.shift() - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - var newPattern - if (prefix) { - if (prefix !== '/') - e = prefix + '/' + e - else - e = prefix + e - } - this._process([e].concat(remain), index, inGlobStar, cb) - } - cb() -} - -Glob.prototype._emitMatch = function (index, e) { - if (this.aborted) - return - - if (isIgnored(this, e)) - return - - if (this.paused) { - this._emitQueue.push([index, e]) - return - } - - var abs = isAbsolute(e) ? e : this._makeAbs(e) - - if (this.mark) - e = this._mark(e) - - if (this.absolute) - e = abs - - if (this.matches[index][e]) - return - - if (this.nodir) { - var c = this.cache[abs] - if (c === 'DIR' || Array.isArray(c)) - return - } - - this.matches[index][e] = true - - var st = this.statCache[abs] - if (st) - this.emit('stat', e, st) - - this.emit('match', e) -} - -Glob.prototype._readdirInGlobStar = function (abs, cb) { - if (this.aborted) - return - - // follow all symlinked directories forever - // just proceed as if this is a non-globstar situation - if (this.follow) - return this._readdir(abs, false, cb) - - var lstatkey = 'lstat\0' + abs - var self = this - var lstatcb = inflight(lstatkey, lstatcb_) - - if (lstatcb) - self.fs.lstat(abs, lstatcb) - - function lstatcb_ (er, lstat) { - if (er && er.code === 'ENOENT') - return cb() - - var isSym = lstat && lstat.isSymbolicLink() - self.symlinks[abs] = isSym - - // If it's not a symlink or a dir, then it's definitely a regular file. - // don't bother doing a readdir in that case. - if (!isSym && lstat && !lstat.isDirectory()) { - self.cache[abs] = 'FILE' - cb() - } else - self._readdir(abs, false, cb) - } -} - -Glob.prototype._readdir = function (abs, inGlobStar, cb) { - if (this.aborted) - return - - cb = inflight('readdir\0'+abs+'\0'+inGlobStar, cb) - if (!cb) - return - - //console.error('RD %j %j', +inGlobStar, abs) - if (inGlobStar && !ownProp(this.symlinks, abs)) - return this._readdirInGlobStar(abs, cb) - - if (ownProp(this.cache, abs)) { - var c = this.cache[abs] - if (!c || c === 'FILE') - return cb() - - if (Array.isArray(c)) - return cb(null, c) - } - - var self = this - self.fs.readdir(abs, readdirCb(this, abs, cb)) -} - -function readdirCb (self, abs, cb) { - return function (er, entries) { - if (er) - self._readdirError(abs, er, cb) - else - self._readdirEntries(abs, entries, cb) - } -} - -Glob.prototype._readdirEntries = function (abs, entries, cb) { - if (this.aborted) - return - - // if we haven't asked to stat everything, then just - // assume that everything in there exists, so we can avoid - // having to stat it a second time. - if (!this.mark && !this.stat) { - for (var i = 0; i < entries.length; i ++) { - var e = entries[i] - if (abs === '/') - e = abs + e - else - e = abs + '/' + e - this.cache[e] = true - } - } - - this.cache[abs] = entries - return cb(null, entries) -} - -Glob.prototype._readdirError = function (f, er, cb) { - if (this.aborted) - return - - // handle errors, and cache the information - switch (er.code) { - case 'ENOTSUP': // https://github.com/isaacs/node-glob/issues/205 - case 'ENOTDIR': // totally normal. means it *does* exist. - var abs = this._makeAbs(f) - this.cache[abs] = 'FILE' - if (abs === this.cwdAbs) { - var error = new Error(er.code + ' invalid cwd ' + this.cwd) - error.path = this.cwd - error.code = er.code - this.emit('error', error) - this.abort() - } - break - - case 'ENOENT': // not terribly unusual - case 'ELOOP': - case 'ENAMETOOLONG': - case 'UNKNOWN': - this.cache[this._makeAbs(f)] = false - break - - default: // some unusual error. Treat as failure. - this.cache[this._makeAbs(f)] = false - if (this.strict) { - this.emit('error', er) - // If the error is handled, then we abort - // if not, we threw out of here - this.abort() - } - if (!this.silent) - console.error('glob error', er) - break - } - - return cb() -} - -Glob.prototype._processGlobStar = function (prefix, read, abs, remain, index, inGlobStar, cb) { - var self = this - this._readdir(abs, inGlobStar, function (er, entries) { - self._processGlobStar2(prefix, read, abs, remain, index, inGlobStar, entries, cb) - }) -} - - -Glob.prototype._processGlobStar2 = function (prefix, read, abs, remain, index, inGlobStar, entries, cb) { - //console.error('pgs2', prefix, remain[0], entries) - - // no entries means not a dir, so it can never have matches - // foo.txt/** doesn't match foo.txt - if (!entries) - return cb() - - // test without the globstar, and with every child both below - // and replacing the globstar. - var remainWithoutGlobStar = remain.slice(1) - var gspref = prefix ? [ prefix ] : [] - var noGlobStar = gspref.concat(remainWithoutGlobStar) - - // the noGlobStar pattern exits the inGlobStar state - this._process(noGlobStar, index, false, cb) - - var isSym = this.symlinks[abs] - var len = entries.length - - // If it's a symlink, and we're in a globstar, then stop - if (isSym && inGlobStar) - return cb() - - for (var i = 0; i < len; i++) { - var e = entries[i] - if (e.charAt(0) === '.' && !this.dot) - continue - - // these two cases enter the inGlobStar state - var instead = gspref.concat(entries[i], remainWithoutGlobStar) - this._process(instead, index, true, cb) - - var below = gspref.concat(entries[i], remain) - this._process(below, index, true, cb) - } - - cb() -} - -Glob.prototype._processSimple = function (prefix, index, cb) { - // XXX review this. Shouldn't it be doing the mounting etc - // before doing stat? kinda weird? - var self = this - this._stat(prefix, function (er, exists) { - self._processSimple2(prefix, index, er, exists, cb) - }) -} -Glob.prototype._processSimple2 = function (prefix, index, er, exists, cb) { - - //console.error('ps2', prefix, exists) - - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - // If it doesn't exist, then just mark the lack of results - if (!exists) - return cb() - - if (prefix && isAbsolute(prefix) && !this.nomount) { - var trail = /[\/\\]$/.test(prefix) - if (prefix.charAt(0) === '/') { - prefix = path.join(this.root, prefix) - } else { - prefix = path.resolve(this.root, prefix) - if (trail) - prefix += '/' - } - } - - if (process.platform === 'win32') - prefix = prefix.replace(/\\/g, '/') - - // Mark this as a match - this._emitMatch(index, prefix) - cb() -} - -// Returns either 'DIR', 'FILE', or false -Glob.prototype._stat = function (f, cb) { - var abs = this._makeAbs(f) - var needDir = f.slice(-1) === '/' - - if (f.length > this.maxLength) - return cb() - - if (!this.stat && ownProp(this.cache, abs)) { - var c = this.cache[abs] - - if (Array.isArray(c)) - c = 'DIR' - - // It exists, but maybe not how we need it - if (!needDir || c === 'DIR') - return cb(null, c) - - if (needDir && c === 'FILE') - return cb() - - // otherwise we have to stat, because maybe c=true - // if we know it exists, but not what it is. - } - - var exists - var stat = this.statCache[abs] - if (stat !== undefined) { - if (stat === false) - return cb(null, stat) - else { - var type = stat.isDirectory() ? 'DIR' : 'FILE' - if (needDir && type === 'FILE') - return cb() - else - return cb(null, type, stat) - } - } - - var self = this - var statcb = inflight('stat\0' + abs, lstatcb_) - if (statcb) - self.fs.lstat(abs, statcb) - - function lstatcb_ (er, lstat) { - if (lstat && lstat.isSymbolicLink()) { - // If it's a symlink, then treat it as the target, unless - // the target does not exist, then treat it as a file. - return self.fs.stat(abs, function (er, stat) { - if (er) - self._stat2(f, abs, null, lstat, cb) - else - self._stat2(f, abs, er, stat, cb) - }) - } else { - self._stat2(f, abs, er, lstat, cb) - } - } -} - -Glob.prototype._stat2 = function (f, abs, er, stat, cb) { - if (er && (er.code === 'ENOENT' || er.code === 'ENOTDIR')) { - this.statCache[abs] = false - return cb() - } - - var needDir = f.slice(-1) === '/' - this.statCache[abs] = stat - - if (abs.slice(-1) === '/' && stat && !stat.isDirectory()) - return cb(null, false, stat) - - var c = true - if (stat) - c = stat.isDirectory() ? 'DIR' : 'FILE' - this.cache[abs] = this.cache[abs] || c - - if (needDir && c === 'FILE') - return cb() - - return cb(null, c, stat) -} - - -/***/ }), - -/***/ "../../node_modules/glob/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = globSync -globSync.GlobSync = GlobSync - -var rp = __webpack_require__("../../node_modules/fs.realpath/index.js") -var minimatch = __webpack_require__("../../node_modules/minimatch/minimatch.js") -var Minimatch = minimatch.Minimatch -var Glob = __webpack_require__("../../node_modules/glob/glob.js").Glob -var util = __webpack_require__("util") -var path = __webpack_require__("path") -var assert = __webpack_require__("assert") -var isAbsolute = __webpack_require__("../../node_modules/path-is-absolute/index.js") -var common = __webpack_require__("../../node_modules/glob/common.js") -var setopts = common.setopts -var ownProp = common.ownProp -var childrenIgnored = common.childrenIgnored -var isIgnored = common.isIgnored - -function globSync (pattern, options) { - if (typeof options === 'function' || arguments.length === 3) - throw new TypeError('callback provided to sync glob\n'+ - 'See: https://github.com/isaacs/node-glob/issues/167') - - return new GlobSync(pattern, options).found -} - -function GlobSync (pattern, options) { - if (!pattern) - throw new Error('must provide pattern') - - if (typeof options === 'function' || arguments.length === 3) - throw new TypeError('callback provided to sync glob\n'+ - 'See: https://github.com/isaacs/node-glob/issues/167') - - if (!(this instanceof GlobSync)) - return new GlobSync(pattern, options) - - setopts(this, pattern, options) - - if (this.noprocess) - return this - - var n = this.minimatch.set.length - this.matches = new Array(n) - for (var i = 0; i < n; i ++) { - this._process(this.minimatch.set[i], i, false) - } - this._finish() -} - -GlobSync.prototype._finish = function () { - assert(this instanceof GlobSync) - if (this.realpath) { - var self = this - this.matches.forEach(function (matchset, index) { - var set = self.matches[index] = Object.create(null) - for (var p in matchset) { - try { - p = self._makeAbs(p) - var real = rp.realpathSync(p, self.realpathCache) - set[real] = true - } catch (er) { - if (er.syscall === 'stat') - set[self._makeAbs(p)] = true - else - throw er - } - } - }) - } - common.finish(this) -} - - -GlobSync.prototype._process = function (pattern, index, inGlobStar) { - assert(this instanceof GlobSync) - - // Get the first [n] parts of pattern that are all strings. - var n = 0 - while (typeof pattern[n] === 'string') { - n ++ - } - // now n is the index of the first one that is *not* a string. - - // See if there's anything else - var prefix - switch (n) { - // if not, then this is rather simple - case pattern.length: - this._processSimple(pattern.join('/'), index) - return - - case 0: - // pattern *starts* with some non-trivial item. - // going to readdir(cwd), but not include the prefix in matches. - prefix = null - break - - default: - // pattern has some string bits in the front. - // whatever it starts with, whether that's 'absolute' like /foo/bar, - // or 'relative' like '../baz' - prefix = pattern.slice(0, n).join('/') - break - } - - var remain = pattern.slice(n) - - // get the list of entries. - var read - if (prefix === null) - read = '.' - else if (isAbsolute(prefix) || isAbsolute(pattern.join('/'))) { - if (!prefix || !isAbsolute(prefix)) - prefix = '/' + prefix - read = prefix - } else - read = prefix - - var abs = this._makeAbs(read) - - //if ignored, skip processing - if (childrenIgnored(this, read)) - return - - var isGlobStar = remain[0] === minimatch.GLOBSTAR - if (isGlobStar) - this._processGlobStar(prefix, read, abs, remain, index, inGlobStar) - else - this._processReaddir(prefix, read, abs, remain, index, inGlobStar) -} - - -GlobSync.prototype._processReaddir = function (prefix, read, abs, remain, index, inGlobStar) { - var entries = this._readdir(abs, inGlobStar) - - // if the abs isn't a dir, then nothing can match! - if (!entries) - return - - // It will only match dot entries if it starts with a dot, or if - // dot is set. Stuff like @(.foo|.bar) isn't allowed. - var pn = remain[0] - var negate = !!this.minimatch.negate - var rawGlob = pn._glob - var dotOk = this.dot || rawGlob.charAt(0) === '.' - - var matchedEntries = [] - for (var i = 0; i < entries.length; i++) { - var e = entries[i] - if (e.charAt(0) !== '.' || dotOk) { - var m - if (negate && !prefix) { - m = !e.match(pn) - } else { - m = e.match(pn) - } - if (m) - matchedEntries.push(e) - } - } - - var len = matchedEntries.length - // If there are no matched entries, then nothing matches. - if (len === 0) - return - - // if this is the last remaining pattern bit, then no need for - // an additional stat *unless* the user has specified mark or - // stat explicitly. We know they exist, since readdir returned - // them. - - if (remain.length === 1 && !this.mark && !this.stat) { - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - if (prefix) { - if (prefix.slice(-1) !== '/') - e = prefix + '/' + e - else - e = prefix + e - } - - if (e.charAt(0) === '/' && !this.nomount) { - e = path.join(this.root, e) - } - this._emitMatch(index, e) - } - // This was the last one, and no stats were needed - return - } - - // now test all matched entries as stand-ins for that part - // of the pattern. - remain.shift() - for (var i = 0; i < len; i ++) { - var e = matchedEntries[i] - var newPattern - if (prefix) - newPattern = [prefix, e] - else - newPattern = [e] - this._process(newPattern.concat(remain), index, inGlobStar) - } -} - - -GlobSync.prototype._emitMatch = function (index, e) { - if (isIgnored(this, e)) - return - - var abs = this._makeAbs(e) - - if (this.mark) - e = this._mark(e) - - if (this.absolute) { - e = abs - } - - if (this.matches[index][e]) - return - - if (this.nodir) { - var c = this.cache[abs] - if (c === 'DIR' || Array.isArray(c)) - return - } - - this.matches[index][e] = true - - if (this.stat) - this._stat(e) -} - - -GlobSync.prototype._readdirInGlobStar = function (abs) { - // follow all symlinked directories forever - // just proceed as if this is a non-globstar situation - if (this.follow) - return this._readdir(abs, false) - - var entries - var lstat - var stat - try { - lstat = this.fs.lstatSync(abs) - } catch (er) { - if (er.code === 'ENOENT') { - // lstat failed, doesn't exist - return null - } - } - - var isSym = lstat && lstat.isSymbolicLink() - this.symlinks[abs] = isSym - - // If it's not a symlink or a dir, then it's definitely a regular file. - // don't bother doing a readdir in that case. - if (!isSym && lstat && !lstat.isDirectory()) - this.cache[abs] = 'FILE' - else - entries = this._readdir(abs, false) - - return entries -} - -GlobSync.prototype._readdir = function (abs, inGlobStar) { - var entries - - if (inGlobStar && !ownProp(this.symlinks, abs)) - return this._readdirInGlobStar(abs) - - if (ownProp(this.cache, abs)) { - var c = this.cache[abs] - if (!c || c === 'FILE') - return null - - if (Array.isArray(c)) - return c - } - - try { - return this._readdirEntries(abs, this.fs.readdirSync(abs)) - } catch (er) { - this._readdirError(abs, er) - return null - } -} - -GlobSync.prototype._readdirEntries = function (abs, entries) { - // if we haven't asked to stat everything, then just - // assume that everything in there exists, so we can avoid - // having to stat it a second time. - if (!this.mark && !this.stat) { - for (var i = 0; i < entries.length; i ++) { - var e = entries[i] - if (abs === '/') - e = abs + e - else - e = abs + '/' + e - this.cache[e] = true - } - } - - this.cache[abs] = entries - - // mark and cache dir-ness - return entries -} - -GlobSync.prototype._readdirError = function (f, er) { - // handle errors, and cache the information - switch (er.code) { - case 'ENOTSUP': // https://github.com/isaacs/node-glob/issues/205 - case 'ENOTDIR': // totally normal. means it *does* exist. - var abs = this._makeAbs(f) - this.cache[abs] = 'FILE' - if (abs === this.cwdAbs) { - var error = new Error(er.code + ' invalid cwd ' + this.cwd) - error.path = this.cwd - error.code = er.code - throw error - } - break - - case 'ENOENT': // not terribly unusual - case 'ELOOP': - case 'ENAMETOOLONG': - case 'UNKNOWN': - this.cache[this._makeAbs(f)] = false - break - - default: // some unusual error. Treat as failure. - this.cache[this._makeAbs(f)] = false - if (this.strict) - throw er - if (!this.silent) - console.error('glob error', er) - break - } -} - -GlobSync.prototype._processGlobStar = function (prefix, read, abs, remain, index, inGlobStar) { - - var entries = this._readdir(abs, inGlobStar) - - // no entries means not a dir, so it can never have matches - // foo.txt/** doesn't match foo.txt - if (!entries) - return - - // test without the globstar, and with every child both below - // and replacing the globstar. - var remainWithoutGlobStar = remain.slice(1) - var gspref = prefix ? [ prefix ] : [] - var noGlobStar = gspref.concat(remainWithoutGlobStar) - - // the noGlobStar pattern exits the inGlobStar state - this._process(noGlobStar, index, false) - - var len = entries.length - var isSym = this.symlinks[abs] - - // If it's a symlink, and we're in a globstar, then stop - if (isSym && inGlobStar) - return - - for (var i = 0; i < len; i++) { - var e = entries[i] - if (e.charAt(0) === '.' && !this.dot) - continue - - // these two cases enter the inGlobStar state - var instead = gspref.concat(entries[i], remainWithoutGlobStar) - this._process(instead, index, true) - - var below = gspref.concat(entries[i], remain) - this._process(below, index, true) - } -} - -GlobSync.prototype._processSimple = function (prefix, index) { - // XXX review this. Shouldn't it be doing the mounting etc - // before doing stat? kinda weird? - var exists = this._stat(prefix) - - if (!this.matches[index]) - this.matches[index] = Object.create(null) - - // If it doesn't exist, then just mark the lack of results - if (!exists) - return - - if (prefix && isAbsolute(prefix) && !this.nomount) { - var trail = /[\/\\]$/.test(prefix) - if (prefix.charAt(0) === '/') { - prefix = path.join(this.root, prefix) - } else { - prefix = path.resolve(this.root, prefix) - if (trail) - prefix += '/' - } - } - - if (process.platform === 'win32') - prefix = prefix.replace(/\\/g, '/') - - // Mark this as a match - this._emitMatch(index, prefix) -} - -// Returns either 'DIR', 'FILE', or false -GlobSync.prototype._stat = function (f) { - var abs = this._makeAbs(f) - var needDir = f.slice(-1) === '/' - - if (f.length > this.maxLength) - return false - - if (!this.stat && ownProp(this.cache, abs)) { - var c = this.cache[abs] - - if (Array.isArray(c)) - c = 'DIR' - - // It exists, but maybe not how we need it - if (!needDir || c === 'DIR') - return c - - if (needDir && c === 'FILE') - return false - - // otherwise we have to stat, because maybe c=true - // if we know it exists, but not what it is. - } - - var exists - var stat = this.statCache[abs] - if (!stat) { - var lstat - try { - lstat = this.fs.lstatSync(abs) - } catch (er) { - if (er && (er.code === 'ENOENT' || er.code === 'ENOTDIR')) { - this.statCache[abs] = false - return false - } - } - - if (lstat && lstat.isSymbolicLink()) { - try { - stat = this.fs.statSync(abs) - } catch (er) { - stat = lstat - } - } else { - stat = lstat - } - } - - this.statCache[abs] = stat - - var c = true - if (stat) - c = stat.isDirectory() ? 'DIR' : 'FILE' - - this.cache[abs] = this.cache[abs] || c - - if (needDir && c === 'FILE') - return false - - return c -} - -GlobSync.prototype._mark = function (p) { - return common.mark(this, p) -} - -GlobSync.prototype._makeAbs = function (f) { - return common.makeAbs(this, f) -} - - -/***/ }), - -/***/ "../../node_modules/globby/gitignore.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {promisify} = __webpack_require__("util"); -const fs = __webpack_require__("fs"); -const path = __webpack_require__("path"); -const fastGlob = __webpack_require__("../../node_modules/fast-glob/out/index.js"); -const gitIgnore = __webpack_require__("../../node_modules/ignore/index.js"); -const slash = __webpack_require__("../../node_modules/slash/index.js"); - -const DEFAULT_IGNORE = [ - '**/node_modules/**', - '**/flow-typed/**', - '**/coverage/**', - '**/.git' -]; - -const readFileP = promisify(fs.readFile); - -const mapGitIgnorePatternTo = base => ignore => { - if (ignore.startsWith('!')) { - return '!' + path.posix.join(base, ignore.slice(1)); - } - - return path.posix.join(base, ignore); -}; - -const parseGitIgnore = (content, options) => { - const base = slash(path.relative(options.cwd, path.dirname(options.fileName))); - - return content - .split(/\r?\n/) - .filter(Boolean) - .filter(line => !line.startsWith('#')) - .map(mapGitIgnorePatternTo(base)); -}; - -const reduceIgnore = files => { - const ignores = gitIgnore(); - for (const file of files) { - ignores.add(parseGitIgnore(file.content, { - cwd: file.cwd, - fileName: file.filePath - })); - } - - return ignores; -}; - -const ensureAbsolutePathForCwd = (cwd, p) => { - cwd = slash(cwd); - if (path.isAbsolute(p)) { - if (slash(p).startsWith(cwd)) { - return p; - } - - throw new Error(`Path ${p} is not in cwd ${cwd}`); - } - - return path.join(cwd, p); -}; - -const getIsIgnoredPredecate = (ignores, cwd) => { - return p => ignores.ignores(slash(path.relative(cwd, ensureAbsolutePathForCwd(cwd, p.path || p)))); -}; - -const getFile = async (file, cwd) => { - const filePath = path.join(cwd, file); - const content = await readFileP(filePath, 'utf8'); - - return { - cwd, - filePath, - content - }; -}; - -const getFileSync = (file, cwd) => { - const filePath = path.join(cwd, file); - const content = fs.readFileSync(filePath, 'utf8'); - - return { - cwd, - filePath, - content - }; -}; - -const normalizeOptions = ({ - ignore = [], - cwd = slash(process.cwd()) -} = {}) => { - return {ignore, cwd}; -}; - -module.exports = async options => { - options = normalizeOptions(options); - - const paths = await fastGlob('**/.gitignore', { - ignore: DEFAULT_IGNORE.concat(options.ignore), - cwd: options.cwd - }); - - const files = await Promise.all(paths.map(file => getFile(file, options.cwd))); - const ignores = reduceIgnore(files); - - return getIsIgnoredPredecate(ignores, options.cwd); -}; - -module.exports.sync = options => { - options = normalizeOptions(options); - - const paths = fastGlob.sync('**/.gitignore', { - ignore: DEFAULT_IGNORE.concat(options.ignore), - cwd: options.cwd - }); - - const files = paths.map(file => getFileSync(file, options.cwd)); - const ignores = reduceIgnore(files); - - return getIsIgnoredPredecate(ignores, options.cwd); -}; - - -/***/ }), - -/***/ "../../node_modules/globby/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const fs = __webpack_require__("fs"); -const arrayUnion = __webpack_require__("../../node_modules/array-union/index.js"); -const merge2 = __webpack_require__("../../node_modules/merge2/index.js"); -const fastGlob = __webpack_require__("../../node_modules/fast-glob/out/index.js"); -const dirGlob = __webpack_require__("../../node_modules/dir-glob/index.js"); -const gitignore = __webpack_require__("../../node_modules/globby/gitignore.js"); -const {FilterStream, UniqueStream} = __webpack_require__("../../node_modules/globby/stream-utils.js"); - -const DEFAULT_FILTER = () => false; - -const isNegative = pattern => pattern[0] === '!'; - -const assertPatternsInput = patterns => { - if (!patterns.every(pattern => typeof pattern === 'string')) { - throw new TypeError('Patterns must be a string or an array of strings'); - } -}; - -const checkCwdOption = (options = {}) => { - if (!options.cwd) { - return; - } - - let stat; - try { - stat = fs.statSync(options.cwd); - } catch { - return; - } - - if (!stat.isDirectory()) { - throw new Error('The `cwd` option must be a path to a directory'); - } -}; - -const getPathString = p => p.stats instanceof fs.Stats ? p.path : p; - -const generateGlobTasks = (patterns, taskOptions) => { - patterns = arrayUnion([].concat(patterns)); - assertPatternsInput(patterns); - checkCwdOption(taskOptions); - - const globTasks = []; - - taskOptions = { - ignore: [], - expandDirectories: true, - ...taskOptions - }; - - for (const [index, pattern] of patterns.entries()) { - if (isNegative(pattern)) { - continue; - } - - const ignore = patterns - .slice(index) - .filter(pattern => isNegative(pattern)) - .map(pattern => pattern.slice(1)); - - const options = { - ...taskOptions, - ignore: taskOptions.ignore.concat(ignore) - }; - - globTasks.push({pattern, options}); - } - - return globTasks; -}; - -const globDirs = (task, fn) => { - let options = {}; - if (task.options.cwd) { - options.cwd = task.options.cwd; - } - - if (Array.isArray(task.options.expandDirectories)) { - options = { - ...options, - files: task.options.expandDirectories - }; - } else if (typeof task.options.expandDirectories === 'object') { - options = { - ...options, - ...task.options.expandDirectories - }; - } - - return fn(task.pattern, options); -}; - -const getPattern = (task, fn) => task.options.expandDirectories ? globDirs(task, fn) : [task.pattern]; - -const getFilterSync = options => { - return options && options.gitignore ? - gitignore.sync({cwd: options.cwd, ignore: options.ignore}) : - DEFAULT_FILTER; -}; - -const globToTask = task => glob => { - const {options} = task; - if (options.ignore && Array.isArray(options.ignore) && options.expandDirectories) { - options.ignore = dirGlob.sync(options.ignore); - } - - return { - pattern: glob, - options - }; -}; - -module.exports = async (patterns, options) => { - const globTasks = generateGlobTasks(patterns, options); - - const getFilter = async () => { - return options && options.gitignore ? - gitignore({cwd: options.cwd, ignore: options.ignore}) : - DEFAULT_FILTER; - }; - - const getTasks = async () => { - const tasks = await Promise.all(globTasks.map(async task => { - const globs = await getPattern(task, dirGlob); - return Promise.all(globs.map(globToTask(task))); - })); - - return arrayUnion(...tasks); - }; - - const [filter, tasks] = await Promise.all([getFilter(), getTasks()]); - const paths = await Promise.all(tasks.map(task => fastGlob(task.pattern, task.options))); - - return arrayUnion(...paths).filter(path_ => !filter(getPathString(path_))); -}; - -module.exports.sync = (patterns, options) => { - const globTasks = generateGlobTasks(patterns, options); - - const tasks = []; - for (const task of globTasks) { - const newTask = getPattern(task, dirGlob.sync).map(globToTask(task)); - tasks.push(...newTask); - } - - const filter = getFilterSync(options); - - let matches = []; - for (const task of tasks) { - matches = arrayUnion(matches, fastGlob.sync(task.pattern, task.options)); - } - - return matches.filter(path_ => !filter(path_)); -}; - -module.exports.stream = (patterns, options) => { - const globTasks = generateGlobTasks(patterns, options); - - const tasks = []; - for (const task of globTasks) { - const newTask = getPattern(task, dirGlob.sync).map(globToTask(task)); - tasks.push(...newTask); - } - - const filter = getFilterSync(options); - const filterStream = new FilterStream(p => !filter(p)); - const uniqueStream = new UniqueStream(); - - return merge2(tasks.map(task => fastGlob.stream(task.pattern, task.options))) - .pipe(filterStream) - .pipe(uniqueStream); -}; - -module.exports.generateGlobTasks = generateGlobTasks; - -module.exports.hasMagic = (patterns, options) => [] - .concat(patterns) - .some(pattern => fastGlob.isDynamicPattern(pattern, options)); - -module.exports.gitignore = gitignore; - - -/***/ }), - -/***/ "../../node_modules/globby/stream-utils.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {Transform} = __webpack_require__("stream"); - -class ObjectTransform extends Transform { - constructor() { - super({ - objectMode: true - }); - } -} - -class FilterStream extends ObjectTransform { - constructor(filter) { - super(); - this._filter = filter; - } - - _transform(data, encoding, callback) { - if (this._filter(data)) { - this.push(data); - } - - callback(); - } -} - -class UniqueStream extends ObjectTransform { - constructor() { - super(); - this._pushed = new Set(); - } - - _transform(data, encoding, callback) { - if (!this._pushed.has(data)) { - this.push(data); - this._pushed.add(data); - } - - callback(); - } -} - -module.exports = { - FilterStream, - UniqueStream -}; - - -/***/ }), - -/***/ "../../node_modules/graceful-fs/clone.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = clone - -function clone (obj) { - if (obj === null || typeof obj !== 'object') - return obj - - if (obj instanceof Object) - var copy = { __proto__: obj.__proto__ } - else - var copy = Object.create(null) - - Object.getOwnPropertyNames(obj).forEach(function (key) { - Object.defineProperty(copy, key, Object.getOwnPropertyDescriptor(obj, key)) - }) - - return copy -} - - -/***/ }), - -/***/ "../../node_modules/graceful-fs/graceful-fs.js": -/***/ (function(module, exports, __webpack_require__) { - -var fs = __webpack_require__("fs") -var polyfills = __webpack_require__("../../node_modules/graceful-fs/polyfills.js") -var legacy = __webpack_require__("../../node_modules/graceful-fs/legacy-streams.js") -var clone = __webpack_require__("../../node_modules/graceful-fs/clone.js") - -var util = __webpack_require__("util") - -/* istanbul ignore next - node 0.x polyfill */ -var gracefulQueue -var previousSymbol - -/* istanbul ignore else - node 0.x polyfill */ -if (typeof Symbol === 'function' && typeof Symbol.for === 'function') { - gracefulQueue = Symbol.for('graceful-fs.queue') - // This is used in testing by future versions - previousSymbol = Symbol.for('graceful-fs.previous') -} else { - gracefulQueue = '___graceful-fs.queue' - previousSymbol = '___graceful-fs.previous' -} - -function noop () {} - -function publishQueue(context, queue) { - Object.defineProperty(context, gracefulQueue, { - get: function() { - return queue - } - }) -} - -var debug = noop -if (util.debuglog) - debug = util.debuglog('gfs4') -else if (/\bgfs4\b/i.test(process.env.NODE_DEBUG || '')) - debug = function() { - var m = util.format.apply(util, arguments) - m = 'GFS4: ' + m.split(/\n/).join('\nGFS4: ') - console.error(m) - } - -// Once time initialization -if (!fs[gracefulQueue]) { - // This queue can be shared by multiple loaded instances - var queue = global[gracefulQueue] || [] - publishQueue(fs, queue) - - // Patch fs.close/closeSync to shared queue version, because we need - // to retry() whenever a close happens *anywhere* in the program. - // This is essential when multiple graceful-fs instances are - // in play at the same time. - fs.close = (function (fs$close) { - function close (fd, cb) { - return fs$close.call(fs, fd, function (err) { - // This function uses the graceful-fs shared queue - if (!err) { - retry() - } - - if (typeof cb === 'function') - cb.apply(this, arguments) - }) - } - - Object.defineProperty(close, previousSymbol, { - value: fs$close - }) - return close - })(fs.close) - - fs.closeSync = (function (fs$closeSync) { - function closeSync (fd) { - // This function uses the graceful-fs shared queue - fs$closeSync.apply(fs, arguments) - retry() - } - - Object.defineProperty(closeSync, previousSymbol, { - value: fs$closeSync - }) - return closeSync - })(fs.closeSync) - - if (/\bgfs4\b/i.test(process.env.NODE_DEBUG || '')) { - process.on('exit', function() { - debug(fs[gracefulQueue]) - __webpack_require__("assert").equal(fs[gracefulQueue].length, 0) - }) - } -} - -if (!global[gracefulQueue]) { - publishQueue(global, fs[gracefulQueue]); -} - -module.exports = patch(clone(fs)) -if (process.env.TEST_GRACEFUL_FS_GLOBAL_PATCH && !fs.__patched) { - module.exports = patch(fs) - fs.__patched = true; -} - -function patch (fs) { - // Everything that references the open() function needs to be in here - polyfills(fs) - fs.gracefulify = patch - - fs.createReadStream = createReadStream - fs.createWriteStream = createWriteStream - var fs$readFile = fs.readFile - fs.readFile = readFile - function readFile (path, options, cb) { - if (typeof options === 'function') - cb = options, options = null - - return go$readFile(path, options, cb) - - function go$readFile (path, options, cb) { - return fs$readFile(path, options, function (err) { - if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) - enqueue([go$readFile, [path, options, cb]]) - else { - if (typeof cb === 'function') - cb.apply(this, arguments) - retry() - } - }) - } - } - - var fs$writeFile = fs.writeFile - fs.writeFile = writeFile - function writeFile (path, data, options, cb) { - if (typeof options === 'function') - cb = options, options = null - - return go$writeFile(path, data, options, cb) - - function go$writeFile (path, data, options, cb) { - return fs$writeFile(path, data, options, function (err) { - if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) - enqueue([go$writeFile, [path, data, options, cb]]) - else { - if (typeof cb === 'function') - cb.apply(this, arguments) - retry() - } - }) - } - } - - var fs$appendFile = fs.appendFile - if (fs$appendFile) - fs.appendFile = appendFile - function appendFile (path, data, options, cb) { - if (typeof options === 'function') - cb = options, options = null - - return go$appendFile(path, data, options, cb) - - function go$appendFile (path, data, options, cb) { - return fs$appendFile(path, data, options, function (err) { - if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) - enqueue([go$appendFile, [path, data, options, cb]]) - else { - if (typeof cb === 'function') - cb.apply(this, arguments) - retry() - } - }) - } - } - - var fs$readdir = fs.readdir - fs.readdir = readdir - function readdir (path, options, cb) { - var args = [path] - if (typeof options !== 'function') { - args.push(options) - } else { - cb = options - } - args.push(go$readdir$cb) - - return go$readdir(args) - - function go$readdir$cb (err, files) { - if (files && files.sort) - files.sort() - - if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) - enqueue([go$readdir, [args]]) - - else { - if (typeof cb === 'function') - cb.apply(this, arguments) - retry() - } - } - } - - function go$readdir (args) { - return fs$readdir.apply(fs, args) - } - - if (process.version.substr(0, 4) === 'v0.8') { - var legStreams = legacy(fs) - ReadStream = legStreams.ReadStream - WriteStream = legStreams.WriteStream - } - - var fs$ReadStream = fs.ReadStream - if (fs$ReadStream) { - ReadStream.prototype = Object.create(fs$ReadStream.prototype) - ReadStream.prototype.open = ReadStream$open - } - - var fs$WriteStream = fs.WriteStream - if (fs$WriteStream) { - WriteStream.prototype = Object.create(fs$WriteStream.prototype) - WriteStream.prototype.open = WriteStream$open - } - - Object.defineProperty(fs, 'ReadStream', { - get: function () { - return ReadStream - }, - set: function (val) { - ReadStream = val - }, - enumerable: true, - configurable: true - }) - Object.defineProperty(fs, 'WriteStream', { - get: function () { - return WriteStream - }, - set: function (val) { - WriteStream = val - }, - enumerable: true, - configurable: true - }) - - // legacy names - var FileReadStream = ReadStream - Object.defineProperty(fs, 'FileReadStream', { - get: function () { - return FileReadStream - }, - set: function (val) { - FileReadStream = val - }, - enumerable: true, - configurable: true - }) - var FileWriteStream = WriteStream - Object.defineProperty(fs, 'FileWriteStream', { - get: function () { - return FileWriteStream - }, - set: function (val) { - FileWriteStream = val - }, - enumerable: true, - configurable: true - }) - - function ReadStream (path, options) { - if (this instanceof ReadStream) - return fs$ReadStream.apply(this, arguments), this - else - return ReadStream.apply(Object.create(ReadStream.prototype), arguments) - } - - function ReadStream$open () { - var that = this - open(that.path, that.flags, that.mode, function (err, fd) { - if (err) { - if (that.autoClose) - that.destroy() - - that.emit('error', err) - } else { - that.fd = fd - that.emit('open', fd) - that.read() - } - }) - } - - function WriteStream (path, options) { - if (this instanceof WriteStream) - return fs$WriteStream.apply(this, arguments), this - else - return WriteStream.apply(Object.create(WriteStream.prototype), arguments) - } - - function WriteStream$open () { - var that = this - open(that.path, that.flags, that.mode, function (err, fd) { - if (err) { - that.destroy() - that.emit('error', err) - } else { - that.fd = fd - that.emit('open', fd) - } - }) - } - - function createReadStream (path, options) { - return new fs.ReadStream(path, options) - } - - function createWriteStream (path, options) { - return new fs.WriteStream(path, options) - } - - var fs$open = fs.open - fs.open = open - function open (path, flags, mode, cb) { - if (typeof mode === 'function') - cb = mode, mode = null - - return go$open(path, flags, mode, cb) - - function go$open (path, flags, mode, cb) { - return fs$open(path, flags, mode, function (err, fd) { - if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) - enqueue([go$open, [path, flags, mode, cb]]) - else { - if (typeof cb === 'function') - cb.apply(this, arguments) - retry() - } - }) - } - } - - return fs -} - -function enqueue (elem) { - debug('ENQUEUE', elem[0].name, elem[1]) - fs[gracefulQueue].push(elem) -} - -function retry () { - var elem = fs[gracefulQueue].shift() - if (elem) { - debug('RETRY', elem[0].name, elem[1]) - elem[0].apply(null, elem[1]) - } -} - - -/***/ }), - -/***/ "../../node_modules/graceful-fs/legacy-streams.js": -/***/ (function(module, exports, __webpack_require__) { - -var Stream = __webpack_require__("stream").Stream - -module.exports = legacy - -function legacy (fs) { - return { - ReadStream: ReadStream, - WriteStream: WriteStream - } - - function ReadStream (path, options) { - if (!(this instanceof ReadStream)) return new ReadStream(path, options); - - Stream.call(this); - - var self = this; - - this.path = path; - this.fd = null; - this.readable = true; - this.paused = false; - - this.flags = 'r'; - this.mode = 438; /*=0666*/ - this.bufferSize = 64 * 1024; - - options = options || {}; - - // Mixin options into this - var keys = Object.keys(options); - for (var index = 0, length = keys.length; index < length; index++) { - var key = keys[index]; - this[key] = options[key]; - } - - if (this.encoding) this.setEncoding(this.encoding); - - if (this.start !== undefined) { - if ('number' !== typeof this.start) { - throw TypeError('start must be a Number'); - } - if (this.end === undefined) { - this.end = Infinity; - } else if ('number' !== typeof this.end) { - throw TypeError('end must be a Number'); - } - - if (this.start > this.end) { - throw new Error('start must be <= end'); - } - - this.pos = this.start; - } - - if (this.fd !== null) { - process.nextTick(function() { - self._read(); - }); - return; - } - - fs.open(this.path, this.flags, this.mode, function (err, fd) { - if (err) { - self.emit('error', err); - self.readable = false; - return; - } - - self.fd = fd; - self.emit('open', fd); - self._read(); - }) - } - - function WriteStream (path, options) { - if (!(this instanceof WriteStream)) return new WriteStream(path, options); - - Stream.call(this); - - this.path = path; - this.fd = null; - this.writable = true; - - this.flags = 'w'; - this.encoding = 'binary'; - this.mode = 438; /*=0666*/ - this.bytesWritten = 0; - - options = options || {}; - - // Mixin options into this - var keys = Object.keys(options); - for (var index = 0, length = keys.length; index < length; index++) { - var key = keys[index]; - this[key] = options[key]; - } - - if (this.start !== undefined) { - if ('number' !== typeof this.start) { - throw TypeError('start must be a Number'); - } - if (this.start < 0) { - throw new Error('start must be >= zero'); - } - - this.pos = this.start; - } - - this.busy = false; - this._queue = []; - - if (this.fd === null) { - this._open = fs.open; - this._queue.push([this._open, this.path, this.flags, this.mode, undefined]); - this.flush(); - } - } -} - - -/***/ }), - -/***/ "../../node_modules/graceful-fs/polyfills.js": -/***/ (function(module, exports, __webpack_require__) { - -var constants = __webpack_require__("constants") - -var origCwd = process.cwd -var cwd = null - -var platform = process.env.GRACEFUL_FS_PLATFORM || process.platform - -process.cwd = function() { - if (!cwd) - cwd = origCwd.call(process) - return cwd -} -try { - process.cwd() -} catch (er) {} - -var chdir = process.chdir -process.chdir = function(d) { - cwd = null - chdir.call(process, d) -} - -module.exports = patch - -function patch (fs) { - // (re-)implement some things that are known busted or missing. - - // lchmod, broken prior to 0.6.2 - // back-port the fix here. - if (constants.hasOwnProperty('O_SYMLINK') && - process.version.match(/^v0\.6\.[0-2]|^v0\.5\./)) { - patchLchmod(fs) - } - - // lutimes implementation, or no-op - if (!fs.lutimes) { - patchLutimes(fs) - } - - // https://github.com/isaacs/node-graceful-fs/issues/4 - // Chown should not fail on einval or eperm if non-root. - // It should not fail on enosys ever, as this just indicates - // that a fs doesn't support the intended operation. - - fs.chown = chownFix(fs.chown) - fs.fchown = chownFix(fs.fchown) - fs.lchown = chownFix(fs.lchown) - - fs.chmod = chmodFix(fs.chmod) - fs.fchmod = chmodFix(fs.fchmod) - fs.lchmod = chmodFix(fs.lchmod) - - fs.chownSync = chownFixSync(fs.chownSync) - fs.fchownSync = chownFixSync(fs.fchownSync) - fs.lchownSync = chownFixSync(fs.lchownSync) - - fs.chmodSync = chmodFixSync(fs.chmodSync) - fs.fchmodSync = chmodFixSync(fs.fchmodSync) - fs.lchmodSync = chmodFixSync(fs.lchmodSync) - - fs.stat = statFix(fs.stat) - fs.fstat = statFix(fs.fstat) - fs.lstat = statFix(fs.lstat) - - fs.statSync = statFixSync(fs.statSync) - fs.fstatSync = statFixSync(fs.fstatSync) - fs.lstatSync = statFixSync(fs.lstatSync) - - // if lchmod/lchown do not exist, then make them no-ops - if (!fs.lchmod) { - fs.lchmod = function (path, mode, cb) { - if (cb) process.nextTick(cb) - } - fs.lchmodSync = function () {} - } - if (!fs.lchown) { - fs.lchown = function (path, uid, gid, cb) { - if (cb) process.nextTick(cb) - } - fs.lchownSync = function () {} - } - - // on Windows, A/V software can lock the directory, causing this - // to fail with an EACCES or EPERM if the directory contains newly - // created files. Try again on failure, for up to 60 seconds. - - // Set the timeout this long because some Windows Anti-Virus, such as Parity - // bit9, may lock files for up to a minute, causing npm package install - // failures. Also, take care to yield the scheduler. Windows scheduling gives - // CPU to a busy looping process, which can cause the program causing the lock - // contention to be starved of CPU by node, so the contention doesn't resolve. - if (platform === "win32") { - fs.rename = (function (fs$rename) { return function (from, to, cb) { - var start = Date.now() - var backoff = 0; - fs$rename(from, to, function CB (er) { - if (er - && (er.code === "EACCES" || er.code === "EPERM") - && Date.now() - start < 60000) { - setTimeout(function() { - fs.stat(to, function (stater, st) { - if (stater && stater.code === "ENOENT") - fs$rename(from, to, CB); - else - cb(er) - }) - }, backoff) - if (backoff < 100) - backoff += 10; - return; - } - if (cb) cb(er) - }) - }})(fs.rename) - } - - // if read() returns EAGAIN, then just try it again. - fs.read = (function (fs$read) { - function read (fd, buffer, offset, length, position, callback_) { - var callback - if (callback_ && typeof callback_ === 'function') { - var eagCounter = 0 - callback = function (er, _, __) { - if (er && er.code === 'EAGAIN' && eagCounter < 10) { - eagCounter ++ - return fs$read.call(fs, fd, buffer, offset, length, position, callback) - } - callback_.apply(this, arguments) - } - } - return fs$read.call(fs, fd, buffer, offset, length, position, callback) - } - - // This ensures `util.promisify` works as it does for native `fs.read`. - read.__proto__ = fs$read - return read - })(fs.read) - - fs.readSync = (function (fs$readSync) { return function (fd, buffer, offset, length, position) { - var eagCounter = 0 - while (true) { - try { - return fs$readSync.call(fs, fd, buffer, offset, length, position) - } catch (er) { - if (er.code === 'EAGAIN' && eagCounter < 10) { - eagCounter ++ - continue - } - throw er - } - } - }})(fs.readSync) - - function patchLchmod (fs) { - fs.lchmod = function (path, mode, callback) { - fs.open( path - , constants.O_WRONLY | constants.O_SYMLINK - , mode - , function (err, fd) { - if (err) { - if (callback) callback(err) - return - } - // prefer to return the chmod error, if one occurs, - // but still try to close, and report closing errors if they occur. - fs.fchmod(fd, mode, function (err) { - fs.close(fd, function(err2) { - if (callback) callback(err || err2) - }) - }) - }) - } - - fs.lchmodSync = function (path, mode) { - var fd = fs.openSync(path, constants.O_WRONLY | constants.O_SYMLINK, mode) - - // prefer to return the chmod error, if one occurs, - // but still try to close, and report closing errors if they occur. - var threw = true - var ret - try { - ret = fs.fchmodSync(fd, mode) - threw = false - } finally { - if (threw) { - try { - fs.closeSync(fd) - } catch (er) {} - } else { - fs.closeSync(fd) - } - } - return ret - } - } - - function patchLutimes (fs) { - if (constants.hasOwnProperty("O_SYMLINK")) { - fs.lutimes = function (path, at, mt, cb) { - fs.open(path, constants.O_SYMLINK, function (er, fd) { - if (er) { - if (cb) cb(er) - return - } - fs.futimes(fd, at, mt, function (er) { - fs.close(fd, function (er2) { - if (cb) cb(er || er2) - }) - }) - }) - } - - fs.lutimesSync = function (path, at, mt) { - var fd = fs.openSync(path, constants.O_SYMLINK) - var ret - var threw = true - try { - ret = fs.futimesSync(fd, at, mt) - threw = false - } finally { - if (threw) { - try { - fs.closeSync(fd) - } catch (er) {} - } else { - fs.closeSync(fd) - } - } - return ret - } - - } else { - fs.lutimes = function (_a, _b, _c, cb) { if (cb) process.nextTick(cb) } - fs.lutimesSync = function () {} - } - } - - function chmodFix (orig) { - if (!orig) return orig - return function (target, mode, cb) { - return orig.call(fs, target, mode, function (er) { - if (chownErOk(er)) er = null - if (cb) cb.apply(this, arguments) - }) - } - } - - function chmodFixSync (orig) { - if (!orig) return orig - return function (target, mode) { - try { - return orig.call(fs, target, mode) - } catch (er) { - if (!chownErOk(er)) throw er - } - } - } - - - function chownFix (orig) { - if (!orig) return orig - return function (target, uid, gid, cb) { - return orig.call(fs, target, uid, gid, function (er) { - if (chownErOk(er)) er = null - if (cb) cb.apply(this, arguments) - }) - } - } - - function chownFixSync (orig) { - if (!orig) return orig - return function (target, uid, gid) { - try { - return orig.call(fs, target, uid, gid) - } catch (er) { - if (!chownErOk(er)) throw er - } - } - } - - function statFix (orig) { - if (!orig) return orig - // Older versions of Node erroneously returned signed integers for - // uid + gid. - return function (target, options, cb) { - if (typeof options === 'function') { - cb = options - options = null - } - function callback (er, stats) { - if (stats) { - if (stats.uid < 0) stats.uid += 0x100000000 - if (stats.gid < 0) stats.gid += 0x100000000 - } - if (cb) cb.apply(this, arguments) - } - return options ? orig.call(fs, target, options, callback) - : orig.call(fs, target, callback) - } - } - - function statFixSync (orig) { - if (!orig) return orig - // Older versions of Node erroneously returned signed integers for - // uid + gid. - return function (target, options) { - var stats = options ? orig.call(fs, target, options) - : orig.call(fs, target) - if (stats.uid < 0) stats.uid += 0x100000000 - if (stats.gid < 0) stats.gid += 0x100000000 - return stats; - } - } - - // ENOSYS means that the fs doesn't support the op. Just ignore - // that, because it doesn't matter. - // - // if there's no getuid, or if getuid() is something other - // than 0, and the error is EINVAL or EPERM, then just ignore - // it. - // - // This specific case is a silent failure in cp, install, tar, - // and most other unix tools that manage permissions. - // - // When running as root, or if other types of errors are - // encountered, then it's strict. - function chownErOk (er) { - if (!er) - return true - - if (er.code === "ENOSYS") - return true - - var nonroot = !process.getuid || process.getuid() !== 0 - if (nonroot) { - if (er.code === "EINVAL" || er.code === "EPERM") - return true - } - - return false - } -} - - -/***/ }), - -/***/ "../../node_modules/has-flag/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = (flag, argv = process.argv) => { - const prefix = flag.startsWith('-') ? '' : (flag.length === 1 ? '-' : '--'); - const position = argv.indexOf(prefix + flag); - const terminatorPosition = argv.indexOf('--'); - return position !== -1 && (terminatorPosition === -1 || position < terminatorPosition); -}; - - -/***/ }), - -/***/ "../../node_modules/has/src/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var bind = __webpack_require__("../../node_modules/function-bind/index.js"); - -module.exports = bind.call(Function.call, Object.prototype.hasOwnProperty); - - -/***/ }), - -/***/ "../../node_modules/hosted-git-info/git-host-info.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var gitHosts = module.exports = { - github: { - // First two are insecure and generally shouldn't be used any more, but - // they are still supported. - 'protocols': [ 'git', 'http', 'git+ssh', 'git+https', 'ssh', 'https' ], - 'domain': 'github.com', - 'treepath': 'tree', - 'filetemplate': 'https://{auth@}raw.githubusercontent.com/{user}/{project}/{committish}/{path}', - 'bugstemplate': 'https://{domain}/{user}/{project}/issues', - 'gittemplate': 'git://{auth@}{domain}/{user}/{project}.git{#committish}', - 'tarballtemplate': 'https://codeload.{domain}/{user}/{project}/tar.gz/{committish}' - }, - bitbucket: { - 'protocols': [ 'git+ssh', 'git+https', 'ssh', 'https' ], - 'domain': 'bitbucket.org', - 'treepath': 'src', - 'tarballtemplate': 'https://{domain}/{user}/{project}/get/{committish}.tar.gz' - }, - gitlab: { - 'protocols': [ 'git+ssh', 'git+https', 'ssh', 'https' ], - 'domain': 'gitlab.com', - 'treepath': 'tree', - 'bugstemplate': 'https://{domain}/{user}/{project}/issues', - 'httpstemplate': 'git+https://{auth@}{domain}/{user}/{projectPath}.git{#committish}', - 'tarballtemplate': 'https://{domain}/{user}/{project}/repository/archive.tar.gz?ref={committish}', - 'pathmatch': /^[/]([^/]+)[/]((?!.*(\/-\/|\/repository\/archive\.tar\.gz\?=.*|\/repository\/[^/]+\/archive.tar.gz$)).*?)(?:[.]git|[/])?$/ - }, - gist: { - 'protocols': [ 'git', 'git+ssh', 'git+https', 'ssh', 'https' ], - 'domain': 'gist.github.com', - 'pathmatch': /^[/](?:([^/]+)[/])?([a-z0-9]{32,})(?:[.]git)?$/, - 'filetemplate': 'https://gist.githubusercontent.com/{user}/{project}/raw{/committish}/{path}', - 'bugstemplate': 'https://{domain}/{project}', - 'gittemplate': 'git://{domain}/{project}.git{#committish}', - 'sshtemplate': 'git@{domain}:/{project}.git{#committish}', - 'sshurltemplate': 'git+ssh://git@{domain}/{project}.git{#committish}', - 'browsetemplate': 'https://{domain}/{project}{/committish}', - 'browsefiletemplate': 'https://{domain}/{project}{/committish}{#path}', - 'docstemplate': 'https://{domain}/{project}{/committish}', - 'httpstemplate': 'git+https://{domain}/{project}.git{#committish}', - 'shortcuttemplate': '{type}:{project}{#committish}', - 'pathtemplate': '{project}{#committish}', - 'tarballtemplate': 'https://codeload.github.com/gist/{project}/tar.gz/{committish}', - 'hashformat': function (fragment) { - return 'file-' + formatHashFragment(fragment) - } - } -} - -var gitHostDefaults = { - 'sshtemplate': 'git@{domain}:{user}/{project}.git{#committish}', - 'sshurltemplate': 'git+ssh://git@{domain}/{user}/{project}.git{#committish}', - 'browsetemplate': 'https://{domain}/{user}/{project}{/tree/committish}', - 'browsefiletemplate': 'https://{domain}/{user}/{project}/{treepath}/{committish}/{path}{#fragment}', - 'docstemplate': 'https://{domain}/{user}/{project}{/tree/committish}#readme', - 'httpstemplate': 'git+https://{auth@}{domain}/{user}/{project}.git{#committish}', - 'filetemplate': 'https://{domain}/{user}/{project}/raw/{committish}/{path}', - 'shortcuttemplate': '{type}:{user}/{project}{#committish}', - 'pathtemplate': '{user}/{project}{#committish}', - 'pathmatch': /^[/]([^/]+)[/]([^/]+?)(?:[.]git|[/])?$/, - 'hashformat': formatHashFragment -} - -Object.keys(gitHosts).forEach(function (name) { - Object.keys(gitHostDefaults).forEach(function (key) { - if (gitHosts[name][key]) return - gitHosts[name][key] = gitHostDefaults[key] - }) - gitHosts[name].protocols_re = RegExp('^(' + - gitHosts[name].protocols.map(function (protocol) { - return protocol.replace(/([\\+*{}()[\]$^|])/g, '\\$1') - }).join('|') + '):$') -}) - -function formatHashFragment (fragment) { - return fragment.toLowerCase().replace(/^\W+|\/|\W+$/g, '').replace(/\W+/g, '-') -} - - -/***/ }), - -/***/ "../../node_modules/hosted-git-info/git-host.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var gitHosts = __webpack_require__("../../node_modules/hosted-git-info/git-host-info.js") -/* eslint-disable node/no-deprecated-api */ - -// copy-pasta util._extend from node's source, to avoid pulling -// the whole util module into peoples' webpack bundles. -/* istanbul ignore next */ -var extend = Object.assign || function _extend (target, source) { - // Don't do anything if source isn't an object - if (source === null || typeof source !== 'object') return target - - var keys = Object.keys(source) - var i = keys.length - while (i--) { - target[keys[i]] = source[keys[i]] - } - return target -} - -module.exports = GitHost -function GitHost (type, user, auth, project, committish, defaultRepresentation, opts) { - var gitHostInfo = this - gitHostInfo.type = type - Object.keys(gitHosts[type]).forEach(function (key) { - gitHostInfo[key] = gitHosts[type][key] - }) - gitHostInfo.user = user - gitHostInfo.auth = auth - gitHostInfo.project = project - gitHostInfo.committish = committish - gitHostInfo.default = defaultRepresentation - gitHostInfo.opts = opts || {} -} - -GitHost.prototype.hash = function () { - return this.committish ? '#' + this.committish : '' -} - -GitHost.prototype._fill = function (template, opts) { - if (!template) return - var vars = extend({}, opts) - vars.path = vars.path ? vars.path.replace(/^[/]+/g, '') : '' - opts = extend(extend({}, this.opts), opts) - var self = this - Object.keys(this).forEach(function (key) { - if (self[key] != null && vars[key] == null) vars[key] = self[key] - }) - var rawAuth = vars.auth - var rawcommittish = vars.committish - var rawFragment = vars.fragment - var rawPath = vars.path - var rawProject = vars.project - Object.keys(vars).forEach(function (key) { - var value = vars[key] - if ((key === 'path' || key === 'project') && typeof value === 'string') { - vars[key] = value.split('/').map(function (pathComponent) { - return encodeURIComponent(pathComponent) - }).join('/') - } else { - vars[key] = encodeURIComponent(value) - } - }) - vars['auth@'] = rawAuth ? rawAuth + '@' : '' - vars['#fragment'] = rawFragment ? '#' + this.hashformat(rawFragment) : '' - vars.fragment = vars.fragment ? vars.fragment : '' - vars['#path'] = rawPath ? '#' + this.hashformat(rawPath) : '' - vars['/path'] = vars.path ? '/' + vars.path : '' - vars.projectPath = rawProject.split('/').map(encodeURIComponent).join('/') - if (opts.noCommittish) { - vars['#committish'] = '' - vars['/tree/committish'] = '' - vars['/committish'] = '' - vars.committish = '' - } else { - vars['#committish'] = rawcommittish ? '#' + rawcommittish : '' - vars['/tree/committish'] = vars.committish - ? '/' + vars.treepath + '/' + vars.committish - : '' - vars['/committish'] = vars.committish ? '/' + vars.committish : '' - vars.committish = vars.committish || 'master' - } - var res = template - Object.keys(vars).forEach(function (key) { - res = res.replace(new RegExp('[{]' + key + '[}]', 'g'), vars[key]) - }) - if (opts.noGitPlus) { - return res.replace(/^git[+]/, '') - } else { - return res - } -} - -GitHost.prototype.ssh = function (opts) { - return this._fill(this.sshtemplate, opts) -} - -GitHost.prototype.sshurl = function (opts) { - return this._fill(this.sshurltemplate, opts) -} - -GitHost.prototype.browse = function (P, F, opts) { - if (typeof P === 'string') { - if (typeof F !== 'string') { - opts = F - F = null - } - return this._fill(this.browsefiletemplate, extend({ - fragment: F, - path: P - }, opts)) - } else { - return this._fill(this.browsetemplate, P) - } -} - -GitHost.prototype.docs = function (opts) { - return this._fill(this.docstemplate, opts) -} - -GitHost.prototype.bugs = function (opts) { - return this._fill(this.bugstemplate, opts) -} - -GitHost.prototype.https = function (opts) { - return this._fill(this.httpstemplate, opts) -} - -GitHost.prototype.git = function (opts) { - return this._fill(this.gittemplate, opts) -} - -GitHost.prototype.shortcut = function (opts) { - return this._fill(this.shortcuttemplate, opts) -} - -GitHost.prototype.path = function (opts) { - return this._fill(this.pathtemplate, opts) -} - -GitHost.prototype.tarball = function (opts_) { - var opts = extend({}, opts_, { noCommittish: false }) - return this._fill(this.tarballtemplate, opts) -} - -GitHost.prototype.file = function (P, opts) { - return this._fill(this.filetemplate, extend({ path: P }, opts)) -} - -GitHost.prototype.getDefaultRepresentation = function () { - return this.default -} - -GitHost.prototype.toString = function (opts) { - if (this.default && typeof this[this.default] === 'function') return this[this.default](opts) - return this.sshurl(opts) -} - - -/***/ }), - -/***/ "../../node_modules/hosted-git-info/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var url = __webpack_require__("url") -var gitHosts = __webpack_require__("../../node_modules/hosted-git-info/git-host-info.js") -var GitHost = module.exports = __webpack_require__("../../node_modules/hosted-git-info/git-host.js") - -var protocolToRepresentationMap = { - 'git+ssh:': 'sshurl', - 'git+https:': 'https', - 'ssh:': 'sshurl', - 'git:': 'git' -} - -function protocolToRepresentation (protocol) { - return protocolToRepresentationMap[protocol] || protocol.slice(0, -1) -} - -var authProtocols = { - 'git:': true, - 'https:': true, - 'git+https:': true, - 'http:': true, - 'git+http:': true -} - -var cache = {} - -module.exports.fromUrl = function (giturl, opts) { - if (typeof giturl !== 'string') return - var key = giturl + JSON.stringify(opts || {}) - - if (!(key in cache)) { - cache[key] = fromUrl(giturl, opts) - } - - return cache[key] -} - -function fromUrl (giturl, opts) { - if (giturl == null || giturl === '') return - var url = fixupUnqualifiedGist( - isGitHubShorthand(giturl) ? 'github:' + giturl : giturl - ) - var parsed = parseGitUrl(url) - var shortcutMatch = url.match(/^([^:]+):(?:[^@]+@)?(?:([^/]*)\/)?([^#]+)/) - var matches = Object.keys(gitHosts).map(function (gitHostName) { - try { - var gitHostInfo = gitHosts[gitHostName] - var auth = null - if (parsed.auth && authProtocols[parsed.protocol]) { - auth = parsed.auth - } - var committish = parsed.hash ? decodeURIComponent(parsed.hash.substr(1)) : null - var user = null - var project = null - var defaultRepresentation = null - if (shortcutMatch && shortcutMatch[1] === gitHostName) { - user = shortcutMatch[2] && decodeURIComponent(shortcutMatch[2]) - project = decodeURIComponent(shortcutMatch[3].replace(/\.git$/, '')) - defaultRepresentation = 'shortcut' - } else { - if (parsed.host && parsed.host !== gitHostInfo.domain && parsed.host.replace(/^www[.]/, '') !== gitHostInfo.domain) return - if (!gitHostInfo.protocols_re.test(parsed.protocol)) return - if (!parsed.path) return - var pathmatch = gitHostInfo.pathmatch - var matched = parsed.path.match(pathmatch) - if (!matched) return - /* istanbul ignore else */ - if (matched[1] !== null && matched[1] !== undefined) { - user = decodeURIComponent(matched[1].replace(/^:/, '')) - } - project = decodeURIComponent(matched[2]) - defaultRepresentation = protocolToRepresentation(parsed.protocol) - } - return new GitHost(gitHostName, user, auth, project, committish, defaultRepresentation, opts) - } catch (ex) { - /* istanbul ignore else */ - if (ex instanceof URIError) { - } else throw ex - } - }).filter(function (gitHostInfo) { return gitHostInfo }) - if (matches.length !== 1) return - return matches[0] -} - -function isGitHubShorthand (arg) { - // Note: This does not fully test the git ref format. - // See https://www.kernel.org/pub/software/scm/git/docs/git-check-ref-format.html - // - // The only way to do this properly would be to shell out to - // git-check-ref-format, and as this is a fast sync function, - // we don't want to do that. Just let git fail if it turns - // out that the commit-ish is invalid. - // GH usernames cannot start with . or - - return /^[^:@%/\s.-][^:@%/\s]*[/][^:@\s/%]+(?:#.*)?$/.test(arg) -} - -function fixupUnqualifiedGist (giturl) { - // necessary for round-tripping gists - var parsed = url.parse(giturl) - if (parsed.protocol === 'gist:' && parsed.host && !parsed.path) { - return parsed.protocol + '/' + parsed.host - } else { - return giturl - } -} - -function parseGitUrl (giturl) { - var matched = giturl.match(/^([^@]+)@([^:/]+):[/]?((?:[^/]+[/])?[^/]+?)(?:[.]git)?(#.*)?$/) - if (!matched) { - var legacy = url.parse(giturl) - // If we don't have url.URL, then sorry, this is just not fixable. - // This affects Node <= 6.12. - if (legacy.auth && typeof url.URL === 'function') { - // git urls can be in the form of scp-style/ssh-connect strings, like - // git+ssh://user@host.com:some/path, which the legacy url parser - // supports, but WhatWG url.URL class does not. However, the legacy - // parser de-urlencodes the username and password, so something like - // https://user%3An%40me:p%40ss%3Aword@x.com/ becomes - // https://user:n@me:p@ss:word@x.com/ which is all kinds of wrong. - // Pull off just the auth and host, so we dont' get the confusing - // scp-style URL, then pass that to the WhatWG parser to get the - // auth properly escaped. - var authmatch = giturl.match(/[^@]+@[^:/]+/) - /* istanbul ignore else - this should be impossible */ - if (authmatch) { - var whatwg = new url.URL(authmatch[0]) - legacy.auth = whatwg.username || '' - if (whatwg.password) legacy.auth += ':' + whatwg.password - } - } - return legacy - } - return { - protocol: 'git+ssh:', - slashes: true, - auth: matched[1], - host: matched[2], - port: null, - hostname: matched[2], - hash: matched[4], - search: null, - query: null, - pathname: '/' + matched[3], - path: '/' + matched[3], - href: 'git+ssh://' + matched[1] + '@' + matched[2] + - '/' + matched[3] + (matched[4] || '') - } -} - - -/***/ }), - -/***/ "../../node_modules/human-signals/build/src/core.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -Object.defineProperty(exports,"__esModule",{value:true});exports.SIGNALS=void 0; - -const SIGNALS=[ -{ -name:"SIGHUP", -number:1, -action:"terminate", -description:"Terminal closed", -standard:"posix"}, - -{ -name:"SIGINT", -number:2, -action:"terminate", -description:"User interruption with CTRL-C", -standard:"ansi"}, - -{ -name:"SIGQUIT", -number:3, -action:"core", -description:"User interruption with CTRL-\\", -standard:"posix"}, - -{ -name:"SIGILL", -number:4, -action:"core", -description:"Invalid machine instruction", -standard:"ansi"}, - -{ -name:"SIGTRAP", -number:5, -action:"core", -description:"Debugger breakpoint", -standard:"posix"}, - -{ -name:"SIGABRT", -number:6, -action:"core", -description:"Aborted", -standard:"ansi"}, - -{ -name:"SIGIOT", -number:6, -action:"core", -description:"Aborted", -standard:"bsd"}, - -{ -name:"SIGBUS", -number:7, -action:"core", -description: -"Bus error due to misaligned, non-existing address or paging error", -standard:"bsd"}, - -{ -name:"SIGEMT", -number:7, -action:"terminate", -description:"Command should be emulated but is not implemented", -standard:"other"}, - -{ -name:"SIGFPE", -number:8, -action:"core", -description:"Floating point arithmetic error", -standard:"ansi"}, - -{ -name:"SIGKILL", -number:9, -action:"terminate", -description:"Forced termination", -standard:"posix", -forced:true}, - -{ -name:"SIGUSR1", -number:10, -action:"terminate", -description:"Application-specific signal", -standard:"posix"}, - -{ -name:"SIGSEGV", -number:11, -action:"core", -description:"Segmentation fault", -standard:"ansi"}, - -{ -name:"SIGUSR2", -number:12, -action:"terminate", -description:"Application-specific signal", -standard:"posix"}, - -{ -name:"SIGPIPE", -number:13, -action:"terminate", -description:"Broken pipe or socket", -standard:"posix"}, - -{ -name:"SIGALRM", -number:14, -action:"terminate", -description:"Timeout or timer", -standard:"posix"}, - -{ -name:"SIGTERM", -number:15, -action:"terminate", -description:"Termination", -standard:"ansi"}, - -{ -name:"SIGSTKFLT", -number:16, -action:"terminate", -description:"Stack is empty or overflowed", -standard:"other"}, - -{ -name:"SIGCHLD", -number:17, -action:"ignore", -description:"Child process terminated, paused or unpaused", -standard:"posix"}, - -{ -name:"SIGCLD", -number:17, -action:"ignore", -description:"Child process terminated, paused or unpaused", -standard:"other"}, - -{ -name:"SIGCONT", -number:18, -action:"unpause", -description:"Unpaused", -standard:"posix", -forced:true}, - -{ -name:"SIGSTOP", -number:19, -action:"pause", -description:"Paused", -standard:"posix", -forced:true}, - -{ -name:"SIGTSTP", -number:20, -action:"pause", -description:"Paused using CTRL-Z or \"suspend\"", -standard:"posix"}, - -{ -name:"SIGTTIN", -number:21, -action:"pause", -description:"Background process cannot read terminal input", -standard:"posix"}, - -{ -name:"SIGBREAK", -number:21, -action:"terminate", -description:"User interruption with CTRL-BREAK", -standard:"other"}, - -{ -name:"SIGTTOU", -number:22, -action:"pause", -description:"Background process cannot write to terminal output", -standard:"posix"}, - -{ -name:"SIGURG", -number:23, -action:"ignore", -description:"Socket received out-of-band data", -standard:"bsd"}, - -{ -name:"SIGXCPU", -number:24, -action:"core", -description:"Process timed out", -standard:"bsd"}, - -{ -name:"SIGXFSZ", -number:25, -action:"core", -description:"File too big", -standard:"bsd"}, - -{ -name:"SIGVTALRM", -number:26, -action:"terminate", -description:"Timeout or timer", -standard:"bsd"}, - -{ -name:"SIGPROF", -number:27, -action:"terminate", -description:"Timeout or timer", -standard:"bsd"}, - -{ -name:"SIGWINCH", -number:28, -action:"ignore", -description:"Terminal window size changed", -standard:"bsd"}, - -{ -name:"SIGIO", -number:29, -action:"terminate", -description:"I/O is available", -standard:"other"}, - -{ -name:"SIGPOLL", -number:29, -action:"terminate", -description:"Watched event", -standard:"other"}, - -{ -name:"SIGINFO", -number:29, -action:"ignore", -description:"Request for process information", -standard:"other"}, - -{ -name:"SIGPWR", -number:30, -action:"terminate", -description:"Device running out of power", -standard:"systemv"}, - -{ -name:"SIGSYS", -number:31, -action:"core", -description:"Invalid system call", -standard:"other"}, - -{ -name:"SIGUNUSED", -number:31, -action:"terminate", -description:"Invalid system call", -standard:"other"}];exports.SIGNALS=SIGNALS; -//# sourceMappingURL=core.js.map - -/***/ }), - -/***/ "../../node_modules/human-signals/build/src/main.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -Object.defineProperty(exports,"__esModule",{value:true});exports.signalsByNumber=exports.signalsByName=void 0;var _os=__webpack_require__("os"); - -var _signals=__webpack_require__("../../node_modules/human-signals/build/src/signals.js"); -var _realtime=__webpack_require__("../../node_modules/human-signals/build/src/realtime.js"); - - - -const getSignalsByName=function(){ -const signals=(0,_signals.getSignals)(); -return signals.reduce(getSignalByName,{}); -}; - -const getSignalByName=function( -signalByNameMemo, -{name,number,description,supported,action,forced,standard}) -{ -return{ -...signalByNameMemo, -[name]:{name,number,description,supported,action,forced,standard}}; - -}; - -const signalsByName=getSignalsByName();exports.signalsByName=signalsByName; - - - - -const getSignalsByNumber=function(){ -const signals=(0,_signals.getSignals)(); -const length=_realtime.SIGRTMAX+1; -const signalsA=Array.from({length},(value,number)=> -getSignalByNumber(number,signals)); - -return Object.assign({},...signalsA); -}; - -const getSignalByNumber=function(number,signals){ -const signal=findSignalByNumber(number,signals); - -if(signal===undefined){ -return{}; -} - -const{name,description,supported,action,forced,standard}=signal; -return{ -[number]:{ -name, -number, -description, -supported, -action, -forced, -standard}}; - - -}; - - - -const findSignalByNumber=function(number,signals){ -const signal=signals.find(({name})=>_os.constants.signals[name]===number); - -if(signal!==undefined){ -return signal; -} - -return signals.find(signalA=>signalA.number===number); -}; - -const signalsByNumber=getSignalsByNumber();exports.signalsByNumber=signalsByNumber; -//# sourceMappingURL=main.js.map - -/***/ }), - -/***/ "../../node_modules/human-signals/build/src/realtime.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -Object.defineProperty(exports,"__esModule",{value:true});exports.SIGRTMAX=exports.getRealtimeSignals=void 0; -const getRealtimeSignals=function(){ -const length=SIGRTMAX-SIGRTMIN+1; -return Array.from({length},getRealtimeSignal); -};exports.getRealtimeSignals=getRealtimeSignals; - -const getRealtimeSignal=function(value,index){ -return{ -name:`SIGRT${index+1}`, -number:SIGRTMIN+index, -action:"terminate", -description:"Application-specific signal (realtime)", -standard:"posix"}; - -}; - -const SIGRTMIN=34; -const SIGRTMAX=64;exports.SIGRTMAX=SIGRTMAX; -//# sourceMappingURL=realtime.js.map - -/***/ }), - -/***/ "../../node_modules/human-signals/build/src/signals.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -Object.defineProperty(exports,"__esModule",{value:true});exports.getSignals=void 0;var _os=__webpack_require__("os"); - -var _core=__webpack_require__("../../node_modules/human-signals/build/src/core.js"); -var _realtime=__webpack_require__("../../node_modules/human-signals/build/src/realtime.js"); - - - -const getSignals=function(){ -const realtimeSignals=(0,_realtime.getRealtimeSignals)(); -const signals=[..._core.SIGNALS,...realtimeSignals].map(normalizeSignal); -return signals; -};exports.getSignals=getSignals; - - - - - - - -const normalizeSignal=function({ -name, -number:defaultNumber, -description, -action, -forced=false, -standard}) -{ -const{ -signals:{[name]:constantSignal}}= -_os.constants; -const supported=constantSignal!==undefined; -const number=supported?constantSignal:defaultNumber; -return{name,number,description,supported,action,forced,standard}; -}; -//# sourceMappingURL=signals.js.map - -/***/ }), - -/***/ "../../node_modules/ignore/index.js": -/***/ (function(module, exports) { - -// A simple implementation of make-array -function makeArray (subject) { - return Array.isArray(subject) - ? subject - : [subject] -} - -const EMPTY = '' -const SPACE = ' ' -const ESCAPE = '\\' -const REGEX_TEST_BLANK_LINE = /^\s+$/ -const REGEX_REPLACE_LEADING_EXCAPED_EXCLAMATION = /^\\!/ -const REGEX_REPLACE_LEADING_EXCAPED_HASH = /^\\#/ -const REGEX_SPLITALL_CRLF = /\r?\n/g -// /foo, -// ./foo, -// ../foo, -// . -// .. -const REGEX_TEST_INVALID_PATH = /^\.*\/|^\.+$/ - -const SLASH = '/' -const KEY_IGNORE = typeof Symbol !== 'undefined' - ? Symbol.for('node-ignore') - /* istanbul ignore next */ - : 'node-ignore' - -const define = (object, key, value) => - Object.defineProperty(object, key, {value}) - -const REGEX_REGEXP_RANGE = /([0-z])-([0-z])/g - -// Sanitize the range of a regular expression -// The cases are complicated, see test cases for details -const sanitizeRange = range => range.replace( - REGEX_REGEXP_RANGE, - (match, from, to) => from.charCodeAt(0) <= to.charCodeAt(0) - ? match - // Invalid range (out of order) which is ok for gitignore rules but - // fatal for JavaScript regular expression, so eliminate it. - : EMPTY -) - -// See fixtures #59 -const cleanRangeBackSlash = slashes => { - const {length} = slashes - return slashes.slice(0, length - length % 2) -} - -// > If the pattern ends with a slash, -// > it is removed for the purpose of the following description, -// > but it would only find a match with a directory. -// > In other words, foo/ will match a directory foo and paths underneath it, -// > but will not match a regular file or a symbolic link foo -// > (this is consistent with the way how pathspec works in general in Git). -// '`foo/`' will not match regular file '`foo`' or symbolic link '`foo`' -// -> ignore-rules will not deal with it, because it costs extra `fs.stat` call -// you could use option `mark: true` with `glob` - -// '`foo/`' should not continue with the '`..`' -const REPLACERS = [ - - // > Trailing spaces are ignored unless they are quoted with backslash ("\") - [ - // (a\ ) -> (a ) - // (a ) -> (a) - // (a \ ) -> (a ) - /\\?\s+$/, - match => match.indexOf('\\') === 0 - ? SPACE - : EMPTY - ], - - // replace (\ ) with ' ' - [ - /\\\s/g, - () => SPACE - ], - - // Escape metacharacters - // which is written down by users but means special for regular expressions. - - // > There are 12 characters with special meanings: - // > - the backslash \, - // > - the caret ^, - // > - the dollar sign $, - // > - the period or dot ., - // > - the vertical bar or pipe symbol |, - // > - the question mark ?, - // > - the asterisk or star *, - // > - the plus sign +, - // > - the opening parenthesis (, - // > - the closing parenthesis ), - // > - and the opening square bracket [, - // > - the opening curly brace {, - // > These special characters are often called "metacharacters". - [ - /[\\$.|*+(){^]/g, - match => `\\${match}` - ], - - [ - // > a question mark (?) matches a single character - /(?!\\)\?/g, - () => '[^/]' - ], - - // leading slash - [ - - // > A leading slash matches the beginning of the pathname. - // > For example, "/*.c" matches "cat-file.c" but not "mozilla-sha1/sha1.c". - // A leading slash matches the beginning of the pathname - /^\//, - () => '^' - ], - - // replace special metacharacter slash after the leading slash - [ - /\//g, - () => '\\/' - ], - - [ - // > A leading "**" followed by a slash means match in all directories. - // > For example, "**/foo" matches file or directory "foo" anywhere, - // > the same as pattern "foo". - // > "**/foo/bar" matches file or directory "bar" anywhere that is directly - // > under directory "foo". - // Notice that the '*'s have been replaced as '\\*' - /^\^*\\\*\\\*\\\//, - - // '**/foo' <-> 'foo' - () => '^(?:.*\\/)?' - ], - - // starting - [ - // there will be no leading '/' - // (which has been replaced by section "leading slash") - // If starts with '**', adding a '^' to the regular expression also works - /^(?=[^^])/, - function startingReplacer () { - // If has a slash `/` at the beginning or middle - return !/\/(?!$)/.test(this) - // > Prior to 2.22.1 - // > If the pattern does not contain a slash /, - // > Git treats it as a shell glob pattern - // Actually, if there is only a trailing slash, - // git also treats it as a shell glob pattern - - // After 2.22.1 (compatible but clearer) - // > If there is a separator at the beginning or middle (or both) - // > of the pattern, then the pattern is relative to the directory - // > level of the particular .gitignore file itself. - // > Otherwise the pattern may also match at any level below - // > the .gitignore level. - ? '(?:^|\\/)' - - // > Otherwise, Git treats the pattern as a shell glob suitable for - // > consumption by fnmatch(3) - : '^' - } - ], - - // two globstars - [ - // Use lookahead assertions so that we could match more than one `'/**'` - /\\\/\\\*\\\*(?=\\\/|$)/g, - - // Zero, one or several directories - // should not use '*', or it will be replaced by the next replacer - - // Check if it is not the last `'/**'` - (_, index, str) => index + 6 < str.length - - // case: /**/ - // > A slash followed by two consecutive asterisks then a slash matches - // > zero or more directories. - // > For example, "a/**/b" matches "a/b", "a/x/b", "a/x/y/b" and so on. - // '/**/' - ? '(?:\\/[^\\/]+)*' - - // case: /** - // > A trailing `"/**"` matches everything inside. - - // #21: everything inside but it should not include the current folder - : '\\/.+' - ], - - // intermediate wildcards - [ - // Never replace escaped '*' - // ignore rule '\*' will match the path '*' - - // 'abc.*/' -> go - // 'abc.*' -> skip this rule - /(^|[^\\]+)\\\*(?=.+)/g, - - // '*.js' matches '.js' - // '*.js' doesn't match 'abc' - (_, p1) => `${p1}[^\\/]*` - ], - - [ - // unescape, revert step 3 except for back slash - // For example, if a user escape a '\\*', - // after step 3, the result will be '\\\\\\*' - /\\\\\\(?=[$.|*+(){^])/g, - () => ESCAPE - ], - - [ - // '\\\\' -> '\\' - /\\\\/g, - () => ESCAPE - ], - - [ - // > The range notation, e.g. [a-zA-Z], - // > can be used to match one of the characters in a range. - - // `\` is escaped by step 3 - /(\\)?\[([^\]/]*?)(\\*)($|\])/g, - (match, leadEscape, range, endEscape, close) => leadEscape === ESCAPE - // '\\[bar]' -> '\\\\[bar\\]' - ? `\\[${range}${cleanRangeBackSlash(endEscape)}${close}` - : close === ']' - ? endEscape.length % 2 === 0 - // A normal case, and it is a range notation - // '[bar]' - // '[bar\\\\]' - ? `[${sanitizeRange(range)}${endEscape}]` - // Invalid range notaton - // '[bar\\]' -> '[bar\\\\]' - : '[]' - : '[]' - ], - - // ending - [ - // 'js' will not match 'js.' - // 'ab' will not match 'abc' - /(?:[^*])$/, - - // WTF! - // https://git-scm.com/docs/gitignore - // changes in [2.22.1](https://git-scm.com/docs/gitignore/2.22.1) - // which re-fixes #24, #38 - - // > If there is a separator at the end of the pattern then the pattern - // > will only match directories, otherwise the pattern can match both - // > files and directories. - - // 'js*' will not match 'a.js' - // 'js/' will not match 'a.js' - // 'js' will match 'a.js' and 'a.js/' - match => /\/$/.test(match) - // foo/ will not match 'foo' - ? `${match}$` - // foo matches 'foo' and 'foo/' - : `${match}(?=$|\\/$)` - ], - - // trailing wildcard - [ - /(\^|\\\/)?\\\*$/, - (_, p1) => { - const prefix = p1 - // '\^': - // '/*' does not match EMPTY - // '/*' does not match everything - - // '\\\/': - // 'abc/*' does not match 'abc/' - ? `${p1}[^/]+` - - // 'a*' matches 'a' - // 'a*' matches 'aa' - : '[^/]*' - - return `${prefix}(?=$|\\/$)` - } - ], -] - -// A simple cache, because an ignore rule only has only one certain meaning -const regexCache = Object.create(null) - -// @param {pattern} -const makeRegex = (pattern, negative, ignorecase) => { - const r = regexCache[pattern] - if (r) { - return r - } - - // const replacers = negative - // ? NEGATIVE_REPLACERS - // : POSITIVE_REPLACERS - - const source = REPLACERS.reduce( - (prev, current) => prev.replace(current[0], current[1].bind(pattern)), - pattern - ) - - return regexCache[pattern] = ignorecase - ? new RegExp(source, 'i') - : new RegExp(source) -} - -const isString = subject => typeof subject === 'string' - -// > A blank line matches no files, so it can serve as a separator for readability. -const checkPattern = pattern => pattern - && isString(pattern) - && !REGEX_TEST_BLANK_LINE.test(pattern) - - // > A line starting with # serves as a comment. - && pattern.indexOf('#') !== 0 - -const splitPattern = pattern => pattern.split(REGEX_SPLITALL_CRLF) - -class IgnoreRule { - constructor ( - origin, - pattern, - negative, - regex - ) { - this.origin = origin - this.pattern = pattern - this.negative = negative - this.regex = regex - } -} - -const createRule = (pattern, ignorecase) => { - const origin = pattern - let negative = false - - // > An optional prefix "!" which negates the pattern; - if (pattern.indexOf('!') === 0) { - negative = true - pattern = pattern.substr(1) - } - - pattern = pattern - // > Put a backslash ("\") in front of the first "!" for patterns that - // > begin with a literal "!", for example, `"\!important!.txt"`. - .replace(REGEX_REPLACE_LEADING_EXCAPED_EXCLAMATION, '!') - // > Put a backslash ("\") in front of the first hash for patterns that - // > begin with a hash. - .replace(REGEX_REPLACE_LEADING_EXCAPED_HASH, '#') - - const regex = makeRegex(pattern, negative, ignorecase) - - return new IgnoreRule( - origin, - pattern, - negative, - regex - ) -} - -const throwError = (message, Ctor) => { - throw new Ctor(message) -} - -const checkPath = (path, originalPath, doThrow) => { - if (!isString(path)) { - return doThrow( - `path must be a string, but got \`${originalPath}\``, - TypeError - ) - } - - // We don't know if we should ignore EMPTY, so throw - if (!path) { - return doThrow(`path must not be empty`, TypeError) - } - - // Check if it is a relative path - if (checkPath.isNotRelative(path)) { - const r = '`path.relative()`d' - return doThrow( - `path should be a ${r} string, but got "${originalPath}"`, - RangeError - ) - } - - return true -} - -const isNotRelative = path => REGEX_TEST_INVALID_PATH.test(path) - -checkPath.isNotRelative = isNotRelative -checkPath.convert = p => p - -class Ignore { - constructor ({ - ignorecase = true - } = {}) { - this._rules = [] - this._ignorecase = ignorecase - define(this, KEY_IGNORE, true) - this._initCache() - } - - _initCache () { - this._ignoreCache = Object.create(null) - this._testCache = Object.create(null) - } - - _addPattern (pattern) { - // #32 - if (pattern && pattern[KEY_IGNORE]) { - this._rules = this._rules.concat(pattern._rules) - this._added = true - return - } - - if (checkPattern(pattern)) { - const rule = createRule(pattern, this._ignorecase) - this._added = true - this._rules.push(rule) - } - } - - // @param {Array | string | Ignore} pattern - add (pattern) { - this._added = false - - makeArray( - isString(pattern) - ? splitPattern(pattern) - : pattern - ).forEach(this._addPattern, this) - - // Some rules have just added to the ignore, - // making the behavior changed. - if (this._added) { - this._initCache() - } - - return this - } - - // legacy - addPattern (pattern) { - return this.add(pattern) - } - - // | ignored : unignored - // negative | 0:0 | 0:1 | 1:0 | 1:1 - // -------- | ------- | ------- | ------- | -------- - // 0 | TEST | TEST | SKIP | X - // 1 | TESTIF | SKIP | TEST | X - - // - SKIP: always skip - // - TEST: always test - // - TESTIF: only test if checkUnignored - // - X: that never happen - - // @param {boolean} whether should check if the path is unignored, - // setting `checkUnignored` to `false` could reduce additional - // path matching. - - // @returns {TestResult} true if a file is ignored - _testOne (path, checkUnignored) { - let ignored = false - let unignored = false - - this._rules.forEach(rule => { - const {negative} = rule - if ( - unignored === negative && ignored !== unignored - || negative && !ignored && !unignored && !checkUnignored - ) { - return - } - - const matched = rule.regex.test(path) - - if (matched) { - ignored = !negative - unignored = negative - } - }) - - return { - ignored, - unignored - } - } - - // @returns {TestResult} - _test (originalPath, cache, checkUnignored, slices) { - const path = originalPath - // Supports nullable path - && checkPath.convert(originalPath) - - checkPath(path, originalPath, throwError) - - return this._t(path, cache, checkUnignored, slices) - } - - _t (path, cache, checkUnignored, slices) { - if (path in cache) { - return cache[path] - } - - if (!slices) { - // path/to/a.js - // ['path', 'to', 'a.js'] - slices = path.split(SLASH) - } - - slices.pop() - - // If the path has no parent directory, just test it - if (!slices.length) { - return cache[path] = this._testOne(path, checkUnignored) - } - - const parent = this._t( - slices.join(SLASH) + SLASH, - cache, - checkUnignored, - slices - ) - - // If the path contains a parent directory, check the parent first - return cache[path] = parent.ignored - // > It is not possible to re-include a file if a parent directory of - // > that file is excluded. - ? parent - : this._testOne(path, checkUnignored) - } - - ignores (path) { - return this._test(path, this._ignoreCache, false).ignored - } - - createFilter () { - return path => !this.ignores(path) - } - - filter (paths) { - return makeArray(paths).filter(this.createFilter()) - } - - // @returns {TestResult} - test (path) { - return this._test(path, this._testCache, true) - } -} - -const factory = options => new Ignore(options) - -const returnFalse = () => false - -const isPathValid = path => - checkPath(path && checkPath.convert(path), path, returnFalse) - -factory.isPathValid = isPathValid - -// Fixes typescript -factory.default = factory - -module.exports = factory - -// Windows -// -------------------------------------------------------------- -/* istanbul ignore if */ -if ( - // Detect `process` so that it can run in browsers. - typeof process !== 'undefined' - && ( - process.env && process.env.IGNORE_TEST_WIN32 - || process.platform === 'win32' - ) -) { - /* eslint no-control-regex: "off" */ - const makePosix = str => /^\\\\\?\\/.test(str) - || /["<>|\u0000-\u001F]+/u.test(str) - ? str - : str.replace(/\\/g, '/') - - checkPath.convert = makePosix - - // 'C:\\foo' <- 'C:\\foo' has been converted to 'C:/' - // 'd:\\foo' - const REGIX_IS_WINDOWS_PATH_ABSOLUTE = /^[a-z]:\//i - checkPath.isNotRelative = path => - REGIX_IS_WINDOWS_PATH_ABSOLUTE.test(path) - || isNotRelative(path) -} - - -/***/ }), - -/***/ "../../node_modules/imurmurhash/imurmurhash.js": -/***/ (function(module, exports, __webpack_require__) { - -/** - * @preserve - * JS Implementation of incremental MurmurHash3 (r150) (as of May 10, 2013) - * - * @author
    Jens Taylor - * @see http://github.com/homebrewing/brauhaus-diff - * @author Gary Court - * @see http://github.com/garycourt/murmurhash-js - * @author Austin Appleby - * @see http://sites.google.com/site/murmurhash/ - */ -(function(){ - var cache; - - // Call this function without `new` to use the cached object (good for - // single-threaded environments), or with `new` to create a new object. - // - // @param {string} key A UTF-16 or ASCII string - // @param {number} seed An optional positive integer - // @return {object} A MurmurHash3 object for incremental hashing - function MurmurHash3(key, seed) { - var m = this instanceof MurmurHash3 ? this : cache; - m.reset(seed) - if (typeof key === 'string' && key.length > 0) { - m.hash(key); - } - - if (m !== this) { - return m; - } - }; - - // Incrementally add a string to this hash - // - // @param {string} key A UTF-16 or ASCII string - // @return {object} this - MurmurHash3.prototype.hash = function(key) { - var h1, k1, i, top, len; - - len = key.length; - this.len += len; - - k1 = this.k1; - i = 0; - switch (this.rem) { - case 0: k1 ^= len > i ? (key.charCodeAt(i++) & 0xffff) : 0; - case 1: k1 ^= len > i ? (key.charCodeAt(i++) & 0xffff) << 8 : 0; - case 2: k1 ^= len > i ? (key.charCodeAt(i++) & 0xffff) << 16 : 0; - case 3: - k1 ^= len > i ? (key.charCodeAt(i) & 0xff) << 24 : 0; - k1 ^= len > i ? (key.charCodeAt(i++) & 0xff00) >> 8 : 0; - } - - this.rem = (len + this.rem) & 3; // & 3 is same as % 4 - len -= this.rem; - if (len > 0) { - h1 = this.h1; - while (1) { - k1 = (k1 * 0x2d51 + (k1 & 0xffff) * 0xcc9e0000) & 0xffffffff; - k1 = (k1 << 15) | (k1 >>> 17); - k1 = (k1 * 0x3593 + (k1 & 0xffff) * 0x1b870000) & 0xffffffff; - - h1 ^= k1; - h1 = (h1 << 13) | (h1 >>> 19); - h1 = (h1 * 5 + 0xe6546b64) & 0xffffffff; - - if (i >= len) { - break; - } - - k1 = ((key.charCodeAt(i++) & 0xffff)) ^ - ((key.charCodeAt(i++) & 0xffff) << 8) ^ - ((key.charCodeAt(i++) & 0xffff) << 16); - top = key.charCodeAt(i++); - k1 ^= ((top & 0xff) << 24) ^ - ((top & 0xff00) >> 8); - } - - k1 = 0; - switch (this.rem) { - case 3: k1 ^= (key.charCodeAt(i + 2) & 0xffff) << 16; - case 2: k1 ^= (key.charCodeAt(i + 1) & 0xffff) << 8; - case 1: k1 ^= (key.charCodeAt(i) & 0xffff); - } - - this.h1 = h1; - } - - this.k1 = k1; - return this; - }; - - // Get the result of this hash - // - // @return {number} The 32-bit hash - MurmurHash3.prototype.result = function() { - var k1, h1; - - k1 = this.k1; - h1 = this.h1; - - if (k1 > 0) { - k1 = (k1 * 0x2d51 + (k1 & 0xffff) * 0xcc9e0000) & 0xffffffff; - k1 = (k1 << 15) | (k1 >>> 17); - k1 = (k1 * 0x3593 + (k1 & 0xffff) * 0x1b870000) & 0xffffffff; - h1 ^= k1; - } - - h1 ^= this.len; - - h1 ^= h1 >>> 16; - h1 = (h1 * 0xca6b + (h1 & 0xffff) * 0x85eb0000) & 0xffffffff; - h1 ^= h1 >>> 13; - h1 = (h1 * 0xae35 + (h1 & 0xffff) * 0xc2b20000) & 0xffffffff; - h1 ^= h1 >>> 16; - - return h1 >>> 0; - }; - - // Reset the hash object for reuse - // - // @param {number} seed An optional positive integer - MurmurHash3.prototype.reset = function(seed) { - this.h1 = typeof seed === 'number' ? seed : 0; - this.rem = this.k1 = this.len = 0; - return this; - }; - - // A cached object to use. This can be safely used if you're in a single- - // threaded environment, otherwise you need to create new hashes to use. - cache = new MurmurHash3(); - - if (true) { - module.exports = MurmurHash3; - } else {} -}()); - - -/***/ }), - -/***/ "../../node_modules/inflight/inflight.js": -/***/ (function(module, exports, __webpack_require__) { - -var wrappy = __webpack_require__("../../node_modules/wrappy/wrappy.js") -var reqs = Object.create(null) -var once = __webpack_require__("../../node_modules/once/once.js") - -module.exports = wrappy(inflight) - -function inflight (key, cb) { - if (reqs[key]) { - reqs[key].push(cb) - return null - } else { - reqs[key] = [cb] - return makeres(key) - } -} - -function makeres (key) { - return once(function RES () { - var cbs = reqs[key] - var len = cbs.length - var args = slice(arguments) - - // XXX It's somewhat ambiguous whether a new callback added in this - // pass should be queued for later execution if something in the - // list of callbacks throws, or if it should just be discarded. - // However, it's such an edge case that it hardly matters, and either - // choice is likely as surprising as the other. - // As it happens, we do go ahead and schedule it for later execution. - try { - for (var i = 0; i < len; i++) { - cbs[i].apply(null, args) - } - } finally { - if (cbs.length > len) { - // added more in the interim. - // de-zalgo, just in case, but don't call again. - cbs.splice(0, len) - process.nextTick(function () { - RES.apply(null, args) - }) - } else { - delete reqs[key] - } - } - }) -} - -function slice (args) { - var length = args.length - var array = [] - - for (var i = 0; i < length; i++) array[i] = args[i] - return array -} - - -/***/ }), - -/***/ "../../node_modules/inherits/inherits.js": -/***/ (function(module, exports, __webpack_require__) { - -try { - var util = __webpack_require__("util"); - /* istanbul ignore next */ - if (typeof util.inherits !== 'function') throw ''; - module.exports = util.inherits; -} catch (e) { - /* istanbul ignore next */ - module.exports = __webpack_require__("../../node_modules/inherits/inherits_browser.js"); -} - - -/***/ }), - -/***/ "../../node_modules/inherits/inherits_browser.js": -/***/ (function(module, exports) { - -if (typeof Object.create === 'function') { - // implementation from standard node.js 'util' module - module.exports = function inherits(ctor, superCtor) { - if (superCtor) { - ctor.super_ = superCtor - ctor.prototype = Object.create(superCtor.prototype, { - constructor: { - value: ctor, - enumerable: false, - writable: true, - configurable: true - } - }) - } - }; -} else { - // old school shim for old browsers - module.exports = function inherits(ctor, superCtor) { - if (superCtor) { - ctor.super_ = superCtor - var TempCtor = function () {} - TempCtor.prototype = superCtor.prototype - ctor.prototype = new TempCtor() - ctor.prototype.constructor = ctor - } - } -} - - -/***/ }), - -/***/ "../../node_modules/is-arrayish/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = function isArrayish(obj) { - if (!obj) { - return false; - } - - return obj instanceof Array || Array.isArray(obj) || - (obj.length >= 0 && obj.splice instanceof Function); -}; - - -/***/ }), - -/***/ "../../node_modules/is-core-module/core.json": -/***/ (function(module) { - -module.exports = JSON.parse("{\"assert\":true,\"node:assert\":[\">= 14.18 && < 15\",\">= 16\"],\"assert/strict\":\">= 15\",\"node:assert/strict\":\">= 16\",\"async_hooks\":\">= 8\",\"node:async_hooks\":[\">= 14.18 && < 15\",\">= 16\"],\"buffer_ieee754\":\">= 0.5 && < 0.9.7\",\"buffer\":true,\"node:buffer\":[\">= 14.18 && < 15\",\">= 16\"],\"child_process\":true,\"node:child_process\":[\">= 14.18 && < 15\",\">= 16\"],\"cluster\":\">= 0.5\",\"node:cluster\":[\">= 14.18 && < 15\",\">= 16\"],\"console\":true,\"node:console\":[\">= 14.18 && < 15\",\">= 16\"],\"constants\":true,\"node:constants\":[\">= 14.18 && < 15\",\">= 16\"],\"crypto\":true,\"node:crypto\":[\">= 14.18 && < 15\",\">= 16\"],\"_debug_agent\":\">= 1 && < 8\",\"_debugger\":\"< 8\",\"dgram\":true,\"node:dgram\":[\">= 14.18 && < 15\",\">= 16\"],\"diagnostics_channel\":[\">= 14.17 && < 15\",\">= 15.1\"],\"node:diagnostics_channel\":[\">= 14.18 && < 15\",\">= 16\"],\"dns\":true,\"node:dns\":[\">= 14.18 && < 15\",\">= 16\"],\"dns/promises\":\">= 15\",\"node:dns/promises\":\">= 16\",\"domain\":\">= 0.7.12\",\"node:domain\":[\">= 14.18 && < 15\",\">= 16\"],\"events\":true,\"node:events\":[\">= 14.18 && < 15\",\">= 16\"],\"freelist\":\"< 6\",\"fs\":true,\"node:fs\":[\">= 14.18 && < 15\",\">= 16\"],\"fs/promises\":[\">= 10 && < 10.1\",\">= 14\"],\"node:fs/promises\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_agent\":\">= 0.11.1\",\"node:_http_agent\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_client\":\">= 0.11.1\",\"node:_http_client\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_common\":\">= 0.11.1\",\"node:_http_common\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_incoming\":\">= 0.11.1\",\"node:_http_incoming\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_outgoing\":\">= 0.11.1\",\"node:_http_outgoing\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_server\":\">= 0.11.1\",\"node:_http_server\":[\">= 14.18 && < 15\",\">= 16\"],\"http\":true,\"node:http\":[\">= 14.18 && < 15\",\">= 16\"],\"http2\":\">= 8.8\",\"node:http2\":[\">= 14.18 && < 15\",\">= 16\"],\"https\":true,\"node:https\":[\">= 14.18 && < 15\",\">= 16\"],\"inspector\":\">= 8\",\"node:inspector\":[\">= 14.18 && < 15\",\">= 16\"],\"_linklist\":\"< 8\",\"module\":true,\"node:module\":[\">= 14.18 && < 15\",\">= 16\"],\"net\":true,\"node:net\":[\">= 14.18 && < 15\",\">= 16\"],\"node-inspect/lib/_inspect\":\">= 7.6 && < 12\",\"node-inspect/lib/internal/inspect_client\":\">= 7.6 && < 12\",\"node-inspect/lib/internal/inspect_repl\":\">= 7.6 && < 12\",\"os\":true,\"node:os\":[\">= 14.18 && < 15\",\">= 16\"],\"path\":true,\"node:path\":[\">= 14.18 && < 15\",\">= 16\"],\"path/posix\":\">= 15.3\",\"node:path/posix\":\">= 16\",\"path/win32\":\">= 15.3\",\"node:path/win32\":\">= 16\",\"perf_hooks\":\">= 8.5\",\"node:perf_hooks\":[\">= 14.18 && < 15\",\">= 16\"],\"process\":\">= 1\",\"node:process\":[\">= 14.18 && < 15\",\">= 16\"],\"punycode\":\">= 0.5\",\"node:punycode\":[\">= 14.18 && < 15\",\">= 16\"],\"querystring\":true,\"node:querystring\":[\">= 14.18 && < 15\",\">= 16\"],\"readline\":true,\"node:readline\":[\">= 14.18 && < 15\",\">= 16\"],\"readline/promises\":\">= 17\",\"node:readline/promises\":\">= 17\",\"repl\":true,\"node:repl\":[\">= 14.18 && < 15\",\">= 16\"],\"smalloc\":\">= 0.11.5 && < 3\",\"_stream_duplex\":\">= 0.9.4\",\"node:_stream_duplex\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_transform\":\">= 0.9.4\",\"node:_stream_transform\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_wrap\":\">= 1.4.1\",\"node:_stream_wrap\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_passthrough\":\">= 0.9.4\",\"node:_stream_passthrough\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_readable\":\">= 0.9.4\",\"node:_stream_readable\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_writable\":\">= 0.9.4\",\"node:_stream_writable\":[\">= 14.18 && < 15\",\">= 16\"],\"stream\":true,\"node:stream\":[\">= 14.18 && < 15\",\">= 16\"],\"stream/consumers\":\">= 16.7\",\"node:stream/consumers\":\">= 16.7\",\"stream/promises\":\">= 15\",\"node:stream/promises\":\">= 16\",\"stream/web\":\">= 16.5\",\"node:stream/web\":\">= 16.5\",\"string_decoder\":true,\"node:string_decoder\":[\">= 14.18 && < 15\",\">= 16\"],\"sys\":[\">= 0.4 && < 0.7\",\">= 0.8\"],\"node:sys\":[\">= 14.18 && < 15\",\">= 16\"],\"timers\":true,\"node:timers\":[\">= 14.18 && < 15\",\">= 16\"],\"timers/promises\":\">= 15\",\"node:timers/promises\":\">= 16\",\"_tls_common\":\">= 0.11.13\",\"node:_tls_common\":[\">= 14.18 && < 15\",\">= 16\"],\"_tls_legacy\":\">= 0.11.3 && < 10\",\"_tls_wrap\":\">= 0.11.3\",\"node:_tls_wrap\":[\">= 14.18 && < 15\",\">= 16\"],\"tls\":true,\"node:tls\":[\">= 14.18 && < 15\",\">= 16\"],\"trace_events\":\">= 10\",\"node:trace_events\":[\">= 14.18 && < 15\",\">= 16\"],\"tty\":true,\"node:tty\":[\">= 14.18 && < 15\",\">= 16\"],\"url\":true,\"node:url\":[\">= 14.18 && < 15\",\">= 16\"],\"util\":true,\"node:util\":[\">= 14.18 && < 15\",\">= 16\"],\"util/types\":\">= 15.3\",\"node:util/types\":\">= 16\",\"v8/tools/arguments\":\">= 10 && < 12\",\"v8/tools/codemap\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/consarray\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/csvparser\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/logreader\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/profile_view\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/splaytree\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8\":\">= 1\",\"node:v8\":[\">= 14.18 && < 15\",\">= 16\"],\"vm\":true,\"node:vm\":[\">= 14.18 && < 15\",\">= 16\"],\"wasi\":\">= 13.4 && < 13.5\",\"worker_threads\":\">= 11.7\",\"node:worker_threads\":[\">= 14.18 && < 15\",\">= 16\"],\"zlib\":\">= 0.5\",\"node:zlib\":[\">= 14.18 && < 15\",\">= 16\"]}"); - -/***/ }), - -/***/ "../../node_modules/is-core-module/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var has = __webpack_require__("../../node_modules/has/src/index.js"); - -function specifierIncluded(current, specifier) { - var nodeParts = current.split('.'); - var parts = specifier.split(' '); - var op = parts.length > 1 ? parts[0] : '='; - var versionParts = (parts.length > 1 ? parts[1] : parts[0]).split('.'); - - for (var i = 0; i < 3; ++i) { - var cur = parseInt(nodeParts[i] || 0, 10); - var ver = parseInt(versionParts[i] || 0, 10); - if (cur === ver) { - continue; // eslint-disable-line no-restricted-syntax, no-continue - } - if (op === '<') { - return cur < ver; - } - if (op === '>=') { - return cur >= ver; - } - return false; - } - return op === '>='; -} - -function matchesRange(current, range) { - var specifiers = range.split(/ ?&& ?/); - if (specifiers.length === 0) { - return false; - } - for (var i = 0; i < specifiers.length; ++i) { - if (!specifierIncluded(current, specifiers[i])) { - return false; - } - } - return true; -} - -function versionIncluded(nodeVersion, specifierValue) { - if (typeof specifierValue === 'boolean') { - return specifierValue; - } - - var current = typeof nodeVersion === 'undefined' - ? process.versions && process.versions.node - : nodeVersion; - - if (typeof current !== 'string') { - throw new TypeError(typeof nodeVersion === 'undefined' ? 'Unable to determine current node version' : 'If provided, a valid node version is required'); - } - - if (specifierValue && typeof specifierValue === 'object') { - for (var i = 0; i < specifierValue.length; ++i) { - if (matchesRange(current, specifierValue[i])) { - return true; - } - } - return false; - } - return matchesRange(current, specifierValue); -} - -var data = __webpack_require__("../../node_modules/is-core-module/core.json"); - -module.exports = function isCore(x, nodeVersion) { - return has(data, x) && versionIncluded(nodeVersion, data[x]); -}; - - -/***/ }), - -/***/ "../../node_modules/is-extglob/index.js": -/***/ (function(module, exports) { - -/*! - * is-extglob - * - * Copyright (c) 2014-2016, Jon Schlinkert. - * Licensed under the MIT License. - */ - -module.exports = function isExtglob(str) { - if (typeof str !== 'string' || str === '') { - return false; - } - - var match; - while ((match = /(\\).|([@?!+*]\(.*\))/g.exec(str))) { - if (match[2]) return true; - str = str.slice(match.index + match[0].length); - } - - return false; -}; - - -/***/ }), - -/***/ "../../node_modules/is-glob/index.js": -/***/ (function(module, exports, __webpack_require__) { - -/*! - * is-glob - * - * Copyright (c) 2014-2017, Jon Schlinkert. - * Released under the MIT License. - */ - -var isExtglob = __webpack_require__("../../node_modules/is-extglob/index.js"); -var chars = { '{': '}', '(': ')', '[': ']'}; -var strictCheck = function(str) { - if (str[0] === '!') { - return true; - } - var index = 0; - var pipeIndex = -2; - var closeSquareIndex = -2; - var closeCurlyIndex = -2; - var closeParenIndex = -2; - var backSlashIndex = -2; - while (index < str.length) { - if (str[index] === '*') { - return true; - } - - if (str[index + 1] === '?' && /[\].+)]/.test(str[index])) { - return true; - } - - if (closeSquareIndex !== -1 && str[index] === '[' && str[index + 1] !== ']') { - if (closeSquareIndex < index) { - closeSquareIndex = str.indexOf(']', index); - } - if (closeSquareIndex > index) { - if (backSlashIndex === -1 || backSlashIndex > closeSquareIndex) { - return true; - } - backSlashIndex = str.indexOf('\\', index); - if (backSlashIndex === -1 || backSlashIndex > closeSquareIndex) { - return true; - } - } - } - - if (closeCurlyIndex !== -1 && str[index] === '{' && str[index + 1] !== '}') { - closeCurlyIndex = str.indexOf('}', index); - if (closeCurlyIndex > index) { - backSlashIndex = str.indexOf('\\', index); - if (backSlashIndex === -1 || backSlashIndex > closeCurlyIndex) { - return true; - } - } - } - - if (closeParenIndex !== -1 && str[index] === '(' && str[index + 1] === '?' && /[:!=]/.test(str[index + 2]) && str[index + 3] !== ')') { - closeParenIndex = str.indexOf(')', index); - if (closeParenIndex > index) { - backSlashIndex = str.indexOf('\\', index); - if (backSlashIndex === -1 || backSlashIndex > closeParenIndex) { - return true; - } - } - } - - if (pipeIndex !== -1 && str[index] === '(' && str[index + 1] !== '|') { - if (pipeIndex < index) { - pipeIndex = str.indexOf('|', index); - } - if (pipeIndex !== -1 && str[pipeIndex + 1] !== ')') { - closeParenIndex = str.indexOf(')', pipeIndex); - if (closeParenIndex > pipeIndex) { - backSlashIndex = str.indexOf('\\', pipeIndex); - if (backSlashIndex === -1 || backSlashIndex > closeParenIndex) { - return true; - } - } - } - } - - if (str[index] === '\\') { - var open = str[index + 1]; - index += 2; - var close = chars[open]; - - if (close) { - var n = str.indexOf(close, index); - if (n !== -1) { - index = n + 1; - } - } - - if (str[index] === '!') { - return true; - } - } else { - index++; - } - } - return false; -}; - -var relaxedCheck = function(str) { - if (str[0] === '!') { - return true; - } - var index = 0; - while (index < str.length) { - if (/[*?{}()[\]]/.test(str[index])) { - return true; - } - - if (str[index] === '\\') { - var open = str[index + 1]; - index += 2; - var close = chars[open]; - - if (close) { - var n = str.indexOf(close, index); - if (n !== -1) { - index = n + 1; - } - } - - if (str[index] === '!') { - return true; - } - } else { - index++; - } - } - return false; -}; - -module.exports = function isGlob(str, options) { - if (typeof str !== 'string' || str === '') { - return false; - } - - if (isExtglob(str)) { - return true; - } - - var check = strictCheck; - - // optionally relax check - if (options && options.strict === false) { - check = relaxedCheck; - } - - return check(str); -}; - - -/***/ }), - -/***/ "../../node_modules/is-interactive/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = ({stream = process.stdout} = {}) => { - return Boolean( - stream && stream.isTTY && - process.env.TERM !== 'dumb' && - !('CI' in process.env) - ); -}; - - -/***/ }), - -/***/ "../../node_modules/is-path-cwd/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); - -module.exports = path_ => { - let cwd = process.cwd(); - - path_ = path.resolve(path_); - - if (process.platform === 'win32') { - cwd = cwd.toLowerCase(); - path_ = path_.toLowerCase(); - } - - return path_ === cwd; -}; - - -/***/ }), - -/***/ "../../node_modules/is-path-inside/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); - -module.exports = (childPath, parentPath) => { - childPath = path.resolve(childPath); - parentPath = path.resolve(parentPath); - - if (process.platform === 'win32') { - childPath = childPath.toLowerCase(); - parentPath = parentPath.toLowerCase(); - } - - if (childPath === parentPath) { - return false; - } - - childPath += path.sep; - parentPath += path.sep; - - return childPath.startsWith(parentPath); -}; - - -/***/ }), - -/***/ "../../node_modules/is-plain-obj/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = value => { - if (Object.prototype.toString.call(value) !== '[object Object]') { - return false; - } - - const prototype = Object.getPrototypeOf(value); - return prototype === null || prototype === Object.prototype; -}; - - -/***/ }), - -/***/ "../../node_modules/is-stream/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const isStream = stream => - stream !== null && - typeof stream === 'object' && - typeof stream.pipe === 'function'; - -isStream.writable = stream => - isStream(stream) && - stream.writable !== false && - typeof stream._write === 'function' && - typeof stream._writableState === 'object'; - -isStream.readable = stream => - isStream(stream) && - stream.readable !== false && - typeof stream._read === 'function' && - typeof stream._readableState === 'object'; - -isStream.duplex = stream => - isStream.writable(stream) && - isStream.readable(stream); - -isStream.transform = stream => - isStream.duplex(stream) && - typeof stream._transform === 'function' && - typeof stream._transformState === 'object'; - -module.exports = isStream; - - -/***/ }), - -/***/ "../../node_modules/isexe/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var fs = __webpack_require__("fs") -var core -if (process.platform === 'win32' || global.TESTING_WINDOWS) { - core = __webpack_require__("../../node_modules/isexe/windows.js") -} else { - core = __webpack_require__("../../node_modules/isexe/mode.js") -} - -module.exports = isexe -isexe.sync = sync - -function isexe (path, options, cb) { - if (typeof options === 'function') { - cb = options - options = {} - } - - if (!cb) { - if (typeof Promise !== 'function') { - throw new TypeError('callback not provided') - } - - return new Promise(function (resolve, reject) { - isexe(path, options || {}, function (er, is) { - if (er) { - reject(er) - } else { - resolve(is) - } - }) - }) - } - - core(path, options || {}, function (er, is) { - // ignore EACCES because that just means we aren't allowed to run it - if (er) { - if (er.code === 'EACCES' || options && options.ignoreErrors) { - er = null - is = false - } - } - cb(er, is) - }) -} - -function sync (path, options) { - // my kingdom for a filtered catch - try { - return core.sync(path, options || {}) - } catch (er) { - if (options && options.ignoreErrors || er.code === 'EACCES') { - return false - } else { - throw er - } - } -} - - -/***/ }), - -/***/ "../../node_modules/isexe/mode.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = isexe -isexe.sync = sync - -var fs = __webpack_require__("fs") - -function isexe (path, options, cb) { - fs.stat(path, function (er, stat) { - cb(er, er ? false : checkStat(stat, options)) - }) -} - -function sync (path, options) { - return checkStat(fs.statSync(path), options) -} - -function checkStat (stat, options) { - return stat.isFile() && checkMode(stat, options) -} - -function checkMode (stat, options) { - var mod = stat.mode - var uid = stat.uid - var gid = stat.gid - - var myUid = options.uid !== undefined ? - options.uid : process.getuid && process.getuid() - var myGid = options.gid !== undefined ? - options.gid : process.getgid && process.getgid() - - var u = parseInt('100', 8) - var g = parseInt('010', 8) - var o = parseInt('001', 8) - var ug = u | g - - var ret = (mod & o) || - (mod & g) && gid === myGid || - (mod & u) && uid === myUid || - (mod & ug) && myUid === 0 - - return ret -} - - -/***/ }), - -/***/ "../../node_modules/isexe/windows.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = isexe -isexe.sync = sync - -var fs = __webpack_require__("fs") - -function checkPathExt (path, options) { - var pathext = options.pathExt !== undefined ? - options.pathExt : process.env.PATHEXT - - if (!pathext) { - return true - } - - pathext = pathext.split(';') - if (pathext.indexOf('') !== -1) { - return true - } - for (var i = 0; i < pathext.length; i++) { - var p = pathext[i].toLowerCase() - if (p && path.substr(-p.length).toLowerCase() === p) { - return true - } - } - return false -} - -function checkStat (stat, path, options) { - if (!stat.isSymbolicLink() && !stat.isFile()) { - return false - } - return checkPathExt(path, options) -} - -function isexe (path, options, cb) { - fs.stat(path, function (er, stat) { - cb(er, er ? false : checkStat(stat, path, options)) - }) -} - -function sync (path, options) { - return checkStat(fs.statSync(path), path, options) -} - - -/***/ }), - -/***/ "../../node_modules/json-parse-better-errors/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = parseJson -function parseJson (txt, reviver, context) { - context = context || 20 - try { - return JSON.parse(txt, reviver) - } catch (e) { - if (typeof txt !== 'string') { - const isEmptyArray = Array.isArray(txt) && txt.length === 0 - const errorMessage = 'Cannot parse ' + - (isEmptyArray ? 'an empty array' : String(txt)) - throw new TypeError(errorMessage) - } - const syntaxErr = e.message.match(/^Unexpected token.*position\s+(\d+)/i) - const errIdx = syntaxErr - ? +syntaxErr[1] - : e.message.match(/^Unexpected end of JSON.*/i) - ? txt.length - 1 - : null - if (errIdx != null) { - const start = errIdx <= context - ? 0 - : errIdx - context - const end = errIdx + context >= txt.length - ? txt.length - : errIdx + context - e.message += ` while parsing near '${ - start === 0 ? '' : '...' - }${txt.slice(start, end)}${ - end === txt.length ? '' : '...' - }'` - } else { - e.message += ` while parsing '${txt.slice(0, context * 2)}'` - } - throw e - } -} - - -/***/ }), - -/***/ "../../node_modules/lines-and-columns/dist/index.mjs": -/***/ (function(__webpack_module__, __webpack_exports__, __webpack_require__) { - -"use strict"; -__webpack_require__.r(__webpack_exports__); -var LF = '\n'; -var CR = '\r'; -var LinesAndColumns = (function () { - function LinesAndColumns(string) { - this.string = string; - var offsets = [0]; - for (var offset = 0; offset < string.length;) { - switch (string[offset]) { - case LF: - offset += LF.length; - offsets.push(offset); - break; - case CR: - offset += CR.length; - if (string[offset] === LF) { - offset += LF.length; - } - offsets.push(offset); - break; - default: - offset++; - break; - } - } - this.offsets = offsets; - } - LinesAndColumns.prototype.locationForIndex = function (index) { - if (index < 0 || index > this.string.length) { - return null; - } - var line = 0; - var offsets = this.offsets; - while (offsets[line + 1] <= index) { - line++; - } - var column = index - offsets[line]; - return { line: line, column: column }; - }; - LinesAndColumns.prototype.indexForLocation = function (location) { - var line = location.line, column = location.column; - if (line < 0 || line >= this.offsets.length) { - return null; - } - if (column < 0 || column > this.lengthOfLine(line)) { - return null; - } - return this.offsets[line] + column; - }; - LinesAndColumns.prototype.lengthOfLine = function (line) { - var offset = this.offsets[line]; - var nextOffset = line === this.offsets.length - 1 ? this.string.length : this.offsets[line + 1]; - return nextOffset - offset; - }; - return LinesAndColumns; -}()); -/* harmony default export */ __webpack_exports__["default"] = (LinesAndColumns); - - -/***/ }), - -/***/ "../../node_modules/load-json-file/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); -const {promisify} = __webpack_require__("util"); -const fs = __webpack_require__("../../node_modules/graceful-fs/graceful-fs.js"); -const stripBom = __webpack_require__("../../node_modules/strip-bom/index.js"); -const parseJson = __webpack_require__("../../node_modules/parse-json/index.js"); - -const parse = (data, filePath, options = {}) => { - data = stripBom(data); - - if (typeof options.beforeParse === 'function') { - data = options.beforeParse(data); - } - - return parseJson(data, options.reviver, path.relative(process.cwd(), filePath)); -}; - -module.exports = async (filePath, options) => parse(await promisify(fs.readFile)(filePath, 'utf8'), filePath, options); -module.exports.sync = (filePath, options) => parse(fs.readFileSync(filePath, 'utf8'), filePath, options); - - -/***/ }), - -/***/ "../../node_modules/merge-stream/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const { PassThrough } = __webpack_require__("stream"); - -module.exports = function (/*streams...*/) { - var sources = [] - var output = new PassThrough({objectMode: true}) - - output.setMaxListeners(0) - - output.add = add - output.isEmpty = isEmpty - - output.on('unpipe', remove) - - Array.prototype.slice.call(arguments).forEach(add) - - return output - - function add (source) { - if (Array.isArray(source)) { - source.forEach(add) - return this - } - - sources.push(source); - source.once('end', remove.bind(null, source)) - source.once('error', output.emit.bind(output, 'error')) - source.pipe(output, {end: false}) - return this - } - - function isEmpty () { - return sources.length == 0; - } - - function remove (source) { - sources = sources.filter(function (it) { return it !== source }) - if (!sources.length && output.readable) { output.end() } - } -} - - -/***/ }), - -/***/ "../../node_modules/merge2/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -/* - * merge2 - * https://github.com/teambition/merge2 - * - * Copyright (c) 2014-2020 Teambition - * Licensed under the MIT license. - */ -const Stream = __webpack_require__("stream") -const PassThrough = Stream.PassThrough -const slice = Array.prototype.slice - -module.exports = merge2 - -function merge2 () { - const streamsQueue = [] - const args = slice.call(arguments) - let merging = false - let options = args[args.length - 1] - - if (options && !Array.isArray(options) && options.pipe == null) { - args.pop() - } else { - options = {} - } - - const doEnd = options.end !== false - const doPipeError = options.pipeError === true - if (options.objectMode == null) { - options.objectMode = true - } - if (options.highWaterMark == null) { - options.highWaterMark = 64 * 1024 - } - const mergedStream = PassThrough(options) - - function addStream () { - for (let i = 0, len = arguments.length; i < len; i++) { - streamsQueue.push(pauseStreams(arguments[i], options)) - } - mergeStream() - return this - } - - function mergeStream () { - if (merging) { - return - } - merging = true - - let streams = streamsQueue.shift() - if (!streams) { - process.nextTick(endStream) - return - } - if (!Array.isArray(streams)) { - streams = [streams] - } - - let pipesCount = streams.length + 1 - - function next () { - if (--pipesCount > 0) { - return - } - merging = false - mergeStream() - } - - function pipe (stream) { - function onend () { - stream.removeListener('merge2UnpipeEnd', onend) - stream.removeListener('end', onend) - if (doPipeError) { - stream.removeListener('error', onerror) - } - next() - } - function onerror (err) { - mergedStream.emit('error', err) - } - // skip ended stream - if (stream._readableState.endEmitted) { - return next() - } - - stream.on('merge2UnpipeEnd', onend) - stream.on('end', onend) - - if (doPipeError) { - stream.on('error', onerror) - } - - stream.pipe(mergedStream, { end: false }) - // compatible for old stream - stream.resume() - } - - for (let i = 0; i < streams.length; i++) { - pipe(streams[i]) - } - - next() - } - - function endStream () { - merging = false - // emit 'queueDrain' when all streams merged. - mergedStream.emit('queueDrain') - if (doEnd) { - mergedStream.end() - } - } - - mergedStream.setMaxListeners(0) - mergedStream.add = addStream - mergedStream.on('unpipe', function (stream) { - stream.emit('merge2UnpipeEnd') - }) - - if (args.length) { - addStream.apply(null, args) - } - return mergedStream -} - -// check and pause streams for pipe. -function pauseStreams (streams, options) { - if (!Array.isArray(streams)) { - // Backwards-compat with old-style streams - if (!streams._readableState && streams.pipe) { - streams = streams.pipe(PassThrough(options)) - } - if (!streams._readableState || !streams.pause || !streams.pipe) { - throw new Error('Only readable stream can be merged.') - } - streams.pause() - } else { - for (let i = 0, len = streams.length; i < len; i++) { - streams[i] = pauseStreams(streams[i], options) - } - } - return streams -} - - -/***/ }), - -/***/ "../../node_modules/mime-db/db.json": -/***/ (function(module) { - -module.exports = JSON.parse("{\"application/1d-interleaved-parityfec\":{\"source\":\"iana\"},\"application/3gpdash-qoe-report+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/3gpp-ims+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/a2l\":{\"source\":\"iana\"},\"application/activemessage\":{\"source\":\"iana\"},\"application/activity+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-costmap+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-costmapfilter+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-directory+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-endpointcost+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-endpointcostparams+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-endpointprop+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-endpointpropparams+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-error+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-networkmap+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-networkmapfilter+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-updatestreamcontrol+json\":{\"source\":\"iana\",\"compressible\":true},\"application/alto-updatestreamparams+json\":{\"source\":\"iana\",\"compressible\":true},\"application/aml\":{\"source\":\"iana\"},\"application/andrew-inset\":{\"source\":\"iana\",\"extensions\":[\"ez\"]},\"application/applefile\":{\"source\":\"iana\"},\"application/applixware\":{\"source\":\"apache\",\"extensions\":[\"aw\"]},\"application/atf\":{\"source\":\"iana\"},\"application/atfx\":{\"source\":\"iana\"},\"application/atom+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"atom\"]},\"application/atomcat+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"atomcat\"]},\"application/atomdeleted+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"atomdeleted\"]},\"application/atomicmail\":{\"source\":\"iana\"},\"application/atomsvc+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"atomsvc\"]},\"application/atsc-dwd+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"dwd\"]},\"application/atsc-dynamic-event-message\":{\"source\":\"iana\"},\"application/atsc-held+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"held\"]},\"application/atsc-rdt+json\":{\"source\":\"iana\",\"compressible\":true},\"application/atsc-rsat+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rsat\"]},\"application/atxml\":{\"source\":\"iana\"},\"application/auth-policy+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/bacnet-xdd+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/batch-smtp\":{\"source\":\"iana\"},\"application/bdoc\":{\"compressible\":false,\"extensions\":[\"bdoc\"]},\"application/beep+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/calendar+json\":{\"source\":\"iana\",\"compressible\":true},\"application/calendar+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xcs\"]},\"application/call-completion\":{\"source\":\"iana\"},\"application/cals-1840\":{\"source\":\"iana\"},\"application/cap+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/cbor\":{\"source\":\"iana\"},\"application/cbor-seq\":{\"source\":\"iana\"},\"application/cccex\":{\"source\":\"iana\"},\"application/ccmp+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/ccxml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ccxml\"]},\"application/cdfx+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"cdfx\"]},\"application/cdmi-capability\":{\"source\":\"iana\",\"extensions\":[\"cdmia\"]},\"application/cdmi-container\":{\"source\":\"iana\",\"extensions\":[\"cdmic\"]},\"application/cdmi-domain\":{\"source\":\"iana\",\"extensions\":[\"cdmid\"]},\"application/cdmi-object\":{\"source\":\"iana\",\"extensions\":[\"cdmio\"]},\"application/cdmi-queue\":{\"source\":\"iana\",\"extensions\":[\"cdmiq\"]},\"application/cdni\":{\"source\":\"iana\"},\"application/cea\":{\"source\":\"iana\"},\"application/cea-2018+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/cellml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/cfw\":{\"source\":\"iana\"},\"application/clue+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/clue_info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/cms\":{\"source\":\"iana\"},\"application/cnrp+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/coap-group+json\":{\"source\":\"iana\",\"compressible\":true},\"application/coap-payload\":{\"source\":\"iana\"},\"application/commonground\":{\"source\":\"iana\"},\"application/conference-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/cose\":{\"source\":\"iana\"},\"application/cose-key\":{\"source\":\"iana\"},\"application/cose-key-set\":{\"source\":\"iana\"},\"application/cpl+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/csrattrs\":{\"source\":\"iana\"},\"application/csta+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/cstadata+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/csvm+json\":{\"source\":\"iana\",\"compressible\":true},\"application/cu-seeme\":{\"source\":\"apache\",\"extensions\":[\"cu\"]},\"application/cwt\":{\"source\":\"iana\"},\"application/cybercash\":{\"source\":\"iana\"},\"application/dart\":{\"compressible\":true},\"application/dash+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mpd\"]},\"application/dashdelta\":{\"source\":\"iana\"},\"application/davmount+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"davmount\"]},\"application/dca-rft\":{\"source\":\"iana\"},\"application/dcd\":{\"source\":\"iana\"},\"application/dec-dx\":{\"source\":\"iana\"},\"application/dialog-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/dicom\":{\"source\":\"iana\"},\"application/dicom+json\":{\"source\":\"iana\",\"compressible\":true},\"application/dicom+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/dii\":{\"source\":\"iana\"},\"application/dit\":{\"source\":\"iana\"},\"application/dns\":{\"source\":\"iana\"},\"application/dns+json\":{\"source\":\"iana\",\"compressible\":true},\"application/dns-message\":{\"source\":\"iana\"},\"application/docbook+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"dbk\"]},\"application/dots+cbor\":{\"source\":\"iana\"},\"application/dskpp+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/dssc+der\":{\"source\":\"iana\",\"extensions\":[\"dssc\"]},\"application/dssc+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xdssc\"]},\"application/dvcs\":{\"source\":\"iana\"},\"application/ecmascript\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ecma\",\"es\"]},\"application/edi-consent\":{\"source\":\"iana\"},\"application/edi-x12\":{\"source\":\"iana\",\"compressible\":false},\"application/edifact\":{\"source\":\"iana\",\"compressible\":false},\"application/efi\":{\"source\":\"iana\"},\"application/emergencycalldata.comment+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/emergencycalldata.control+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/emergencycalldata.deviceinfo+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/emergencycalldata.ecall.msd\":{\"source\":\"iana\"},\"application/emergencycalldata.providerinfo+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/emergencycalldata.serviceinfo+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/emergencycalldata.subscriberinfo+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/emergencycalldata.veds+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/emma+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"emma\"]},\"application/emotionml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"emotionml\"]},\"application/encaprtp\":{\"source\":\"iana\"},\"application/epp+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/epub+zip\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"epub\"]},\"application/eshop\":{\"source\":\"iana\"},\"application/exi\":{\"source\":\"iana\",\"extensions\":[\"exi\"]},\"application/expect-ct-report+json\":{\"source\":\"iana\",\"compressible\":true},\"application/fastinfoset\":{\"source\":\"iana\"},\"application/fastsoap\":{\"source\":\"iana\"},\"application/fdt+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"fdt\"]},\"application/fhir+json\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/fhir+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/fido.trusted-apps+json\":{\"compressible\":true},\"application/fits\":{\"source\":\"iana\"},\"application/flexfec\":{\"source\":\"iana\"},\"application/font-sfnt\":{\"source\":\"iana\"},\"application/font-tdpfr\":{\"source\":\"iana\",\"extensions\":[\"pfr\"]},\"application/font-woff\":{\"source\":\"iana\",\"compressible\":false},\"application/framework-attributes+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/geo+json\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"geojson\"]},\"application/geo+json-seq\":{\"source\":\"iana\"},\"application/geopackage+sqlite3\":{\"source\":\"iana\"},\"application/geoxacml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/gltf-buffer\":{\"source\":\"iana\"},\"application/gml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"gml\"]},\"application/gpx+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"gpx\"]},\"application/gxf\":{\"source\":\"apache\",\"extensions\":[\"gxf\"]},\"application/gzip\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"gz\"]},\"application/h224\":{\"source\":\"iana\"},\"application/held+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/hjson\":{\"extensions\":[\"hjson\"]},\"application/http\":{\"source\":\"iana\"},\"application/hyperstudio\":{\"source\":\"iana\",\"extensions\":[\"stk\"]},\"application/ibe-key-request+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/ibe-pkg-reply+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/ibe-pp-data\":{\"source\":\"iana\"},\"application/iges\":{\"source\":\"iana\"},\"application/im-iscomposing+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/index\":{\"source\":\"iana\"},\"application/index.cmd\":{\"source\":\"iana\"},\"application/index.obj\":{\"source\":\"iana\"},\"application/index.response\":{\"source\":\"iana\"},\"application/index.vnd\":{\"source\":\"iana\"},\"application/inkml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ink\",\"inkml\"]},\"application/iotp\":{\"source\":\"iana\"},\"application/ipfix\":{\"source\":\"iana\",\"extensions\":[\"ipfix\"]},\"application/ipp\":{\"source\":\"iana\"},\"application/isup\":{\"source\":\"iana\"},\"application/its+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"its\"]},\"application/java-archive\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"jar\",\"war\",\"ear\"]},\"application/java-serialized-object\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"ser\"]},\"application/java-vm\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"class\"]},\"application/javascript\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"js\",\"mjs\"]},\"application/jf2feed+json\":{\"source\":\"iana\",\"compressible\":true},\"application/jose\":{\"source\":\"iana\"},\"application/jose+json\":{\"source\":\"iana\",\"compressible\":true},\"application/jrd+json\":{\"source\":\"iana\",\"compressible\":true},\"application/json\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"json\",\"map\"]},\"application/json-patch+json\":{\"source\":\"iana\",\"compressible\":true},\"application/json-seq\":{\"source\":\"iana\"},\"application/json5\":{\"extensions\":[\"json5\"]},\"application/jsonml+json\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"jsonml\"]},\"application/jwk+json\":{\"source\":\"iana\",\"compressible\":true},\"application/jwk-set+json\":{\"source\":\"iana\",\"compressible\":true},\"application/jwt\":{\"source\":\"iana\"},\"application/kpml-request+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/kpml-response+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/ld+json\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"jsonld\"]},\"application/lgr+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"lgr\"]},\"application/link-format\":{\"source\":\"iana\"},\"application/load-control+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/lost+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"lostxml\"]},\"application/lostsync+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/lpf+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/lxf\":{\"source\":\"iana\"},\"application/mac-binhex40\":{\"source\":\"iana\",\"extensions\":[\"hqx\"]},\"application/mac-compactpro\":{\"source\":\"apache\",\"extensions\":[\"cpt\"]},\"application/macwriteii\":{\"source\":\"iana\"},\"application/mads+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mads\"]},\"application/manifest+json\":{\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"webmanifest\"]},\"application/marc\":{\"source\":\"iana\",\"extensions\":[\"mrc\"]},\"application/marcxml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mrcx\"]},\"application/mathematica\":{\"source\":\"iana\",\"extensions\":[\"ma\",\"nb\",\"mb\"]},\"application/mathml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mathml\"]},\"application/mathml-content+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mathml-presentation+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-associated-procedure-description+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-deregister+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-envelope+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-msk+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-msk-response+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-protection-description+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-reception-report+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-register+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-register-response+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-schedule+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbms-user-service-description+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mbox\":{\"source\":\"iana\",\"extensions\":[\"mbox\"]},\"application/media-policy-dataset+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/media_control+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/mediaservercontrol+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mscml\"]},\"application/merge-patch+json\":{\"source\":\"iana\",\"compressible\":true},\"application/metalink+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"metalink\"]},\"application/metalink4+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"meta4\"]},\"application/mets+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mets\"]},\"application/mf4\":{\"source\":\"iana\"},\"application/mikey\":{\"source\":\"iana\"},\"application/mipc\":{\"source\":\"iana\"},\"application/mmt-aei+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"maei\"]},\"application/mmt-usd+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"musd\"]},\"application/mods+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mods\"]},\"application/moss-keys\":{\"source\":\"iana\"},\"application/moss-signature\":{\"source\":\"iana\"},\"application/mosskey-data\":{\"source\":\"iana\"},\"application/mosskey-request\":{\"source\":\"iana\"},\"application/mp21\":{\"source\":\"iana\",\"extensions\":[\"m21\",\"mp21\"]},\"application/mp4\":{\"source\":\"iana\",\"extensions\":[\"mp4s\",\"m4p\"]},\"application/mpeg4-generic\":{\"source\":\"iana\"},\"application/mpeg4-iod\":{\"source\":\"iana\"},\"application/mpeg4-iod-xmt\":{\"source\":\"iana\"},\"application/mrb-consumer+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xdf\"]},\"application/mrb-publish+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xdf\"]},\"application/msc-ivr+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/msc-mixer+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/msword\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"doc\",\"dot\"]},\"application/mud+json\":{\"source\":\"iana\",\"compressible\":true},\"application/multipart-core\":{\"source\":\"iana\"},\"application/mxf\":{\"source\":\"iana\",\"extensions\":[\"mxf\"]},\"application/n-quads\":{\"source\":\"iana\",\"extensions\":[\"nq\"]},\"application/n-triples\":{\"source\":\"iana\",\"extensions\":[\"nt\"]},\"application/nasdata\":{\"source\":\"iana\"},\"application/news-checkgroups\":{\"source\":\"iana\",\"charset\":\"US-ASCII\"},\"application/news-groupinfo\":{\"source\":\"iana\",\"charset\":\"US-ASCII\"},\"application/news-transmission\":{\"source\":\"iana\"},\"application/nlsml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/node\":{\"source\":\"iana\",\"extensions\":[\"cjs\"]},\"application/nss\":{\"source\":\"iana\"},\"application/ocsp-request\":{\"source\":\"iana\"},\"application/ocsp-response\":{\"source\":\"iana\"},\"application/octet-stream\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"bin\",\"dms\",\"lrf\",\"mar\",\"so\",\"dist\",\"distz\",\"pkg\",\"bpk\",\"dump\",\"elc\",\"deploy\",\"exe\",\"dll\",\"deb\",\"dmg\",\"iso\",\"img\",\"msi\",\"msp\",\"msm\",\"buffer\"]},\"application/oda\":{\"source\":\"iana\",\"extensions\":[\"oda\"]},\"application/odm+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/odx\":{\"source\":\"iana\"},\"application/oebps-package+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"opf\"]},\"application/ogg\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"ogx\"]},\"application/omdoc+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"omdoc\"]},\"application/onenote\":{\"source\":\"apache\",\"extensions\":[\"onetoc\",\"onetoc2\",\"onetmp\",\"onepkg\"]},\"application/oscore\":{\"source\":\"iana\"},\"application/oxps\":{\"source\":\"iana\",\"extensions\":[\"oxps\"]},\"application/p2p-overlay+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"relo\"]},\"application/parityfec\":{\"source\":\"iana\"},\"application/passport\":{\"source\":\"iana\"},\"application/patch-ops-error+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xer\"]},\"application/pdf\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"pdf\"]},\"application/pdx\":{\"source\":\"iana\"},\"application/pem-certificate-chain\":{\"source\":\"iana\"},\"application/pgp-encrypted\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"pgp\"]},\"application/pgp-keys\":{\"source\":\"iana\"},\"application/pgp-signature\":{\"source\":\"iana\",\"extensions\":[\"asc\",\"sig\"]},\"application/pics-rules\":{\"source\":\"apache\",\"extensions\":[\"prf\"]},\"application/pidf+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/pidf-diff+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/pkcs10\":{\"source\":\"iana\",\"extensions\":[\"p10\"]},\"application/pkcs12\":{\"source\":\"iana\"},\"application/pkcs7-mime\":{\"source\":\"iana\",\"extensions\":[\"p7m\",\"p7c\"]},\"application/pkcs7-signature\":{\"source\":\"iana\",\"extensions\":[\"p7s\"]},\"application/pkcs8\":{\"source\":\"iana\",\"extensions\":[\"p8\"]},\"application/pkcs8-encrypted\":{\"source\":\"iana\"},\"application/pkix-attr-cert\":{\"source\":\"iana\",\"extensions\":[\"ac\"]},\"application/pkix-cert\":{\"source\":\"iana\",\"extensions\":[\"cer\"]},\"application/pkix-crl\":{\"source\":\"iana\",\"extensions\":[\"crl\"]},\"application/pkix-pkipath\":{\"source\":\"iana\",\"extensions\":[\"pkipath\"]},\"application/pkixcmp\":{\"source\":\"iana\",\"extensions\":[\"pki\"]},\"application/pls+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"pls\"]},\"application/poc-settings+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/postscript\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ai\",\"eps\",\"ps\"]},\"application/ppsp-tracker+json\":{\"source\":\"iana\",\"compressible\":true},\"application/problem+json\":{\"source\":\"iana\",\"compressible\":true},\"application/problem+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/provenance+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"provx\"]},\"application/prs.alvestrand.titrax-sheet\":{\"source\":\"iana\"},\"application/prs.cww\":{\"source\":\"iana\",\"extensions\":[\"cww\"]},\"application/prs.hpub+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/prs.nprend\":{\"source\":\"iana\"},\"application/prs.plucker\":{\"source\":\"iana\"},\"application/prs.rdf-xml-crypt\":{\"source\":\"iana\"},\"application/prs.xsf+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/pskc+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"pskcxml\"]},\"application/pvd+json\":{\"source\":\"iana\",\"compressible\":true},\"application/qsig\":{\"source\":\"iana\"},\"application/raml+yaml\":{\"compressible\":true,\"extensions\":[\"raml\"]},\"application/raptorfec\":{\"source\":\"iana\"},\"application/rdap+json\":{\"source\":\"iana\",\"compressible\":true},\"application/rdf+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rdf\",\"owl\"]},\"application/reginfo+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rif\"]},\"application/relax-ng-compact-syntax\":{\"source\":\"iana\",\"extensions\":[\"rnc\"]},\"application/remote-printing\":{\"source\":\"iana\"},\"application/reputon+json\":{\"source\":\"iana\",\"compressible\":true},\"application/resource-lists+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rl\"]},\"application/resource-lists-diff+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rld\"]},\"application/rfc+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/riscos\":{\"source\":\"iana\"},\"application/rlmi+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/rls-services+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rs\"]},\"application/route-apd+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rapd\"]},\"application/route-s-tsid+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"sls\"]},\"application/route-usd+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rusd\"]},\"application/rpki-ghostbusters\":{\"source\":\"iana\",\"extensions\":[\"gbr\"]},\"application/rpki-manifest\":{\"source\":\"iana\",\"extensions\":[\"mft\"]},\"application/rpki-publication\":{\"source\":\"iana\"},\"application/rpki-roa\":{\"source\":\"iana\",\"extensions\":[\"roa\"]},\"application/rpki-updown\":{\"source\":\"iana\"},\"application/rsd+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"rsd\"]},\"application/rss+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"rss\"]},\"application/rtf\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rtf\"]},\"application/rtploopback\":{\"source\":\"iana\"},\"application/rtx\":{\"source\":\"iana\"},\"application/samlassertion+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/samlmetadata+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/sbe\":{\"source\":\"iana\"},\"application/sbml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"sbml\"]},\"application/scaip+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/scim+json\":{\"source\":\"iana\",\"compressible\":true},\"application/scvp-cv-request\":{\"source\":\"iana\",\"extensions\":[\"scq\"]},\"application/scvp-cv-response\":{\"source\":\"iana\",\"extensions\":[\"scs\"]},\"application/scvp-vp-request\":{\"source\":\"iana\",\"extensions\":[\"spq\"]},\"application/scvp-vp-response\":{\"source\":\"iana\",\"extensions\":[\"spp\"]},\"application/sdp\":{\"source\":\"iana\",\"extensions\":[\"sdp\"]},\"application/secevent+jwt\":{\"source\":\"iana\"},\"application/senml+cbor\":{\"source\":\"iana\"},\"application/senml+json\":{\"source\":\"iana\",\"compressible\":true},\"application/senml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"senmlx\"]},\"application/senml-etch+cbor\":{\"source\":\"iana\"},\"application/senml-etch+json\":{\"source\":\"iana\",\"compressible\":true},\"application/senml-exi\":{\"source\":\"iana\"},\"application/sensml+cbor\":{\"source\":\"iana\"},\"application/sensml+json\":{\"source\":\"iana\",\"compressible\":true},\"application/sensml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"sensmlx\"]},\"application/sensml-exi\":{\"source\":\"iana\"},\"application/sep+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/sep-exi\":{\"source\":\"iana\"},\"application/session-info\":{\"source\":\"iana\"},\"application/set-payment\":{\"source\":\"iana\"},\"application/set-payment-initiation\":{\"source\":\"iana\",\"extensions\":[\"setpay\"]},\"application/set-registration\":{\"source\":\"iana\"},\"application/set-registration-initiation\":{\"source\":\"iana\",\"extensions\":[\"setreg\"]},\"application/sgml\":{\"source\":\"iana\"},\"application/sgml-open-catalog\":{\"source\":\"iana\"},\"application/shf+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"shf\"]},\"application/sieve\":{\"source\":\"iana\",\"extensions\":[\"siv\",\"sieve\"]},\"application/simple-filter+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/simple-message-summary\":{\"source\":\"iana\"},\"application/simplesymbolcontainer\":{\"source\":\"iana\"},\"application/sipc\":{\"source\":\"iana\"},\"application/slate\":{\"source\":\"iana\"},\"application/smil\":{\"source\":\"iana\"},\"application/smil+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"smi\",\"smil\"]},\"application/smpte336m\":{\"source\":\"iana\"},\"application/soap+fastinfoset\":{\"source\":\"iana\"},\"application/soap+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/sparql-query\":{\"source\":\"iana\",\"extensions\":[\"rq\"]},\"application/sparql-results+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"srx\"]},\"application/spirits-event+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/sql\":{\"source\":\"iana\"},\"application/srgs\":{\"source\":\"iana\",\"extensions\":[\"gram\"]},\"application/srgs+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"grxml\"]},\"application/sru+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"sru\"]},\"application/ssdl+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"ssdl\"]},\"application/ssml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ssml\"]},\"application/stix+json\":{\"source\":\"iana\",\"compressible\":true},\"application/swid+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"swidtag\"]},\"application/tamp-apex-update\":{\"source\":\"iana\"},\"application/tamp-apex-update-confirm\":{\"source\":\"iana\"},\"application/tamp-community-update\":{\"source\":\"iana\"},\"application/tamp-community-update-confirm\":{\"source\":\"iana\"},\"application/tamp-error\":{\"source\":\"iana\"},\"application/tamp-sequence-adjust\":{\"source\":\"iana\"},\"application/tamp-sequence-adjust-confirm\":{\"source\":\"iana\"},\"application/tamp-status-query\":{\"source\":\"iana\"},\"application/tamp-status-response\":{\"source\":\"iana\"},\"application/tamp-update\":{\"source\":\"iana\"},\"application/tamp-update-confirm\":{\"source\":\"iana\"},\"application/tar\":{\"compressible\":true},\"application/taxii+json\":{\"source\":\"iana\",\"compressible\":true},\"application/td+json\":{\"source\":\"iana\",\"compressible\":true},\"application/tei+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"tei\",\"teicorpus\"]},\"application/tetra_isi\":{\"source\":\"iana\"},\"application/thraud+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"tfi\"]},\"application/timestamp-query\":{\"source\":\"iana\"},\"application/timestamp-reply\":{\"source\":\"iana\"},\"application/timestamped-data\":{\"source\":\"iana\",\"extensions\":[\"tsd\"]},\"application/tlsrpt+gzip\":{\"source\":\"iana\"},\"application/tlsrpt+json\":{\"source\":\"iana\",\"compressible\":true},\"application/tnauthlist\":{\"source\":\"iana\"},\"application/toml\":{\"compressible\":true,\"extensions\":[\"toml\"]},\"application/trickle-ice-sdpfrag\":{\"source\":\"iana\"},\"application/trig\":{\"source\":\"iana\"},\"application/ttml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ttml\"]},\"application/tve-trigger\":{\"source\":\"iana\"},\"application/tzif\":{\"source\":\"iana\"},\"application/tzif-leap\":{\"source\":\"iana\"},\"application/ulpfec\":{\"source\":\"iana\"},\"application/urc-grpsheet+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/urc-ressheet+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rsheet\"]},\"application/urc-targetdesc+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/urc-uisocketdesc+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vcard+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vcard+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vemmi\":{\"source\":\"iana\"},\"application/vividence.scriptfile\":{\"source\":\"apache\"},\"application/vnd.1000minds.decision-model+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"1km\"]},\"application/vnd.3gpp-prose+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp-prose-pc3ch+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp-v2x-local-service-information\":{\"source\":\"iana\"},\"application/vnd.3gpp.access-transfer-events+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.bsf+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.gmop+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mc-signalling-ear\":{\"source\":\"iana\"},\"application/vnd.3gpp.mcdata-affiliation-command+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcdata-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcdata-payload\":{\"source\":\"iana\"},\"application/vnd.3gpp.mcdata-service-config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcdata-signalling\":{\"source\":\"iana\"},\"application/vnd.3gpp.mcdata-ue-config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcdata-user-profile+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-affiliation-command+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-floor-request+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-location-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-mbms-usage-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-service-config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-signed+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-ue-config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-ue-init-config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcptt-user-profile+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-affiliation-command+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-affiliation-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-location-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-mbms-usage-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-service-config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-transmission-request+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-ue-config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mcvideo-user-profile+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.mid-call+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.pic-bw-large\":{\"source\":\"iana\",\"extensions\":[\"plb\"]},\"application/vnd.3gpp.pic-bw-small\":{\"source\":\"iana\",\"extensions\":[\"psb\"]},\"application/vnd.3gpp.pic-bw-var\":{\"source\":\"iana\",\"extensions\":[\"pvb\"]},\"application/vnd.3gpp.sms\":{\"source\":\"iana\"},\"application/vnd.3gpp.sms+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.srvcc-ext+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.srvcc-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.state-and-event-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp.ussd+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp2.bcmcsinfo+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.3gpp2.sms\":{\"source\":\"iana\"},\"application/vnd.3gpp2.tcap\":{\"source\":\"iana\",\"extensions\":[\"tcap\"]},\"application/vnd.3lightssoftware.imagescal\":{\"source\":\"iana\"},\"application/vnd.3m.post-it-notes\":{\"source\":\"iana\",\"extensions\":[\"pwn\"]},\"application/vnd.accpac.simply.aso\":{\"source\":\"iana\",\"extensions\":[\"aso\"]},\"application/vnd.accpac.simply.imp\":{\"source\":\"iana\",\"extensions\":[\"imp\"]},\"application/vnd.acucobol\":{\"source\":\"iana\",\"extensions\":[\"acu\"]},\"application/vnd.acucorp\":{\"source\":\"iana\",\"extensions\":[\"atc\",\"acutc\"]},\"application/vnd.adobe.air-application-installer-package+zip\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"air\"]},\"application/vnd.adobe.flash.movie\":{\"source\":\"iana\"},\"application/vnd.adobe.formscentral.fcdt\":{\"source\":\"iana\",\"extensions\":[\"fcdt\"]},\"application/vnd.adobe.fxp\":{\"source\":\"iana\",\"extensions\":[\"fxp\",\"fxpl\"]},\"application/vnd.adobe.partial-upload\":{\"source\":\"iana\"},\"application/vnd.adobe.xdp+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xdp\"]},\"application/vnd.adobe.xfdf\":{\"source\":\"iana\",\"extensions\":[\"xfdf\"]},\"application/vnd.aether.imp\":{\"source\":\"iana\"},\"application/vnd.afpc.afplinedata\":{\"source\":\"iana\"},\"application/vnd.afpc.afplinedata-pagedef\":{\"source\":\"iana\"},\"application/vnd.afpc.foca-charset\":{\"source\":\"iana\"},\"application/vnd.afpc.foca-codedfont\":{\"source\":\"iana\"},\"application/vnd.afpc.foca-codepage\":{\"source\":\"iana\"},\"application/vnd.afpc.modca\":{\"source\":\"iana\"},\"application/vnd.afpc.modca-formdef\":{\"source\":\"iana\"},\"application/vnd.afpc.modca-mediummap\":{\"source\":\"iana\"},\"application/vnd.afpc.modca-objectcontainer\":{\"source\":\"iana\"},\"application/vnd.afpc.modca-overlay\":{\"source\":\"iana\"},\"application/vnd.afpc.modca-pagesegment\":{\"source\":\"iana\"},\"application/vnd.ah-barcode\":{\"source\":\"iana\"},\"application/vnd.ahead.space\":{\"source\":\"iana\",\"extensions\":[\"ahead\"]},\"application/vnd.airzip.filesecure.azf\":{\"source\":\"iana\",\"extensions\":[\"azf\"]},\"application/vnd.airzip.filesecure.azs\":{\"source\":\"iana\",\"extensions\":[\"azs\"]},\"application/vnd.amadeus+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.amazon.ebook\":{\"source\":\"apache\",\"extensions\":[\"azw\"]},\"application/vnd.amazon.mobi8-ebook\":{\"source\":\"iana\"},\"application/vnd.americandynamics.acc\":{\"source\":\"iana\",\"extensions\":[\"acc\"]},\"application/vnd.amiga.ami\":{\"source\":\"iana\",\"extensions\":[\"ami\"]},\"application/vnd.amundsen.maze+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.android.ota\":{\"source\":\"iana\"},\"application/vnd.android.package-archive\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"apk\"]},\"application/vnd.anki\":{\"source\":\"iana\"},\"application/vnd.anser-web-certificate-issue-initiation\":{\"source\":\"iana\",\"extensions\":[\"cii\"]},\"application/vnd.anser-web-funds-transfer-initiation\":{\"source\":\"apache\",\"extensions\":[\"fti\"]},\"application/vnd.antix.game-component\":{\"source\":\"iana\",\"extensions\":[\"atx\"]},\"application/vnd.apache.thrift.binary\":{\"source\":\"iana\"},\"application/vnd.apache.thrift.compact\":{\"source\":\"iana\"},\"application/vnd.apache.thrift.json\":{\"source\":\"iana\"},\"application/vnd.api+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.aplextor.warrp+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.apothekende.reservation+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.apple.installer+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mpkg\"]},\"application/vnd.apple.keynote\":{\"source\":\"iana\",\"extensions\":[\"keynote\"]},\"application/vnd.apple.mpegurl\":{\"source\":\"iana\",\"extensions\":[\"m3u8\"]},\"application/vnd.apple.numbers\":{\"source\":\"iana\",\"extensions\":[\"numbers\"]},\"application/vnd.apple.pages\":{\"source\":\"iana\",\"extensions\":[\"pages\"]},\"application/vnd.apple.pkpass\":{\"compressible\":false,\"extensions\":[\"pkpass\"]},\"application/vnd.arastra.swi\":{\"source\":\"iana\"},\"application/vnd.aristanetworks.swi\":{\"source\":\"iana\",\"extensions\":[\"swi\"]},\"application/vnd.artisan+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.artsquare\":{\"source\":\"iana\"},\"application/vnd.astraea-software.iota\":{\"source\":\"iana\",\"extensions\":[\"iota\"]},\"application/vnd.audiograph\":{\"source\":\"iana\",\"extensions\":[\"aep\"]},\"application/vnd.autopackage\":{\"source\":\"iana\"},\"application/vnd.avalon+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.avistar+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.balsamiq.bmml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"bmml\"]},\"application/vnd.balsamiq.bmpr\":{\"source\":\"iana\"},\"application/vnd.banana-accounting\":{\"source\":\"iana\"},\"application/vnd.bbf.usp.error\":{\"source\":\"iana\"},\"application/vnd.bbf.usp.msg\":{\"source\":\"iana\"},\"application/vnd.bbf.usp.msg+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.bekitzur-stech+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.bint.med-content\":{\"source\":\"iana\"},\"application/vnd.biopax.rdf+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.blink-idb-value-wrapper\":{\"source\":\"iana\"},\"application/vnd.blueice.multipass\":{\"source\":\"iana\",\"extensions\":[\"mpm\"]},\"application/vnd.bluetooth.ep.oob\":{\"source\":\"iana\"},\"application/vnd.bluetooth.le.oob\":{\"source\":\"iana\"},\"application/vnd.bmi\":{\"source\":\"iana\",\"extensions\":[\"bmi\"]},\"application/vnd.bpf\":{\"source\":\"iana\"},\"application/vnd.bpf3\":{\"source\":\"iana\"},\"application/vnd.businessobjects\":{\"source\":\"iana\",\"extensions\":[\"rep\"]},\"application/vnd.byu.uapi+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.cab-jscript\":{\"source\":\"iana\"},\"application/vnd.canon-cpdl\":{\"source\":\"iana\"},\"application/vnd.canon-lips\":{\"source\":\"iana\"},\"application/vnd.capasystems-pg+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.cendio.thinlinc.clientconf\":{\"source\":\"iana\"},\"application/vnd.century-systems.tcp_stream\":{\"source\":\"iana\"},\"application/vnd.chemdraw+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"cdxml\"]},\"application/vnd.chess-pgn\":{\"source\":\"iana\"},\"application/vnd.chipnuts.karaoke-mmd\":{\"source\":\"iana\",\"extensions\":[\"mmd\"]},\"application/vnd.ciedi\":{\"source\":\"iana\"},\"application/vnd.cinderella\":{\"source\":\"iana\",\"extensions\":[\"cdy\"]},\"application/vnd.cirpack.isdn-ext\":{\"source\":\"iana\"},\"application/vnd.citationstyles.style+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"csl\"]},\"application/vnd.claymore\":{\"source\":\"iana\",\"extensions\":[\"cla\"]},\"application/vnd.cloanto.rp9\":{\"source\":\"iana\",\"extensions\":[\"rp9\"]},\"application/vnd.clonk.c4group\":{\"source\":\"iana\",\"extensions\":[\"c4g\",\"c4d\",\"c4f\",\"c4p\",\"c4u\"]},\"application/vnd.cluetrust.cartomobile-config\":{\"source\":\"iana\",\"extensions\":[\"c11amc\"]},\"application/vnd.cluetrust.cartomobile-config-pkg\":{\"source\":\"iana\",\"extensions\":[\"c11amz\"]},\"application/vnd.coffeescript\":{\"source\":\"iana\"},\"application/vnd.collabio.xodocuments.document\":{\"source\":\"iana\"},\"application/vnd.collabio.xodocuments.document-template\":{\"source\":\"iana\"},\"application/vnd.collabio.xodocuments.presentation\":{\"source\":\"iana\"},\"application/vnd.collabio.xodocuments.presentation-template\":{\"source\":\"iana\"},\"application/vnd.collabio.xodocuments.spreadsheet\":{\"source\":\"iana\"},\"application/vnd.collabio.xodocuments.spreadsheet-template\":{\"source\":\"iana\"},\"application/vnd.collection+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.collection.doc+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.collection.next+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.comicbook+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.comicbook-rar\":{\"source\":\"iana\"},\"application/vnd.commerce-battelle\":{\"source\":\"iana\"},\"application/vnd.commonspace\":{\"source\":\"iana\",\"extensions\":[\"csp\"]},\"application/vnd.contact.cmsg\":{\"source\":\"iana\",\"extensions\":[\"cdbcmsg\"]},\"application/vnd.coreos.ignition+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.cosmocaller\":{\"source\":\"iana\",\"extensions\":[\"cmc\"]},\"application/vnd.crick.clicker\":{\"source\":\"iana\",\"extensions\":[\"clkx\"]},\"application/vnd.crick.clicker.keyboard\":{\"source\":\"iana\",\"extensions\":[\"clkk\"]},\"application/vnd.crick.clicker.palette\":{\"source\":\"iana\",\"extensions\":[\"clkp\"]},\"application/vnd.crick.clicker.template\":{\"source\":\"iana\",\"extensions\":[\"clkt\"]},\"application/vnd.crick.clicker.wordbank\":{\"source\":\"iana\",\"extensions\":[\"clkw\"]},\"application/vnd.criticaltools.wbs+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"wbs\"]},\"application/vnd.cryptii.pipe+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.crypto-shade-file\":{\"source\":\"iana\"},\"application/vnd.ctc-posml\":{\"source\":\"iana\",\"extensions\":[\"pml\"]},\"application/vnd.ctct.ws+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.cups-pdf\":{\"source\":\"iana\"},\"application/vnd.cups-postscript\":{\"source\":\"iana\"},\"application/vnd.cups-ppd\":{\"source\":\"iana\",\"extensions\":[\"ppd\"]},\"application/vnd.cups-raster\":{\"source\":\"iana\"},\"application/vnd.cups-raw\":{\"source\":\"iana\"},\"application/vnd.curl\":{\"source\":\"iana\"},\"application/vnd.curl.car\":{\"source\":\"apache\",\"extensions\":[\"car\"]},\"application/vnd.curl.pcurl\":{\"source\":\"apache\",\"extensions\":[\"pcurl\"]},\"application/vnd.cyan.dean.root+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.cybank\":{\"source\":\"iana\"},\"application/vnd.d2l.coursepackage1p0+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.dart\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"dart\"]},\"application/vnd.data-vision.rdz\":{\"source\":\"iana\",\"extensions\":[\"rdz\"]},\"application/vnd.datapackage+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dataresource+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dbf\":{\"source\":\"iana\"},\"application/vnd.debian.binary-package\":{\"source\":\"iana\"},\"application/vnd.dece.data\":{\"source\":\"iana\",\"extensions\":[\"uvf\",\"uvvf\",\"uvd\",\"uvvd\"]},\"application/vnd.dece.ttml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"uvt\",\"uvvt\"]},\"application/vnd.dece.unspecified\":{\"source\":\"iana\",\"extensions\":[\"uvx\",\"uvvx\"]},\"application/vnd.dece.zip\":{\"source\":\"iana\",\"extensions\":[\"uvz\",\"uvvz\"]},\"application/vnd.denovo.fcselayout-link\":{\"source\":\"iana\",\"extensions\":[\"fe_launch\"]},\"application/vnd.desmume.movie\":{\"source\":\"iana\"},\"application/vnd.dir-bi.plate-dl-nosuffix\":{\"source\":\"iana\"},\"application/vnd.dm.delegation+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dna\":{\"source\":\"iana\",\"extensions\":[\"dna\"]},\"application/vnd.document+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dolby.mlp\":{\"source\":\"apache\",\"extensions\":[\"mlp\"]},\"application/vnd.dolby.mobile.1\":{\"source\":\"iana\"},\"application/vnd.dolby.mobile.2\":{\"source\":\"iana\"},\"application/vnd.doremir.scorecloud-binary-document\":{\"source\":\"iana\"},\"application/vnd.dpgraph\":{\"source\":\"iana\",\"extensions\":[\"dpg\"]},\"application/vnd.dreamfactory\":{\"source\":\"iana\",\"extensions\":[\"dfac\"]},\"application/vnd.drive+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ds-keypoint\":{\"source\":\"apache\",\"extensions\":[\"kpxx\"]},\"application/vnd.dtg.local\":{\"source\":\"iana\"},\"application/vnd.dtg.local.flash\":{\"source\":\"iana\"},\"application/vnd.dtg.local.html\":{\"source\":\"iana\"},\"application/vnd.dvb.ait\":{\"source\":\"iana\",\"extensions\":[\"ait\"]},\"application/vnd.dvb.dvbisl+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.dvbj\":{\"source\":\"iana\"},\"application/vnd.dvb.esgcontainer\":{\"source\":\"iana\"},\"application/vnd.dvb.ipdcdftnotifaccess\":{\"source\":\"iana\"},\"application/vnd.dvb.ipdcesgaccess\":{\"source\":\"iana\"},\"application/vnd.dvb.ipdcesgaccess2\":{\"source\":\"iana\"},\"application/vnd.dvb.ipdcesgpdd\":{\"source\":\"iana\"},\"application/vnd.dvb.ipdcroaming\":{\"source\":\"iana\"},\"application/vnd.dvb.iptv.alfec-base\":{\"source\":\"iana\"},\"application/vnd.dvb.iptv.alfec-enhancement\":{\"source\":\"iana\"},\"application/vnd.dvb.notif-aggregate-root+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.notif-container+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.notif-generic+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.notif-ia-msglist+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.notif-ia-registration-request+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.notif-ia-registration-response+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.notif-init+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.dvb.pfr\":{\"source\":\"iana\"},\"application/vnd.dvb.service\":{\"source\":\"iana\",\"extensions\":[\"svc\"]},\"application/vnd.dxr\":{\"source\":\"iana\"},\"application/vnd.dynageo\":{\"source\":\"iana\",\"extensions\":[\"geo\"]},\"application/vnd.dzr\":{\"source\":\"iana\"},\"application/vnd.easykaraoke.cdgdownload\":{\"source\":\"iana\"},\"application/vnd.ecdis-update\":{\"source\":\"iana\"},\"application/vnd.ecip.rlp\":{\"source\":\"iana\"},\"application/vnd.ecowin.chart\":{\"source\":\"iana\",\"extensions\":[\"mag\"]},\"application/vnd.ecowin.filerequest\":{\"source\":\"iana\"},\"application/vnd.ecowin.fileupdate\":{\"source\":\"iana\"},\"application/vnd.ecowin.series\":{\"source\":\"iana\"},\"application/vnd.ecowin.seriesrequest\":{\"source\":\"iana\"},\"application/vnd.ecowin.seriesupdate\":{\"source\":\"iana\"},\"application/vnd.efi.img\":{\"source\":\"iana\"},\"application/vnd.efi.iso\":{\"source\":\"iana\"},\"application/vnd.emclient.accessrequest+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.enliven\":{\"source\":\"iana\",\"extensions\":[\"nml\"]},\"application/vnd.enphase.envoy\":{\"source\":\"iana\"},\"application/vnd.eprints.data+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.epson.esf\":{\"source\":\"iana\",\"extensions\":[\"esf\"]},\"application/vnd.epson.msf\":{\"source\":\"iana\",\"extensions\":[\"msf\"]},\"application/vnd.epson.quickanime\":{\"source\":\"iana\",\"extensions\":[\"qam\"]},\"application/vnd.epson.salt\":{\"source\":\"iana\",\"extensions\":[\"slt\"]},\"application/vnd.epson.ssf\":{\"source\":\"iana\",\"extensions\":[\"ssf\"]},\"application/vnd.ericsson.quickcall\":{\"source\":\"iana\"},\"application/vnd.espass-espass+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.eszigno3+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"es3\",\"et3\"]},\"application/vnd.etsi.aoc+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.asic-e+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.etsi.asic-s+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.etsi.cug+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvcommand+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvdiscovery+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvprofile+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvsad-bc+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvsad-cod+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvsad-npvr+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvservice+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvsync+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.iptvueprofile+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.mcid+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.mheg5\":{\"source\":\"iana\"},\"application/vnd.etsi.overload-control-policy-dataset+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.pstn+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.sci+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.simservs+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.timestamp-token\":{\"source\":\"iana\"},\"application/vnd.etsi.tsl+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.etsi.tsl.der\":{\"source\":\"iana\"},\"application/vnd.eudora.data\":{\"source\":\"iana\"},\"application/vnd.evolv.ecig.profile\":{\"source\":\"iana\"},\"application/vnd.evolv.ecig.settings\":{\"source\":\"iana\"},\"application/vnd.evolv.ecig.theme\":{\"source\":\"iana\"},\"application/vnd.exstream-empower+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.exstream-package\":{\"source\":\"iana\"},\"application/vnd.ezpix-album\":{\"source\":\"iana\",\"extensions\":[\"ez2\"]},\"application/vnd.ezpix-package\":{\"source\":\"iana\",\"extensions\":[\"ez3\"]},\"application/vnd.f-secure.mobile\":{\"source\":\"iana\"},\"application/vnd.fastcopy-disk-image\":{\"source\":\"iana\"},\"application/vnd.fdf\":{\"source\":\"iana\",\"extensions\":[\"fdf\"]},\"application/vnd.fdsn.mseed\":{\"source\":\"iana\",\"extensions\":[\"mseed\"]},\"application/vnd.fdsn.seed\":{\"source\":\"iana\",\"extensions\":[\"seed\",\"dataless\"]},\"application/vnd.ffsns\":{\"source\":\"iana\"},\"application/vnd.ficlab.flb+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.filmit.zfc\":{\"source\":\"iana\"},\"application/vnd.fints\":{\"source\":\"iana\"},\"application/vnd.firemonkeys.cloudcell\":{\"source\":\"iana\"},\"application/vnd.flographit\":{\"source\":\"iana\",\"extensions\":[\"gph\"]},\"application/vnd.fluxtime.clip\":{\"source\":\"iana\",\"extensions\":[\"ftc\"]},\"application/vnd.font-fontforge-sfd\":{\"source\":\"iana\"},\"application/vnd.framemaker\":{\"source\":\"iana\",\"extensions\":[\"fm\",\"frame\",\"maker\",\"book\"]},\"application/vnd.frogans.fnc\":{\"source\":\"iana\",\"extensions\":[\"fnc\"]},\"application/vnd.frogans.ltf\":{\"source\":\"iana\",\"extensions\":[\"ltf\"]},\"application/vnd.fsc.weblaunch\":{\"source\":\"iana\",\"extensions\":[\"fsc\"]},\"application/vnd.fujitsu.oasys\":{\"source\":\"iana\",\"extensions\":[\"oas\"]},\"application/vnd.fujitsu.oasys2\":{\"source\":\"iana\",\"extensions\":[\"oa2\"]},\"application/vnd.fujitsu.oasys3\":{\"source\":\"iana\",\"extensions\":[\"oa3\"]},\"application/vnd.fujitsu.oasysgp\":{\"source\":\"iana\",\"extensions\":[\"fg5\"]},\"application/vnd.fujitsu.oasysprs\":{\"source\":\"iana\",\"extensions\":[\"bh2\"]},\"application/vnd.fujixerox.art-ex\":{\"source\":\"iana\"},\"application/vnd.fujixerox.art4\":{\"source\":\"iana\"},\"application/vnd.fujixerox.ddd\":{\"source\":\"iana\",\"extensions\":[\"ddd\"]},\"application/vnd.fujixerox.docuworks\":{\"source\":\"iana\",\"extensions\":[\"xdw\"]},\"application/vnd.fujixerox.docuworks.binder\":{\"source\":\"iana\",\"extensions\":[\"xbd\"]},\"application/vnd.fujixerox.docuworks.container\":{\"source\":\"iana\"},\"application/vnd.fujixerox.hbpl\":{\"source\":\"iana\"},\"application/vnd.fut-misnet\":{\"source\":\"iana\"},\"application/vnd.futoin+cbor\":{\"source\":\"iana\"},\"application/vnd.futoin+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.fuzzysheet\":{\"source\":\"iana\",\"extensions\":[\"fzs\"]},\"application/vnd.genomatix.tuxedo\":{\"source\":\"iana\",\"extensions\":[\"txd\"]},\"application/vnd.gentics.grd+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.geo+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.geocube+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.geogebra.file\":{\"source\":\"iana\",\"extensions\":[\"ggb\"]},\"application/vnd.geogebra.tool\":{\"source\":\"iana\",\"extensions\":[\"ggt\"]},\"application/vnd.geometry-explorer\":{\"source\":\"iana\",\"extensions\":[\"gex\",\"gre\"]},\"application/vnd.geonext\":{\"source\":\"iana\",\"extensions\":[\"gxt\"]},\"application/vnd.geoplan\":{\"source\":\"iana\",\"extensions\":[\"g2w\"]},\"application/vnd.geospace\":{\"source\":\"iana\",\"extensions\":[\"g3w\"]},\"application/vnd.gerber\":{\"source\":\"iana\"},\"application/vnd.globalplatform.card-content-mgt\":{\"source\":\"iana\"},\"application/vnd.globalplatform.card-content-mgt-response\":{\"source\":\"iana\"},\"application/vnd.gmx\":{\"source\":\"iana\",\"extensions\":[\"gmx\"]},\"application/vnd.google-apps.document\":{\"compressible\":false,\"extensions\":[\"gdoc\"]},\"application/vnd.google-apps.presentation\":{\"compressible\":false,\"extensions\":[\"gslides\"]},\"application/vnd.google-apps.spreadsheet\":{\"compressible\":false,\"extensions\":[\"gsheet\"]},\"application/vnd.google-earth.kml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"kml\"]},\"application/vnd.google-earth.kmz\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"kmz\"]},\"application/vnd.gov.sk.e-form+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.gov.sk.e-form+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.gov.sk.xmldatacontainer+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.grafeq\":{\"source\":\"iana\",\"extensions\":[\"gqf\",\"gqs\"]},\"application/vnd.gridmp\":{\"source\":\"iana\"},\"application/vnd.groove-account\":{\"source\":\"iana\",\"extensions\":[\"gac\"]},\"application/vnd.groove-help\":{\"source\":\"iana\",\"extensions\":[\"ghf\"]},\"application/vnd.groove-identity-message\":{\"source\":\"iana\",\"extensions\":[\"gim\"]},\"application/vnd.groove-injector\":{\"source\":\"iana\",\"extensions\":[\"grv\"]},\"application/vnd.groove-tool-message\":{\"source\":\"iana\",\"extensions\":[\"gtm\"]},\"application/vnd.groove-tool-template\":{\"source\":\"iana\",\"extensions\":[\"tpl\"]},\"application/vnd.groove-vcard\":{\"source\":\"iana\",\"extensions\":[\"vcg\"]},\"application/vnd.hal+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.hal+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"hal\"]},\"application/vnd.handheld-entertainment+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"zmm\"]},\"application/vnd.hbci\":{\"source\":\"iana\",\"extensions\":[\"hbci\"]},\"application/vnd.hc+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.hcl-bireports\":{\"source\":\"iana\"},\"application/vnd.hdt\":{\"source\":\"iana\"},\"application/vnd.heroku+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.hhe.lesson-player\":{\"source\":\"iana\",\"extensions\":[\"les\"]},\"application/vnd.hp-hpgl\":{\"source\":\"iana\",\"extensions\":[\"hpgl\"]},\"application/vnd.hp-hpid\":{\"source\":\"iana\",\"extensions\":[\"hpid\"]},\"application/vnd.hp-hps\":{\"source\":\"iana\",\"extensions\":[\"hps\"]},\"application/vnd.hp-jlyt\":{\"source\":\"iana\",\"extensions\":[\"jlt\"]},\"application/vnd.hp-pcl\":{\"source\":\"iana\",\"extensions\":[\"pcl\"]},\"application/vnd.hp-pclxl\":{\"source\":\"iana\",\"extensions\":[\"pclxl\"]},\"application/vnd.httphone\":{\"source\":\"iana\"},\"application/vnd.hydrostatix.sof-data\":{\"source\":\"iana\",\"extensions\":[\"sfd-hdstx\"]},\"application/vnd.hyper+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.hyper-item+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.hyperdrive+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.hzn-3d-crossword\":{\"source\":\"iana\"},\"application/vnd.ibm.afplinedata\":{\"source\":\"iana\"},\"application/vnd.ibm.electronic-media\":{\"source\":\"iana\"},\"application/vnd.ibm.minipay\":{\"source\":\"iana\",\"extensions\":[\"mpy\"]},\"application/vnd.ibm.modcap\":{\"source\":\"iana\",\"extensions\":[\"afp\",\"listafp\",\"list3820\"]},\"application/vnd.ibm.rights-management\":{\"source\":\"iana\",\"extensions\":[\"irm\"]},\"application/vnd.ibm.secure-container\":{\"source\":\"iana\",\"extensions\":[\"sc\"]},\"application/vnd.iccprofile\":{\"source\":\"iana\",\"extensions\":[\"icc\",\"icm\"]},\"application/vnd.ieee.1905\":{\"source\":\"iana\"},\"application/vnd.igloader\":{\"source\":\"iana\",\"extensions\":[\"igl\"]},\"application/vnd.imagemeter.folder+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.imagemeter.image+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.immervision-ivp\":{\"source\":\"iana\",\"extensions\":[\"ivp\"]},\"application/vnd.immervision-ivu\":{\"source\":\"iana\",\"extensions\":[\"ivu\"]},\"application/vnd.ims.imsccv1p1\":{\"source\":\"iana\"},\"application/vnd.ims.imsccv1p2\":{\"source\":\"iana\"},\"application/vnd.ims.imsccv1p3\":{\"source\":\"iana\"},\"application/vnd.ims.lis.v2.result+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ims.lti.v2.toolconsumerprofile+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ims.lti.v2.toolproxy+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ims.lti.v2.toolproxy.id+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ims.lti.v2.toolsettings+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ims.lti.v2.toolsettings.simple+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.informedcontrol.rms+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.informix-visionary\":{\"source\":\"iana\"},\"application/vnd.infotech.project\":{\"source\":\"iana\"},\"application/vnd.infotech.project+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.innopath.wamp.notification\":{\"source\":\"iana\"},\"application/vnd.insors.igm\":{\"source\":\"iana\",\"extensions\":[\"igm\"]},\"application/vnd.intercon.formnet\":{\"source\":\"iana\",\"extensions\":[\"xpw\",\"xpx\"]},\"application/vnd.intergeo\":{\"source\":\"iana\",\"extensions\":[\"i2g\"]},\"application/vnd.intertrust.digibox\":{\"source\":\"iana\"},\"application/vnd.intertrust.nncp\":{\"source\":\"iana\"},\"application/vnd.intu.qbo\":{\"source\":\"iana\",\"extensions\":[\"qbo\"]},\"application/vnd.intu.qfx\":{\"source\":\"iana\",\"extensions\":[\"qfx\"]},\"application/vnd.iptc.g2.catalogitem+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.iptc.g2.conceptitem+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.iptc.g2.knowledgeitem+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.iptc.g2.newsitem+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.iptc.g2.newsmessage+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.iptc.g2.packageitem+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.iptc.g2.planningitem+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ipunplugged.rcprofile\":{\"source\":\"iana\",\"extensions\":[\"rcprofile\"]},\"application/vnd.irepository.package+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"irp\"]},\"application/vnd.is-xpr\":{\"source\":\"iana\",\"extensions\":[\"xpr\"]},\"application/vnd.isac.fcs\":{\"source\":\"iana\",\"extensions\":[\"fcs\"]},\"application/vnd.iso11783-10+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.jam\":{\"source\":\"iana\",\"extensions\":[\"jam\"]},\"application/vnd.japannet-directory-service\":{\"source\":\"iana\"},\"application/vnd.japannet-jpnstore-wakeup\":{\"source\":\"iana\"},\"application/vnd.japannet-payment-wakeup\":{\"source\":\"iana\"},\"application/vnd.japannet-registration\":{\"source\":\"iana\"},\"application/vnd.japannet-registration-wakeup\":{\"source\":\"iana\"},\"application/vnd.japannet-setstore-wakeup\":{\"source\":\"iana\"},\"application/vnd.japannet-verification\":{\"source\":\"iana\"},\"application/vnd.japannet-verification-wakeup\":{\"source\":\"iana\"},\"application/vnd.jcp.javame.midlet-rms\":{\"source\":\"iana\",\"extensions\":[\"rms\"]},\"application/vnd.jisp\":{\"source\":\"iana\",\"extensions\":[\"jisp\"]},\"application/vnd.joost.joda-archive\":{\"source\":\"iana\",\"extensions\":[\"joda\"]},\"application/vnd.jsk.isdn-ngn\":{\"source\":\"iana\"},\"application/vnd.kahootz\":{\"source\":\"iana\",\"extensions\":[\"ktz\",\"ktr\"]},\"application/vnd.kde.karbon\":{\"source\":\"iana\",\"extensions\":[\"karbon\"]},\"application/vnd.kde.kchart\":{\"source\":\"iana\",\"extensions\":[\"chrt\"]},\"application/vnd.kde.kformula\":{\"source\":\"iana\",\"extensions\":[\"kfo\"]},\"application/vnd.kde.kivio\":{\"source\":\"iana\",\"extensions\":[\"flw\"]},\"application/vnd.kde.kontour\":{\"source\":\"iana\",\"extensions\":[\"kon\"]},\"application/vnd.kde.kpresenter\":{\"source\":\"iana\",\"extensions\":[\"kpr\",\"kpt\"]},\"application/vnd.kde.kspread\":{\"source\":\"iana\",\"extensions\":[\"ksp\"]},\"application/vnd.kde.kword\":{\"source\":\"iana\",\"extensions\":[\"kwd\",\"kwt\"]},\"application/vnd.kenameaapp\":{\"source\":\"iana\",\"extensions\":[\"htke\"]},\"application/vnd.kidspiration\":{\"source\":\"iana\",\"extensions\":[\"kia\"]},\"application/vnd.kinar\":{\"source\":\"iana\",\"extensions\":[\"kne\",\"knp\"]},\"application/vnd.koan\":{\"source\":\"iana\",\"extensions\":[\"skp\",\"skd\",\"skt\",\"skm\"]},\"application/vnd.kodak-descriptor\":{\"source\":\"iana\",\"extensions\":[\"sse\"]},\"application/vnd.las\":{\"source\":\"iana\"},\"application/vnd.las.las+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.las.las+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"lasxml\"]},\"application/vnd.laszip\":{\"source\":\"iana\"},\"application/vnd.leap+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.liberty-request+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.llamagraphics.life-balance.desktop\":{\"source\":\"iana\",\"extensions\":[\"lbd\"]},\"application/vnd.llamagraphics.life-balance.exchange+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"lbe\"]},\"application/vnd.logipipe.circuit+zip\":{\"source\":\"iana\",\"compressible\":false},\"application/vnd.loom\":{\"source\":\"iana\"},\"application/vnd.lotus-1-2-3\":{\"source\":\"iana\",\"extensions\":[\"123\"]},\"application/vnd.lotus-approach\":{\"source\":\"iana\",\"extensions\":[\"apr\"]},\"application/vnd.lotus-freelance\":{\"source\":\"iana\",\"extensions\":[\"pre\"]},\"application/vnd.lotus-notes\":{\"source\":\"iana\",\"extensions\":[\"nsf\"]},\"application/vnd.lotus-organizer\":{\"source\":\"iana\",\"extensions\":[\"org\"]},\"application/vnd.lotus-screencam\":{\"source\":\"iana\",\"extensions\":[\"scm\"]},\"application/vnd.lotus-wordpro\":{\"source\":\"iana\",\"extensions\":[\"lwp\"]},\"application/vnd.macports.portpkg\":{\"source\":\"iana\",\"extensions\":[\"portpkg\"]},\"application/vnd.mapbox-vector-tile\":{\"source\":\"iana\"},\"application/vnd.marlin.drm.actiontoken+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.marlin.drm.conftoken+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.marlin.drm.license+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.marlin.drm.mdcf\":{\"source\":\"iana\"},\"application/vnd.mason+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.maxmind.maxmind-db\":{\"source\":\"iana\"},\"application/vnd.mcd\":{\"source\":\"iana\",\"extensions\":[\"mcd\"]},\"application/vnd.medcalcdata\":{\"source\":\"iana\",\"extensions\":[\"mc1\"]},\"application/vnd.mediastation.cdkey\":{\"source\":\"iana\",\"extensions\":[\"cdkey\"]},\"application/vnd.meridian-slingshot\":{\"source\":\"iana\"},\"application/vnd.mfer\":{\"source\":\"iana\",\"extensions\":[\"mwf\"]},\"application/vnd.mfmp\":{\"source\":\"iana\",\"extensions\":[\"mfm\"]},\"application/vnd.micro+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.micrografx.flo\":{\"source\":\"iana\",\"extensions\":[\"flo\"]},\"application/vnd.micrografx.igx\":{\"source\":\"iana\",\"extensions\":[\"igx\"]},\"application/vnd.microsoft.portable-executable\":{\"source\":\"iana\"},\"application/vnd.microsoft.windows.thumbnail-cache\":{\"source\":\"iana\"},\"application/vnd.miele+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.mif\":{\"source\":\"iana\",\"extensions\":[\"mif\"]},\"application/vnd.minisoft-hp3000-save\":{\"source\":\"iana\"},\"application/vnd.mitsubishi.misty-guard.trustweb\":{\"source\":\"iana\"},\"application/vnd.mobius.daf\":{\"source\":\"iana\",\"extensions\":[\"daf\"]},\"application/vnd.mobius.dis\":{\"source\":\"iana\",\"extensions\":[\"dis\"]},\"application/vnd.mobius.mbk\":{\"source\":\"iana\",\"extensions\":[\"mbk\"]},\"application/vnd.mobius.mqy\":{\"source\":\"iana\",\"extensions\":[\"mqy\"]},\"application/vnd.mobius.msl\":{\"source\":\"iana\",\"extensions\":[\"msl\"]},\"application/vnd.mobius.plc\":{\"source\":\"iana\",\"extensions\":[\"plc\"]},\"application/vnd.mobius.txf\":{\"source\":\"iana\",\"extensions\":[\"txf\"]},\"application/vnd.mophun.application\":{\"source\":\"iana\",\"extensions\":[\"mpn\"]},\"application/vnd.mophun.certificate\":{\"source\":\"iana\",\"extensions\":[\"mpc\"]},\"application/vnd.motorola.flexsuite\":{\"source\":\"iana\"},\"application/vnd.motorola.flexsuite.adsi\":{\"source\":\"iana\"},\"application/vnd.motorola.flexsuite.fis\":{\"source\":\"iana\"},\"application/vnd.motorola.flexsuite.gotap\":{\"source\":\"iana\"},\"application/vnd.motorola.flexsuite.kmr\":{\"source\":\"iana\"},\"application/vnd.motorola.flexsuite.ttc\":{\"source\":\"iana\"},\"application/vnd.motorola.flexsuite.wem\":{\"source\":\"iana\"},\"application/vnd.motorola.iprm\":{\"source\":\"iana\"},\"application/vnd.mozilla.xul+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xul\"]},\"application/vnd.ms-3mfdocument\":{\"source\":\"iana\"},\"application/vnd.ms-artgalry\":{\"source\":\"iana\",\"extensions\":[\"cil\"]},\"application/vnd.ms-asf\":{\"source\":\"iana\"},\"application/vnd.ms-cab-compressed\":{\"source\":\"iana\",\"extensions\":[\"cab\"]},\"application/vnd.ms-color.iccprofile\":{\"source\":\"apache\"},\"application/vnd.ms-excel\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"xls\",\"xlm\",\"xla\",\"xlc\",\"xlt\",\"xlw\"]},\"application/vnd.ms-excel.addin.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"xlam\"]},\"application/vnd.ms-excel.sheet.binary.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"xlsb\"]},\"application/vnd.ms-excel.sheet.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"xlsm\"]},\"application/vnd.ms-excel.template.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"xltm\"]},\"application/vnd.ms-fontobject\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"eot\"]},\"application/vnd.ms-htmlhelp\":{\"source\":\"iana\",\"extensions\":[\"chm\"]},\"application/vnd.ms-ims\":{\"source\":\"iana\",\"extensions\":[\"ims\"]},\"application/vnd.ms-lrm\":{\"source\":\"iana\",\"extensions\":[\"lrm\"]},\"application/vnd.ms-office.activex+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ms-officetheme\":{\"source\":\"iana\",\"extensions\":[\"thmx\"]},\"application/vnd.ms-opentype\":{\"source\":\"apache\",\"compressible\":true},\"application/vnd.ms-outlook\":{\"compressible\":false,\"extensions\":[\"msg\"]},\"application/vnd.ms-package.obfuscated-opentype\":{\"source\":\"apache\"},\"application/vnd.ms-pki.seccat\":{\"source\":\"apache\",\"extensions\":[\"cat\"]},\"application/vnd.ms-pki.stl\":{\"source\":\"apache\",\"extensions\":[\"stl\"]},\"application/vnd.ms-playready.initiator+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ms-powerpoint\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"ppt\",\"pps\",\"pot\"]},\"application/vnd.ms-powerpoint.addin.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"ppam\"]},\"application/vnd.ms-powerpoint.presentation.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"pptm\"]},\"application/vnd.ms-powerpoint.slide.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"sldm\"]},\"application/vnd.ms-powerpoint.slideshow.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"ppsm\"]},\"application/vnd.ms-powerpoint.template.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"potm\"]},\"application/vnd.ms-printdevicecapabilities+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ms-printing.printticket+xml\":{\"source\":\"apache\",\"compressible\":true},\"application/vnd.ms-printschematicket+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.ms-project\":{\"source\":\"iana\",\"extensions\":[\"mpp\",\"mpt\"]},\"application/vnd.ms-tnef\":{\"source\":\"iana\"},\"application/vnd.ms-windows.devicepairing\":{\"source\":\"iana\"},\"application/vnd.ms-windows.nwprinting.oob\":{\"source\":\"iana\"},\"application/vnd.ms-windows.printerpairing\":{\"source\":\"iana\"},\"application/vnd.ms-windows.wsd.oob\":{\"source\":\"iana\"},\"application/vnd.ms-wmdrm.lic-chlg-req\":{\"source\":\"iana\"},\"application/vnd.ms-wmdrm.lic-resp\":{\"source\":\"iana\"},\"application/vnd.ms-wmdrm.meter-chlg-req\":{\"source\":\"iana\"},\"application/vnd.ms-wmdrm.meter-resp\":{\"source\":\"iana\"},\"application/vnd.ms-word.document.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"docm\"]},\"application/vnd.ms-word.template.macroenabled.12\":{\"source\":\"iana\",\"extensions\":[\"dotm\"]},\"application/vnd.ms-works\":{\"source\":\"iana\",\"extensions\":[\"wps\",\"wks\",\"wcm\",\"wdb\"]},\"application/vnd.ms-wpl\":{\"source\":\"iana\",\"extensions\":[\"wpl\"]},\"application/vnd.ms-xpsdocument\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"xps\"]},\"application/vnd.msa-disk-image\":{\"source\":\"iana\"},\"application/vnd.mseq\":{\"source\":\"iana\",\"extensions\":[\"mseq\"]},\"application/vnd.msign\":{\"source\":\"iana\"},\"application/vnd.multiad.creator\":{\"source\":\"iana\"},\"application/vnd.multiad.creator.cif\":{\"source\":\"iana\"},\"application/vnd.music-niff\":{\"source\":\"iana\"},\"application/vnd.musician\":{\"source\":\"iana\",\"extensions\":[\"mus\"]},\"application/vnd.muvee.style\":{\"source\":\"iana\",\"extensions\":[\"msty\"]},\"application/vnd.mynfc\":{\"source\":\"iana\",\"extensions\":[\"taglet\"]},\"application/vnd.ncd.control\":{\"source\":\"iana\"},\"application/vnd.ncd.reference\":{\"source\":\"iana\"},\"application/vnd.nearst.inv+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.nervana\":{\"source\":\"iana\"},\"application/vnd.netfpx\":{\"source\":\"iana\"},\"application/vnd.neurolanguage.nlu\":{\"source\":\"iana\",\"extensions\":[\"nlu\"]},\"application/vnd.nimn\":{\"source\":\"iana\"},\"application/vnd.nintendo.nitro.rom\":{\"source\":\"iana\"},\"application/vnd.nintendo.snes.rom\":{\"source\":\"iana\"},\"application/vnd.nitf\":{\"source\":\"iana\",\"extensions\":[\"ntf\",\"nitf\"]},\"application/vnd.noblenet-directory\":{\"source\":\"iana\",\"extensions\":[\"nnd\"]},\"application/vnd.noblenet-sealer\":{\"source\":\"iana\",\"extensions\":[\"nns\"]},\"application/vnd.noblenet-web\":{\"source\":\"iana\",\"extensions\":[\"nnw\"]},\"application/vnd.nokia.catalogs\":{\"source\":\"iana\"},\"application/vnd.nokia.conml+wbxml\":{\"source\":\"iana\"},\"application/vnd.nokia.conml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.nokia.iptv.config+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.nokia.isds-radio-presets\":{\"source\":\"iana\"},\"application/vnd.nokia.landmark+wbxml\":{\"source\":\"iana\"},\"application/vnd.nokia.landmark+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.nokia.landmarkcollection+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.nokia.n-gage.ac+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ac\"]},\"application/vnd.nokia.n-gage.data\":{\"source\":\"iana\",\"extensions\":[\"ngdat\"]},\"application/vnd.nokia.n-gage.symbian.install\":{\"source\":\"iana\",\"extensions\":[\"n-gage\"]},\"application/vnd.nokia.ncd\":{\"source\":\"iana\"},\"application/vnd.nokia.pcd+wbxml\":{\"source\":\"iana\"},\"application/vnd.nokia.pcd+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.nokia.radio-preset\":{\"source\":\"iana\",\"extensions\":[\"rpst\"]},\"application/vnd.nokia.radio-presets\":{\"source\":\"iana\",\"extensions\":[\"rpss\"]},\"application/vnd.novadigm.edm\":{\"source\":\"iana\",\"extensions\":[\"edm\"]},\"application/vnd.novadigm.edx\":{\"source\":\"iana\",\"extensions\":[\"edx\"]},\"application/vnd.novadigm.ext\":{\"source\":\"iana\",\"extensions\":[\"ext\"]},\"application/vnd.ntt-local.content-share\":{\"source\":\"iana\"},\"application/vnd.ntt-local.file-transfer\":{\"source\":\"iana\"},\"application/vnd.ntt-local.ogw_remote-access\":{\"source\":\"iana\"},\"application/vnd.ntt-local.sip-ta_remote\":{\"source\":\"iana\"},\"application/vnd.ntt-local.sip-ta_tcp_stream\":{\"source\":\"iana\"},\"application/vnd.oasis.opendocument.chart\":{\"source\":\"iana\",\"extensions\":[\"odc\"]},\"application/vnd.oasis.opendocument.chart-template\":{\"source\":\"iana\",\"extensions\":[\"otc\"]},\"application/vnd.oasis.opendocument.database\":{\"source\":\"iana\",\"extensions\":[\"odb\"]},\"application/vnd.oasis.opendocument.formula\":{\"source\":\"iana\",\"extensions\":[\"odf\"]},\"application/vnd.oasis.opendocument.formula-template\":{\"source\":\"iana\",\"extensions\":[\"odft\"]},\"application/vnd.oasis.opendocument.graphics\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"odg\"]},\"application/vnd.oasis.opendocument.graphics-template\":{\"source\":\"iana\",\"extensions\":[\"otg\"]},\"application/vnd.oasis.opendocument.image\":{\"source\":\"iana\",\"extensions\":[\"odi\"]},\"application/vnd.oasis.opendocument.image-template\":{\"source\":\"iana\",\"extensions\":[\"oti\"]},\"application/vnd.oasis.opendocument.presentation\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"odp\"]},\"application/vnd.oasis.opendocument.presentation-template\":{\"source\":\"iana\",\"extensions\":[\"otp\"]},\"application/vnd.oasis.opendocument.spreadsheet\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"ods\"]},\"application/vnd.oasis.opendocument.spreadsheet-template\":{\"source\":\"iana\",\"extensions\":[\"ots\"]},\"application/vnd.oasis.opendocument.text\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"odt\"]},\"application/vnd.oasis.opendocument.text-master\":{\"source\":\"iana\",\"extensions\":[\"odm\"]},\"application/vnd.oasis.opendocument.text-template\":{\"source\":\"iana\",\"extensions\":[\"ott\"]},\"application/vnd.oasis.opendocument.text-web\":{\"source\":\"iana\",\"extensions\":[\"oth\"]},\"application/vnd.obn\":{\"source\":\"iana\"},\"application/vnd.ocf+cbor\":{\"source\":\"iana\"},\"application/vnd.oci.image.manifest.v1+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oftn.l10n+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.contentaccessdownload+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.contentaccessstreaming+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.cspg-hexbinary\":{\"source\":\"iana\"},\"application/vnd.oipf.dae.svg+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.dae.xhtml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.mippvcontrolmessage+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.pae.gem\":{\"source\":\"iana\"},\"application/vnd.oipf.spdiscovery+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.spdlist+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.ueprofile+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oipf.userprofile+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.olpc-sugar\":{\"source\":\"iana\",\"extensions\":[\"xo\"]},\"application/vnd.oma-scws-config\":{\"source\":\"iana\"},\"application/vnd.oma-scws-http-request\":{\"source\":\"iana\"},\"application/vnd.oma-scws-http-response\":{\"source\":\"iana\"},\"application/vnd.oma.bcast.associated-procedure-parameter+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.bcast.drm-trigger+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.bcast.imd+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.bcast.ltkm\":{\"source\":\"iana\"},\"application/vnd.oma.bcast.notification+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.bcast.provisioningtrigger\":{\"source\":\"iana\"},\"application/vnd.oma.bcast.sgboot\":{\"source\":\"iana\"},\"application/vnd.oma.bcast.sgdd+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.bcast.sgdu\":{\"source\":\"iana\"},\"application/vnd.oma.bcast.simple-symbol-container\":{\"source\":\"iana\"},\"application/vnd.oma.bcast.smartcard-trigger+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.bcast.sprov+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.bcast.stkm\":{\"source\":\"iana\"},\"application/vnd.oma.cab-address-book+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.cab-feature-handler+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.cab-pcc+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.cab-subs-invite+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.cab-user-prefs+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.dcd\":{\"source\":\"iana\"},\"application/vnd.oma.dcdc\":{\"source\":\"iana\"},\"application/vnd.oma.dd2+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"dd2\"]},\"application/vnd.oma.drm.risd+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.group-usage-list+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.lwm2m+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.lwm2m+tlv\":{\"source\":\"iana\"},\"application/vnd.oma.pal+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.poc.detailed-progress-report+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.poc.final-report+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.poc.groups+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.poc.invocation-descriptor+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.poc.optimized-progress-report+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.push\":{\"source\":\"iana\"},\"application/vnd.oma.scidm.messages+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oma.xcap-directory+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.omads-email+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/vnd.omads-file+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/vnd.omads-folder+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/vnd.omaloc-supl-init\":{\"source\":\"iana\"},\"application/vnd.onepager\":{\"source\":\"iana\"},\"application/vnd.onepagertamp\":{\"source\":\"iana\"},\"application/vnd.onepagertamx\":{\"source\":\"iana\"},\"application/vnd.onepagertat\":{\"source\":\"iana\"},\"application/vnd.onepagertatp\":{\"source\":\"iana\"},\"application/vnd.onepagertatx\":{\"source\":\"iana\"},\"application/vnd.openblox.game+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"obgx\"]},\"application/vnd.openblox.game-binary\":{\"source\":\"iana\"},\"application/vnd.openeye.oeb\":{\"source\":\"iana\"},\"application/vnd.openofficeorg.extension\":{\"source\":\"apache\",\"extensions\":[\"oxt\"]},\"application/vnd.openstreetmap.data+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"osm\"]},\"application/vnd.openxmlformats-officedocument.custom-properties+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.customxmlproperties+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.drawing+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.drawingml.chart+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.drawingml.chartshapes+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.drawingml.diagramcolors+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.drawingml.diagramdata+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.drawingml.diagramlayout+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.drawingml.diagramstyle+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.extended-properties+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.commentauthors+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.comments+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.handoutmaster+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.notesmaster+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.notesslide+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.presentation\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"pptx\"]},\"application/vnd.openxmlformats-officedocument.presentationml.presentation.main+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.presprops+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.slide\":{\"source\":\"iana\",\"extensions\":[\"sldx\"]},\"application/vnd.openxmlformats-officedocument.presentationml.slide+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.slidelayout+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.slidemaster+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.slideshow\":{\"source\":\"iana\",\"extensions\":[\"ppsx\"]},\"application/vnd.openxmlformats-officedocument.presentationml.slideshow.main+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.slideupdateinfo+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.tablestyles+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.tags+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.template\":{\"source\":\"iana\",\"extensions\":[\"potx\"]},\"application/vnd.openxmlformats-officedocument.presentationml.template.main+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.presentationml.viewprops+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.calcchain+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.chartsheet+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.comments+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.connections+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.dialogsheet+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.externallink+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.pivotcachedefinition+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.pivotcacherecords+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.pivottable+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.querytable+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.revisionheaders+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.revisionlog+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.sharedstrings+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"xlsx\"]},\"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.sheetmetadata+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.table+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.tablesinglecells+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.template\":{\"source\":\"iana\",\"extensions\":[\"xltx\"]},\"application/vnd.openxmlformats-officedocument.spreadsheetml.template.main+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.usernames+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.volatiledependencies+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.theme+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.themeoverride+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.vmldrawing\":{\"source\":\"iana\"},\"application/vnd.openxmlformats-officedocument.wordprocessingml.comments+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.document\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"docx\"]},\"application/vnd.openxmlformats-officedocument.wordprocessingml.document.glossary+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.endnotes+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.fonttable+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.footer+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.footnotes+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.numbering+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.template\":{\"source\":\"iana\",\"extensions\":[\"dotx\"]},\"application/vnd.openxmlformats-officedocument.wordprocessingml.template.main+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-officedocument.wordprocessingml.websettings+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-package.core-properties+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-package.digital-signature-xmlsignature+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.openxmlformats-package.relationships+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oracle.resource+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.orange.indata\":{\"source\":\"iana\"},\"application/vnd.osa.netdeploy\":{\"source\":\"iana\"},\"application/vnd.osgeo.mapguide.package\":{\"source\":\"iana\",\"extensions\":[\"mgp\"]},\"application/vnd.osgi.bundle\":{\"source\":\"iana\"},\"application/vnd.osgi.dp\":{\"source\":\"iana\",\"extensions\":[\"dp\"]},\"application/vnd.osgi.subsystem\":{\"source\":\"iana\",\"extensions\":[\"esa\"]},\"application/vnd.otps.ct-kip+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.oxli.countgraph\":{\"source\":\"iana\"},\"application/vnd.pagerduty+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.palm\":{\"source\":\"iana\",\"extensions\":[\"pdb\",\"pqa\",\"oprc\"]},\"application/vnd.panoply\":{\"source\":\"iana\"},\"application/vnd.paos.xml\":{\"source\":\"iana\"},\"application/vnd.patentdive\":{\"source\":\"iana\"},\"application/vnd.patientecommsdoc\":{\"source\":\"iana\"},\"application/vnd.pawaafile\":{\"source\":\"iana\",\"extensions\":[\"paw\"]},\"application/vnd.pcos\":{\"source\":\"iana\"},\"application/vnd.pg.format\":{\"source\":\"iana\",\"extensions\":[\"str\"]},\"application/vnd.pg.osasli\":{\"source\":\"iana\",\"extensions\":[\"ei6\"]},\"application/vnd.piaccess.application-licence\":{\"source\":\"iana\"},\"application/vnd.picsel\":{\"source\":\"iana\",\"extensions\":[\"efif\"]},\"application/vnd.pmi.widget\":{\"source\":\"iana\",\"extensions\":[\"wg\"]},\"application/vnd.poc.group-advertisement+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.pocketlearn\":{\"source\":\"iana\",\"extensions\":[\"plf\"]},\"application/vnd.powerbuilder6\":{\"source\":\"iana\",\"extensions\":[\"pbd\"]},\"application/vnd.powerbuilder6-s\":{\"source\":\"iana\"},\"application/vnd.powerbuilder7\":{\"source\":\"iana\"},\"application/vnd.powerbuilder7-s\":{\"source\":\"iana\"},\"application/vnd.powerbuilder75\":{\"source\":\"iana\"},\"application/vnd.powerbuilder75-s\":{\"source\":\"iana\"},\"application/vnd.preminet\":{\"source\":\"iana\"},\"application/vnd.previewsystems.box\":{\"source\":\"iana\",\"extensions\":[\"box\"]},\"application/vnd.proteus.magazine\":{\"source\":\"iana\",\"extensions\":[\"mgz\"]},\"application/vnd.psfs\":{\"source\":\"iana\"},\"application/vnd.publishare-delta-tree\":{\"source\":\"iana\",\"extensions\":[\"qps\"]},\"application/vnd.pvi.ptid1\":{\"source\":\"iana\",\"extensions\":[\"ptid\"]},\"application/vnd.pwg-multiplexed\":{\"source\":\"iana\"},\"application/vnd.pwg-xhtml-print+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.qualcomm.brew-app-res\":{\"source\":\"iana\"},\"application/vnd.quarantainenet\":{\"source\":\"iana\"},\"application/vnd.quark.quarkxpress\":{\"source\":\"iana\",\"extensions\":[\"qxd\",\"qxt\",\"qwd\",\"qwt\",\"qxl\",\"qxb\"]},\"application/vnd.quobject-quoxdocument\":{\"source\":\"iana\"},\"application/vnd.radisys.moml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-audit+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-audit-conf+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-audit-conn+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-audit-dialog+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-audit-stream+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-conf+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-dialog+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-dialog-base+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-dialog-fax-detect+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-dialog-fax-sendrecv+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-dialog-group+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-dialog-speech+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.radisys.msml-dialog-transform+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.rainstor.data\":{\"source\":\"iana\"},\"application/vnd.rapid\":{\"source\":\"iana\"},\"application/vnd.rar\":{\"source\":\"iana\"},\"application/vnd.realvnc.bed\":{\"source\":\"iana\",\"extensions\":[\"bed\"]},\"application/vnd.recordare.musicxml\":{\"source\":\"iana\",\"extensions\":[\"mxl\"]},\"application/vnd.recordare.musicxml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"musicxml\"]},\"application/vnd.renlearn.rlprint\":{\"source\":\"iana\"},\"application/vnd.restful+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.rig.cryptonote\":{\"source\":\"iana\",\"extensions\":[\"cryptonote\"]},\"application/vnd.rim.cod\":{\"source\":\"apache\",\"extensions\":[\"cod\"]},\"application/vnd.rn-realmedia\":{\"source\":\"apache\",\"extensions\":[\"rm\"]},\"application/vnd.rn-realmedia-vbr\":{\"source\":\"apache\",\"extensions\":[\"rmvb\"]},\"application/vnd.route66.link66+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"link66\"]},\"application/vnd.rs-274x\":{\"source\":\"iana\"},\"application/vnd.ruckus.download\":{\"source\":\"iana\"},\"application/vnd.s3sms\":{\"source\":\"iana\"},\"application/vnd.sailingtracker.track\":{\"source\":\"iana\",\"extensions\":[\"st\"]},\"application/vnd.sar\":{\"source\":\"iana\"},\"application/vnd.sbm.cid\":{\"source\":\"iana\"},\"application/vnd.sbm.mid2\":{\"source\":\"iana\"},\"application/vnd.scribus\":{\"source\":\"iana\"},\"application/vnd.sealed.3df\":{\"source\":\"iana\"},\"application/vnd.sealed.csf\":{\"source\":\"iana\"},\"application/vnd.sealed.doc\":{\"source\":\"iana\"},\"application/vnd.sealed.eml\":{\"source\":\"iana\"},\"application/vnd.sealed.mht\":{\"source\":\"iana\"},\"application/vnd.sealed.net\":{\"source\":\"iana\"},\"application/vnd.sealed.ppt\":{\"source\":\"iana\"},\"application/vnd.sealed.tiff\":{\"source\":\"iana\"},\"application/vnd.sealed.xls\":{\"source\":\"iana\"},\"application/vnd.sealedmedia.softseal.html\":{\"source\":\"iana\"},\"application/vnd.sealedmedia.softseal.pdf\":{\"source\":\"iana\"},\"application/vnd.seemail\":{\"source\":\"iana\",\"extensions\":[\"see\"]},\"application/vnd.sema\":{\"source\":\"iana\",\"extensions\":[\"sema\"]},\"application/vnd.semd\":{\"source\":\"iana\",\"extensions\":[\"semd\"]},\"application/vnd.semf\":{\"source\":\"iana\",\"extensions\":[\"semf\"]},\"application/vnd.shade-save-file\":{\"source\":\"iana\"},\"application/vnd.shana.informed.formdata\":{\"source\":\"iana\",\"extensions\":[\"ifm\"]},\"application/vnd.shana.informed.formtemplate\":{\"source\":\"iana\",\"extensions\":[\"itp\"]},\"application/vnd.shana.informed.interchange\":{\"source\":\"iana\",\"extensions\":[\"iif\"]},\"application/vnd.shana.informed.package\":{\"source\":\"iana\",\"extensions\":[\"ipk\"]},\"application/vnd.shootproof+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.shopkick+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.shp\":{\"source\":\"iana\"},\"application/vnd.shx\":{\"source\":\"iana\"},\"application/vnd.sigrok.session\":{\"source\":\"iana\"},\"application/vnd.simtech-mindmapper\":{\"source\":\"iana\",\"extensions\":[\"twd\",\"twds\"]},\"application/vnd.siren+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.smaf\":{\"source\":\"iana\",\"extensions\":[\"mmf\"]},\"application/vnd.smart.notebook\":{\"source\":\"iana\"},\"application/vnd.smart.teacher\":{\"source\":\"iana\",\"extensions\":[\"teacher\"]},\"application/vnd.snesdev-page-table\":{\"source\":\"iana\"},\"application/vnd.software602.filler.form+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"fo\"]},\"application/vnd.software602.filler.form-xml-zip\":{\"source\":\"iana\"},\"application/vnd.solent.sdkm+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"sdkm\",\"sdkd\"]},\"application/vnd.spotfire.dxp\":{\"source\":\"iana\",\"extensions\":[\"dxp\"]},\"application/vnd.spotfire.sfs\":{\"source\":\"iana\",\"extensions\":[\"sfs\"]},\"application/vnd.sqlite3\":{\"source\":\"iana\"},\"application/vnd.sss-cod\":{\"source\":\"iana\"},\"application/vnd.sss-dtf\":{\"source\":\"iana\"},\"application/vnd.sss-ntf\":{\"source\":\"iana\"},\"application/vnd.stardivision.calc\":{\"source\":\"apache\",\"extensions\":[\"sdc\"]},\"application/vnd.stardivision.draw\":{\"source\":\"apache\",\"extensions\":[\"sda\"]},\"application/vnd.stardivision.impress\":{\"source\":\"apache\",\"extensions\":[\"sdd\"]},\"application/vnd.stardivision.math\":{\"source\":\"apache\",\"extensions\":[\"smf\"]},\"application/vnd.stardivision.writer\":{\"source\":\"apache\",\"extensions\":[\"sdw\",\"vor\"]},\"application/vnd.stardivision.writer-global\":{\"source\":\"apache\",\"extensions\":[\"sgl\"]},\"application/vnd.stepmania.package\":{\"source\":\"iana\",\"extensions\":[\"smzip\"]},\"application/vnd.stepmania.stepchart\":{\"source\":\"iana\",\"extensions\":[\"sm\"]},\"application/vnd.street-stream\":{\"source\":\"iana\"},\"application/vnd.sun.wadl+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"wadl\"]},\"application/vnd.sun.xml.calc\":{\"source\":\"apache\",\"extensions\":[\"sxc\"]},\"application/vnd.sun.xml.calc.template\":{\"source\":\"apache\",\"extensions\":[\"stc\"]},\"application/vnd.sun.xml.draw\":{\"source\":\"apache\",\"extensions\":[\"sxd\"]},\"application/vnd.sun.xml.draw.template\":{\"source\":\"apache\",\"extensions\":[\"std\"]},\"application/vnd.sun.xml.impress\":{\"source\":\"apache\",\"extensions\":[\"sxi\"]},\"application/vnd.sun.xml.impress.template\":{\"source\":\"apache\",\"extensions\":[\"sti\"]},\"application/vnd.sun.xml.math\":{\"source\":\"apache\",\"extensions\":[\"sxm\"]},\"application/vnd.sun.xml.writer\":{\"source\":\"apache\",\"extensions\":[\"sxw\"]},\"application/vnd.sun.xml.writer.global\":{\"source\":\"apache\",\"extensions\":[\"sxg\"]},\"application/vnd.sun.xml.writer.template\":{\"source\":\"apache\",\"extensions\":[\"stw\"]},\"application/vnd.sus-calendar\":{\"source\":\"iana\",\"extensions\":[\"sus\",\"susp\"]},\"application/vnd.svd\":{\"source\":\"iana\",\"extensions\":[\"svd\"]},\"application/vnd.swiftview-ics\":{\"source\":\"iana\"},\"application/vnd.symbian.install\":{\"source\":\"apache\",\"extensions\":[\"sis\",\"sisx\"]},\"application/vnd.syncml+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"xsm\"]},\"application/vnd.syncml.dm+wbxml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"extensions\":[\"bdm\"]},\"application/vnd.syncml.dm+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"xdm\"]},\"application/vnd.syncml.dm.notification\":{\"source\":\"iana\"},\"application/vnd.syncml.dmddf+wbxml\":{\"source\":\"iana\"},\"application/vnd.syncml.dmddf+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"ddf\"]},\"application/vnd.syncml.dmtnds+wbxml\":{\"source\":\"iana\"},\"application/vnd.syncml.dmtnds+xml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true},\"application/vnd.syncml.ds.notification\":{\"source\":\"iana\"},\"application/vnd.tableschema+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.tao.intent-module-archive\":{\"source\":\"iana\",\"extensions\":[\"tao\"]},\"application/vnd.tcpdump.pcap\":{\"source\":\"iana\",\"extensions\":[\"pcap\",\"cap\",\"dmp\"]},\"application/vnd.think-cell.ppttc+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.tmd.mediaflex.api+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.tml\":{\"source\":\"iana\"},\"application/vnd.tmobile-livetv\":{\"source\":\"iana\",\"extensions\":[\"tmo\"]},\"application/vnd.tri.onesource\":{\"source\":\"iana\"},\"application/vnd.trid.tpt\":{\"source\":\"iana\",\"extensions\":[\"tpt\"]},\"application/vnd.triscape.mxs\":{\"source\":\"iana\",\"extensions\":[\"mxs\"]},\"application/vnd.trueapp\":{\"source\":\"iana\",\"extensions\":[\"tra\"]},\"application/vnd.truedoc\":{\"source\":\"iana\"},\"application/vnd.ubisoft.webplayer\":{\"source\":\"iana\"},\"application/vnd.ufdl\":{\"source\":\"iana\",\"extensions\":[\"ufd\",\"ufdl\"]},\"application/vnd.uiq.theme\":{\"source\":\"iana\",\"extensions\":[\"utz\"]},\"application/vnd.umajin\":{\"source\":\"iana\",\"extensions\":[\"umj\"]},\"application/vnd.unity\":{\"source\":\"iana\",\"extensions\":[\"unityweb\"]},\"application/vnd.uoml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"uoml\"]},\"application/vnd.uplanet.alert\":{\"source\":\"iana\"},\"application/vnd.uplanet.alert-wbxml\":{\"source\":\"iana\"},\"application/vnd.uplanet.bearer-choice\":{\"source\":\"iana\"},\"application/vnd.uplanet.bearer-choice-wbxml\":{\"source\":\"iana\"},\"application/vnd.uplanet.cacheop\":{\"source\":\"iana\"},\"application/vnd.uplanet.cacheop-wbxml\":{\"source\":\"iana\"},\"application/vnd.uplanet.channel\":{\"source\":\"iana\"},\"application/vnd.uplanet.channel-wbxml\":{\"source\":\"iana\"},\"application/vnd.uplanet.list\":{\"source\":\"iana\"},\"application/vnd.uplanet.list-wbxml\":{\"source\":\"iana\"},\"application/vnd.uplanet.listcmd\":{\"source\":\"iana\"},\"application/vnd.uplanet.listcmd-wbxml\":{\"source\":\"iana\"},\"application/vnd.uplanet.signal\":{\"source\":\"iana\"},\"application/vnd.uri-map\":{\"source\":\"iana\"},\"application/vnd.valve.source.material\":{\"source\":\"iana\"},\"application/vnd.vcx\":{\"source\":\"iana\",\"extensions\":[\"vcx\"]},\"application/vnd.vd-study\":{\"source\":\"iana\"},\"application/vnd.vectorworks\":{\"source\":\"iana\"},\"application/vnd.vel+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.verimatrix.vcas\":{\"source\":\"iana\"},\"application/vnd.veryant.thin\":{\"source\":\"iana\"},\"application/vnd.ves.encrypted\":{\"source\":\"iana\"},\"application/vnd.vidsoft.vidconference\":{\"source\":\"iana\"},\"application/vnd.visio\":{\"source\":\"iana\",\"extensions\":[\"vsd\",\"vst\",\"vss\",\"vsw\"]},\"application/vnd.visionary\":{\"source\":\"iana\",\"extensions\":[\"vis\"]},\"application/vnd.vividence.scriptfile\":{\"source\":\"iana\"},\"application/vnd.vsf\":{\"source\":\"iana\",\"extensions\":[\"vsf\"]},\"application/vnd.wap.sic\":{\"source\":\"iana\"},\"application/vnd.wap.slc\":{\"source\":\"iana\"},\"application/vnd.wap.wbxml\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"extensions\":[\"wbxml\"]},\"application/vnd.wap.wmlc\":{\"source\":\"iana\",\"extensions\":[\"wmlc\"]},\"application/vnd.wap.wmlscriptc\":{\"source\":\"iana\",\"extensions\":[\"wmlsc\"]},\"application/vnd.webturbo\":{\"source\":\"iana\",\"extensions\":[\"wtb\"]},\"application/vnd.wfa.p2p\":{\"source\":\"iana\"},\"application/vnd.wfa.wsc\":{\"source\":\"iana\"},\"application/vnd.windows.devicepairing\":{\"source\":\"iana\"},\"application/vnd.wmc\":{\"source\":\"iana\"},\"application/vnd.wmf.bootstrap\":{\"source\":\"iana\"},\"application/vnd.wolfram.mathematica\":{\"source\":\"iana\"},\"application/vnd.wolfram.mathematica.package\":{\"source\":\"iana\"},\"application/vnd.wolfram.player\":{\"source\":\"iana\",\"extensions\":[\"nbp\"]},\"application/vnd.wordperfect\":{\"source\":\"iana\",\"extensions\":[\"wpd\"]},\"application/vnd.wqd\":{\"source\":\"iana\",\"extensions\":[\"wqd\"]},\"application/vnd.wrq-hp3000-labelled\":{\"source\":\"iana\"},\"application/vnd.wt.stf\":{\"source\":\"iana\",\"extensions\":[\"stf\"]},\"application/vnd.wv.csp+wbxml\":{\"source\":\"iana\"},\"application/vnd.wv.csp+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.wv.ssp+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.xacml+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.xara\":{\"source\":\"iana\",\"extensions\":[\"xar\"]},\"application/vnd.xfdl\":{\"source\":\"iana\",\"extensions\":[\"xfdl\"]},\"application/vnd.xfdl.webform\":{\"source\":\"iana\"},\"application/vnd.xmi+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/vnd.xmpie.cpkg\":{\"source\":\"iana\"},\"application/vnd.xmpie.dpkg\":{\"source\":\"iana\"},\"application/vnd.xmpie.plan\":{\"source\":\"iana\"},\"application/vnd.xmpie.ppkg\":{\"source\":\"iana\"},\"application/vnd.xmpie.xlim\":{\"source\":\"iana\"},\"application/vnd.yamaha.hv-dic\":{\"source\":\"iana\",\"extensions\":[\"hvd\"]},\"application/vnd.yamaha.hv-script\":{\"source\":\"iana\",\"extensions\":[\"hvs\"]},\"application/vnd.yamaha.hv-voice\":{\"source\":\"iana\",\"extensions\":[\"hvp\"]},\"application/vnd.yamaha.openscoreformat\":{\"source\":\"iana\",\"extensions\":[\"osf\"]},\"application/vnd.yamaha.openscoreformat.osfpvg+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"osfpvg\"]},\"application/vnd.yamaha.remote-setup\":{\"source\":\"iana\"},\"application/vnd.yamaha.smaf-audio\":{\"source\":\"iana\",\"extensions\":[\"saf\"]},\"application/vnd.yamaha.smaf-phrase\":{\"source\":\"iana\",\"extensions\":[\"spf\"]},\"application/vnd.yamaha.through-ngn\":{\"source\":\"iana\"},\"application/vnd.yamaha.tunnel-udpencap\":{\"source\":\"iana\"},\"application/vnd.yaoweme\":{\"source\":\"iana\"},\"application/vnd.yellowriver-custom-menu\":{\"source\":\"iana\",\"extensions\":[\"cmp\"]},\"application/vnd.youtube.yt\":{\"source\":\"iana\"},\"application/vnd.zul\":{\"source\":\"iana\",\"extensions\":[\"zir\",\"zirz\"]},\"application/vnd.zzazz.deck+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"zaz\"]},\"application/voicexml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"vxml\"]},\"application/voucher-cms+json\":{\"source\":\"iana\",\"compressible\":true},\"application/vq-rtcpxr\":{\"source\":\"iana\"},\"application/wasm\":{\"compressible\":true,\"extensions\":[\"wasm\"]},\"application/watcherinfo+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/webpush-options+json\":{\"source\":\"iana\",\"compressible\":true},\"application/whoispp-query\":{\"source\":\"iana\"},\"application/whoispp-response\":{\"source\":\"iana\"},\"application/widget\":{\"source\":\"iana\",\"extensions\":[\"wgt\"]},\"application/winhlp\":{\"source\":\"apache\",\"extensions\":[\"hlp\"]},\"application/wita\":{\"source\":\"iana\"},\"application/wordperfect5.1\":{\"source\":\"iana\"},\"application/wsdl+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"wsdl\"]},\"application/wspolicy+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"wspolicy\"]},\"application/x-7z-compressed\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"7z\"]},\"application/x-abiword\":{\"source\":\"apache\",\"extensions\":[\"abw\"]},\"application/x-ace-compressed\":{\"source\":\"apache\",\"extensions\":[\"ace\"]},\"application/x-amf\":{\"source\":\"apache\"},\"application/x-apple-diskimage\":{\"source\":\"apache\",\"extensions\":[\"dmg\"]},\"application/x-arj\":{\"compressible\":false,\"extensions\":[\"arj\"]},\"application/x-authorware-bin\":{\"source\":\"apache\",\"extensions\":[\"aab\",\"x32\",\"u32\",\"vox\"]},\"application/x-authorware-map\":{\"source\":\"apache\",\"extensions\":[\"aam\"]},\"application/x-authorware-seg\":{\"source\":\"apache\",\"extensions\":[\"aas\"]},\"application/x-bcpio\":{\"source\":\"apache\",\"extensions\":[\"bcpio\"]},\"application/x-bdoc\":{\"compressible\":false,\"extensions\":[\"bdoc\"]},\"application/x-bittorrent\":{\"source\":\"apache\",\"extensions\":[\"torrent\"]},\"application/x-blorb\":{\"source\":\"apache\",\"extensions\":[\"blb\",\"blorb\"]},\"application/x-bzip\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"bz\"]},\"application/x-bzip2\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"bz2\",\"boz\"]},\"application/x-cbr\":{\"source\":\"apache\",\"extensions\":[\"cbr\",\"cba\",\"cbt\",\"cbz\",\"cb7\"]},\"application/x-cdlink\":{\"source\":\"apache\",\"extensions\":[\"vcd\"]},\"application/x-cfs-compressed\":{\"source\":\"apache\",\"extensions\":[\"cfs\"]},\"application/x-chat\":{\"source\":\"apache\",\"extensions\":[\"chat\"]},\"application/x-chess-pgn\":{\"source\":\"apache\",\"extensions\":[\"pgn\"]},\"application/x-chrome-extension\":{\"extensions\":[\"crx\"]},\"application/x-cocoa\":{\"source\":\"nginx\",\"extensions\":[\"cco\"]},\"application/x-compress\":{\"source\":\"apache\"},\"application/x-conference\":{\"source\":\"apache\",\"extensions\":[\"nsc\"]},\"application/x-cpio\":{\"source\":\"apache\",\"extensions\":[\"cpio\"]},\"application/x-csh\":{\"source\":\"apache\",\"extensions\":[\"csh\"]},\"application/x-deb\":{\"compressible\":false},\"application/x-debian-package\":{\"source\":\"apache\",\"extensions\":[\"deb\",\"udeb\"]},\"application/x-dgc-compressed\":{\"source\":\"apache\",\"extensions\":[\"dgc\"]},\"application/x-director\":{\"source\":\"apache\",\"extensions\":[\"dir\",\"dcr\",\"dxr\",\"cst\",\"cct\",\"cxt\",\"w3d\",\"fgd\",\"swa\"]},\"application/x-doom\":{\"source\":\"apache\",\"extensions\":[\"wad\"]},\"application/x-dtbncx+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"ncx\"]},\"application/x-dtbook+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"dtb\"]},\"application/x-dtbresource+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"res\"]},\"application/x-dvi\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"dvi\"]},\"application/x-envoy\":{\"source\":\"apache\",\"extensions\":[\"evy\"]},\"application/x-eva\":{\"source\":\"apache\",\"extensions\":[\"eva\"]},\"application/x-font-bdf\":{\"source\":\"apache\",\"extensions\":[\"bdf\"]},\"application/x-font-dos\":{\"source\":\"apache\"},\"application/x-font-framemaker\":{\"source\":\"apache\"},\"application/x-font-ghostscript\":{\"source\":\"apache\",\"extensions\":[\"gsf\"]},\"application/x-font-libgrx\":{\"source\":\"apache\"},\"application/x-font-linux-psf\":{\"source\":\"apache\",\"extensions\":[\"psf\"]},\"application/x-font-pcf\":{\"source\":\"apache\",\"extensions\":[\"pcf\"]},\"application/x-font-snf\":{\"source\":\"apache\",\"extensions\":[\"snf\"]},\"application/x-font-speedo\":{\"source\":\"apache\"},\"application/x-font-sunos-news\":{\"source\":\"apache\"},\"application/x-font-type1\":{\"source\":\"apache\",\"extensions\":[\"pfa\",\"pfb\",\"pfm\",\"afm\"]},\"application/x-font-vfont\":{\"source\":\"apache\"},\"application/x-freearc\":{\"source\":\"apache\",\"extensions\":[\"arc\"]},\"application/x-futuresplash\":{\"source\":\"apache\",\"extensions\":[\"spl\"]},\"application/x-gca-compressed\":{\"source\":\"apache\",\"extensions\":[\"gca\"]},\"application/x-glulx\":{\"source\":\"apache\",\"extensions\":[\"ulx\"]},\"application/x-gnumeric\":{\"source\":\"apache\",\"extensions\":[\"gnumeric\"]},\"application/x-gramps-xml\":{\"source\":\"apache\",\"extensions\":[\"gramps\"]},\"application/x-gtar\":{\"source\":\"apache\",\"extensions\":[\"gtar\"]},\"application/x-gzip\":{\"source\":\"apache\"},\"application/x-hdf\":{\"source\":\"apache\",\"extensions\":[\"hdf\"]},\"application/x-httpd-php\":{\"compressible\":true,\"extensions\":[\"php\"]},\"application/x-install-instructions\":{\"source\":\"apache\",\"extensions\":[\"install\"]},\"application/x-iso9660-image\":{\"source\":\"apache\",\"extensions\":[\"iso\"]},\"application/x-java-archive-diff\":{\"source\":\"nginx\",\"extensions\":[\"jardiff\"]},\"application/x-java-jnlp-file\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"jnlp\"]},\"application/x-javascript\":{\"compressible\":true},\"application/x-keepass2\":{\"extensions\":[\"kdbx\"]},\"application/x-latex\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"latex\"]},\"application/x-lua-bytecode\":{\"extensions\":[\"luac\"]},\"application/x-lzh-compressed\":{\"source\":\"apache\",\"extensions\":[\"lzh\",\"lha\"]},\"application/x-makeself\":{\"source\":\"nginx\",\"extensions\":[\"run\"]},\"application/x-mie\":{\"source\":\"apache\",\"extensions\":[\"mie\"]},\"application/x-mobipocket-ebook\":{\"source\":\"apache\",\"extensions\":[\"prc\",\"mobi\"]},\"application/x-mpegurl\":{\"compressible\":false},\"application/x-ms-application\":{\"source\":\"apache\",\"extensions\":[\"application\"]},\"application/x-ms-shortcut\":{\"source\":\"apache\",\"extensions\":[\"lnk\"]},\"application/x-ms-wmd\":{\"source\":\"apache\",\"extensions\":[\"wmd\"]},\"application/x-ms-wmz\":{\"source\":\"apache\",\"extensions\":[\"wmz\"]},\"application/x-ms-xbap\":{\"source\":\"apache\",\"extensions\":[\"xbap\"]},\"application/x-msaccess\":{\"source\":\"apache\",\"extensions\":[\"mdb\"]},\"application/x-msbinder\":{\"source\":\"apache\",\"extensions\":[\"obd\"]},\"application/x-mscardfile\":{\"source\":\"apache\",\"extensions\":[\"crd\"]},\"application/x-msclip\":{\"source\":\"apache\",\"extensions\":[\"clp\"]},\"application/x-msdos-program\":{\"extensions\":[\"exe\"]},\"application/x-msdownload\":{\"source\":\"apache\",\"extensions\":[\"exe\",\"dll\",\"com\",\"bat\",\"msi\"]},\"application/x-msmediaview\":{\"source\":\"apache\",\"extensions\":[\"mvb\",\"m13\",\"m14\"]},\"application/x-msmetafile\":{\"source\":\"apache\",\"extensions\":[\"wmf\",\"wmz\",\"emf\",\"emz\"]},\"application/x-msmoney\":{\"source\":\"apache\",\"extensions\":[\"mny\"]},\"application/x-mspublisher\":{\"source\":\"apache\",\"extensions\":[\"pub\"]},\"application/x-msschedule\":{\"source\":\"apache\",\"extensions\":[\"scd\"]},\"application/x-msterminal\":{\"source\":\"apache\",\"extensions\":[\"trm\"]},\"application/x-mswrite\":{\"source\":\"apache\",\"extensions\":[\"wri\"]},\"application/x-netcdf\":{\"source\":\"apache\",\"extensions\":[\"nc\",\"cdf\"]},\"application/x-ns-proxy-autoconfig\":{\"compressible\":true,\"extensions\":[\"pac\"]},\"application/x-nzb\":{\"source\":\"apache\",\"extensions\":[\"nzb\"]},\"application/x-perl\":{\"source\":\"nginx\",\"extensions\":[\"pl\",\"pm\"]},\"application/x-pilot\":{\"source\":\"nginx\",\"extensions\":[\"prc\",\"pdb\"]},\"application/x-pkcs12\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"p12\",\"pfx\"]},\"application/x-pkcs7-certificates\":{\"source\":\"apache\",\"extensions\":[\"p7b\",\"spc\"]},\"application/x-pkcs7-certreqresp\":{\"source\":\"apache\",\"extensions\":[\"p7r\"]},\"application/x-pki-message\":{\"source\":\"iana\"},\"application/x-rar-compressed\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"rar\"]},\"application/x-redhat-package-manager\":{\"source\":\"nginx\",\"extensions\":[\"rpm\"]},\"application/x-research-info-systems\":{\"source\":\"apache\",\"extensions\":[\"ris\"]},\"application/x-sea\":{\"source\":\"nginx\",\"extensions\":[\"sea\"]},\"application/x-sh\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"sh\"]},\"application/x-shar\":{\"source\":\"apache\",\"extensions\":[\"shar\"]},\"application/x-shockwave-flash\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"swf\"]},\"application/x-silverlight-app\":{\"source\":\"apache\",\"extensions\":[\"xap\"]},\"application/x-sql\":{\"source\":\"apache\",\"extensions\":[\"sql\"]},\"application/x-stuffit\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"sit\"]},\"application/x-stuffitx\":{\"source\":\"apache\",\"extensions\":[\"sitx\"]},\"application/x-subrip\":{\"source\":\"apache\",\"extensions\":[\"srt\"]},\"application/x-sv4cpio\":{\"source\":\"apache\",\"extensions\":[\"sv4cpio\"]},\"application/x-sv4crc\":{\"source\":\"apache\",\"extensions\":[\"sv4crc\"]},\"application/x-t3vm-image\":{\"source\":\"apache\",\"extensions\":[\"t3\"]},\"application/x-tads\":{\"source\":\"apache\",\"extensions\":[\"gam\"]},\"application/x-tar\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"tar\"]},\"application/x-tcl\":{\"source\":\"apache\",\"extensions\":[\"tcl\",\"tk\"]},\"application/x-tex\":{\"source\":\"apache\",\"extensions\":[\"tex\"]},\"application/x-tex-tfm\":{\"source\":\"apache\",\"extensions\":[\"tfm\"]},\"application/x-texinfo\":{\"source\":\"apache\",\"extensions\":[\"texinfo\",\"texi\"]},\"application/x-tgif\":{\"source\":\"apache\",\"extensions\":[\"obj\"]},\"application/x-ustar\":{\"source\":\"apache\",\"extensions\":[\"ustar\"]},\"application/x-virtualbox-hdd\":{\"compressible\":true,\"extensions\":[\"hdd\"]},\"application/x-virtualbox-ova\":{\"compressible\":true,\"extensions\":[\"ova\"]},\"application/x-virtualbox-ovf\":{\"compressible\":true,\"extensions\":[\"ovf\"]},\"application/x-virtualbox-vbox\":{\"compressible\":true,\"extensions\":[\"vbox\"]},\"application/x-virtualbox-vbox-extpack\":{\"compressible\":false,\"extensions\":[\"vbox-extpack\"]},\"application/x-virtualbox-vdi\":{\"compressible\":true,\"extensions\":[\"vdi\"]},\"application/x-virtualbox-vhd\":{\"compressible\":true,\"extensions\":[\"vhd\"]},\"application/x-virtualbox-vmdk\":{\"compressible\":true,\"extensions\":[\"vmdk\"]},\"application/x-wais-source\":{\"source\":\"apache\",\"extensions\":[\"src\"]},\"application/x-web-app-manifest+json\":{\"compressible\":true,\"extensions\":[\"webapp\"]},\"application/x-www-form-urlencoded\":{\"source\":\"iana\",\"compressible\":true},\"application/x-x509-ca-cert\":{\"source\":\"iana\",\"extensions\":[\"der\",\"crt\",\"pem\"]},\"application/x-x509-ca-ra-cert\":{\"source\":\"iana\"},\"application/x-x509-next-ca-cert\":{\"source\":\"iana\"},\"application/x-xfig\":{\"source\":\"apache\",\"extensions\":[\"fig\"]},\"application/x-xliff+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"xlf\"]},\"application/x-xpinstall\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"xpi\"]},\"application/x-xz\":{\"source\":\"apache\",\"extensions\":[\"xz\"]},\"application/x-zmachine\":{\"source\":\"apache\",\"extensions\":[\"z1\",\"z2\",\"z3\",\"z4\",\"z5\",\"z6\",\"z7\",\"z8\"]},\"application/x400-bp\":{\"source\":\"iana\"},\"application/xacml+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/xaml+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"xaml\"]},\"application/xcap-att+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xav\"]},\"application/xcap-caps+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xca\"]},\"application/xcap-diff+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xdf\"]},\"application/xcap-el+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xel\"]},\"application/xcap-error+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xer\"]},\"application/xcap-ns+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xns\"]},\"application/xcon-conference-info+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/xcon-conference-info-diff+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/xenc+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xenc\"]},\"application/xhtml+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xhtml\",\"xht\"]},\"application/xhtml-voice+xml\":{\"source\":\"apache\",\"compressible\":true},\"application/xliff+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xlf\"]},\"application/xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xml\",\"xsl\",\"xsd\",\"rng\"]},\"application/xml-dtd\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"dtd\"]},\"application/xml-external-parsed-entity\":{\"source\":\"iana\"},\"application/xml-patch+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/xmpp+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/xop+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xop\"]},\"application/xproc+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"xpl\"]},\"application/xslt+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xslt\"]},\"application/xspf+xml\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"xspf\"]},\"application/xv+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"mxml\",\"xhvml\",\"xvml\",\"xvm\"]},\"application/yang\":{\"source\":\"iana\",\"extensions\":[\"yang\"]},\"application/yang-data+json\":{\"source\":\"iana\",\"compressible\":true},\"application/yang-data+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/yang-patch+json\":{\"source\":\"iana\",\"compressible\":true},\"application/yang-patch+xml\":{\"source\":\"iana\",\"compressible\":true},\"application/yin+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"yin\"]},\"application/zip\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"zip\"]},\"application/zlib\":{\"source\":\"iana\"},\"application/zstd\":{\"source\":\"iana\"},\"audio/1d-interleaved-parityfec\":{\"source\":\"iana\"},\"audio/32kadpcm\":{\"source\":\"iana\"},\"audio/3gpp\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"3gpp\"]},\"audio/3gpp2\":{\"source\":\"iana\"},\"audio/aac\":{\"source\":\"iana\"},\"audio/ac3\":{\"source\":\"iana\"},\"audio/adpcm\":{\"source\":\"apache\",\"extensions\":[\"adp\"]},\"audio/amr\":{\"source\":\"iana\"},\"audio/amr-wb\":{\"source\":\"iana\"},\"audio/amr-wb+\":{\"source\":\"iana\"},\"audio/aptx\":{\"source\":\"iana\"},\"audio/asc\":{\"source\":\"iana\"},\"audio/atrac-advanced-lossless\":{\"source\":\"iana\"},\"audio/atrac-x\":{\"source\":\"iana\"},\"audio/atrac3\":{\"source\":\"iana\"},\"audio/basic\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"au\",\"snd\"]},\"audio/bv16\":{\"source\":\"iana\"},\"audio/bv32\":{\"source\":\"iana\"},\"audio/clearmode\":{\"source\":\"iana\"},\"audio/cn\":{\"source\":\"iana\"},\"audio/dat12\":{\"source\":\"iana\"},\"audio/dls\":{\"source\":\"iana\"},\"audio/dsr-es201108\":{\"source\":\"iana\"},\"audio/dsr-es202050\":{\"source\":\"iana\"},\"audio/dsr-es202211\":{\"source\":\"iana\"},\"audio/dsr-es202212\":{\"source\":\"iana\"},\"audio/dv\":{\"source\":\"iana\"},\"audio/dvi4\":{\"source\":\"iana\"},\"audio/eac3\":{\"source\":\"iana\"},\"audio/encaprtp\":{\"source\":\"iana\"},\"audio/evrc\":{\"source\":\"iana\"},\"audio/evrc-qcp\":{\"source\":\"iana\"},\"audio/evrc0\":{\"source\":\"iana\"},\"audio/evrc1\":{\"source\":\"iana\"},\"audio/evrcb\":{\"source\":\"iana\"},\"audio/evrcb0\":{\"source\":\"iana\"},\"audio/evrcb1\":{\"source\":\"iana\"},\"audio/evrcnw\":{\"source\":\"iana\"},\"audio/evrcnw0\":{\"source\":\"iana\"},\"audio/evrcnw1\":{\"source\":\"iana\"},\"audio/evrcwb\":{\"source\":\"iana\"},\"audio/evrcwb0\":{\"source\":\"iana\"},\"audio/evrcwb1\":{\"source\":\"iana\"},\"audio/evs\":{\"source\":\"iana\"},\"audio/flexfec\":{\"source\":\"iana\"},\"audio/fwdred\":{\"source\":\"iana\"},\"audio/g711-0\":{\"source\":\"iana\"},\"audio/g719\":{\"source\":\"iana\"},\"audio/g722\":{\"source\":\"iana\"},\"audio/g7221\":{\"source\":\"iana\"},\"audio/g723\":{\"source\":\"iana\"},\"audio/g726-16\":{\"source\":\"iana\"},\"audio/g726-24\":{\"source\":\"iana\"},\"audio/g726-32\":{\"source\":\"iana\"},\"audio/g726-40\":{\"source\":\"iana\"},\"audio/g728\":{\"source\":\"iana\"},\"audio/g729\":{\"source\":\"iana\"},\"audio/g7291\":{\"source\":\"iana\"},\"audio/g729d\":{\"source\":\"iana\"},\"audio/g729e\":{\"source\":\"iana\"},\"audio/gsm\":{\"source\":\"iana\"},\"audio/gsm-efr\":{\"source\":\"iana\"},\"audio/gsm-hr-08\":{\"source\":\"iana\"},\"audio/ilbc\":{\"source\":\"iana\"},\"audio/ip-mr_v2.5\":{\"source\":\"iana\"},\"audio/isac\":{\"source\":\"apache\"},\"audio/l16\":{\"source\":\"iana\"},\"audio/l20\":{\"source\":\"iana\"},\"audio/l24\":{\"source\":\"iana\",\"compressible\":false},\"audio/l8\":{\"source\":\"iana\"},\"audio/lpc\":{\"source\":\"iana\"},\"audio/melp\":{\"source\":\"iana\"},\"audio/melp1200\":{\"source\":\"iana\"},\"audio/melp2400\":{\"source\":\"iana\"},\"audio/melp600\":{\"source\":\"iana\"},\"audio/mhas\":{\"source\":\"iana\"},\"audio/midi\":{\"source\":\"apache\",\"extensions\":[\"mid\",\"midi\",\"kar\",\"rmi\"]},\"audio/mobile-xmf\":{\"source\":\"iana\",\"extensions\":[\"mxmf\"]},\"audio/mp3\":{\"compressible\":false,\"extensions\":[\"mp3\"]},\"audio/mp4\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"m4a\",\"mp4a\"]},\"audio/mp4a-latm\":{\"source\":\"iana\"},\"audio/mpa\":{\"source\":\"iana\"},\"audio/mpa-robust\":{\"source\":\"iana\"},\"audio/mpeg\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"mpga\",\"mp2\",\"mp2a\",\"mp3\",\"m2a\",\"m3a\"]},\"audio/mpeg4-generic\":{\"source\":\"iana\"},\"audio/musepack\":{\"source\":\"apache\"},\"audio/ogg\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"oga\",\"ogg\",\"spx\"]},\"audio/opus\":{\"source\":\"iana\"},\"audio/parityfec\":{\"source\":\"iana\"},\"audio/pcma\":{\"source\":\"iana\"},\"audio/pcma-wb\":{\"source\":\"iana\"},\"audio/pcmu\":{\"source\":\"iana\"},\"audio/pcmu-wb\":{\"source\":\"iana\"},\"audio/prs.sid\":{\"source\":\"iana\"},\"audio/qcelp\":{\"source\":\"iana\"},\"audio/raptorfec\":{\"source\":\"iana\"},\"audio/red\":{\"source\":\"iana\"},\"audio/rtp-enc-aescm128\":{\"source\":\"iana\"},\"audio/rtp-midi\":{\"source\":\"iana\"},\"audio/rtploopback\":{\"source\":\"iana\"},\"audio/rtx\":{\"source\":\"iana\"},\"audio/s3m\":{\"source\":\"apache\",\"extensions\":[\"s3m\"]},\"audio/silk\":{\"source\":\"apache\",\"extensions\":[\"sil\"]},\"audio/smv\":{\"source\":\"iana\"},\"audio/smv-qcp\":{\"source\":\"iana\"},\"audio/smv0\":{\"source\":\"iana\"},\"audio/sp-midi\":{\"source\":\"iana\"},\"audio/speex\":{\"source\":\"iana\"},\"audio/t140c\":{\"source\":\"iana\"},\"audio/t38\":{\"source\":\"iana\"},\"audio/telephone-event\":{\"source\":\"iana\"},\"audio/tetra_acelp\":{\"source\":\"iana\"},\"audio/tetra_acelp_bb\":{\"source\":\"iana\"},\"audio/tone\":{\"source\":\"iana\"},\"audio/uemclip\":{\"source\":\"iana\"},\"audio/ulpfec\":{\"source\":\"iana\"},\"audio/usac\":{\"source\":\"iana\"},\"audio/vdvi\":{\"source\":\"iana\"},\"audio/vmr-wb\":{\"source\":\"iana\"},\"audio/vnd.3gpp.iufp\":{\"source\":\"iana\"},\"audio/vnd.4sb\":{\"source\":\"iana\"},\"audio/vnd.audiokoz\":{\"source\":\"iana\"},\"audio/vnd.celp\":{\"source\":\"iana\"},\"audio/vnd.cisco.nse\":{\"source\":\"iana\"},\"audio/vnd.cmles.radio-events\":{\"source\":\"iana\"},\"audio/vnd.cns.anp1\":{\"source\":\"iana\"},\"audio/vnd.cns.inf1\":{\"source\":\"iana\"},\"audio/vnd.dece.audio\":{\"source\":\"iana\",\"extensions\":[\"uva\",\"uvva\"]},\"audio/vnd.digital-winds\":{\"source\":\"iana\",\"extensions\":[\"eol\"]},\"audio/vnd.dlna.adts\":{\"source\":\"iana\"},\"audio/vnd.dolby.heaac.1\":{\"source\":\"iana\"},\"audio/vnd.dolby.heaac.2\":{\"source\":\"iana\"},\"audio/vnd.dolby.mlp\":{\"source\":\"iana\"},\"audio/vnd.dolby.mps\":{\"source\":\"iana\"},\"audio/vnd.dolby.pl2\":{\"source\":\"iana\"},\"audio/vnd.dolby.pl2x\":{\"source\":\"iana\"},\"audio/vnd.dolby.pl2z\":{\"source\":\"iana\"},\"audio/vnd.dolby.pulse.1\":{\"source\":\"iana\"},\"audio/vnd.dra\":{\"source\":\"iana\",\"extensions\":[\"dra\"]},\"audio/vnd.dts\":{\"source\":\"iana\",\"extensions\":[\"dts\"]},\"audio/vnd.dts.hd\":{\"source\":\"iana\",\"extensions\":[\"dtshd\"]},\"audio/vnd.dts.uhd\":{\"source\":\"iana\"},\"audio/vnd.dvb.file\":{\"source\":\"iana\"},\"audio/vnd.everad.plj\":{\"source\":\"iana\"},\"audio/vnd.hns.audio\":{\"source\":\"iana\"},\"audio/vnd.lucent.voice\":{\"source\":\"iana\",\"extensions\":[\"lvp\"]},\"audio/vnd.ms-playready.media.pya\":{\"source\":\"iana\",\"extensions\":[\"pya\"]},\"audio/vnd.nokia.mobile-xmf\":{\"source\":\"iana\"},\"audio/vnd.nortel.vbk\":{\"source\":\"iana\"},\"audio/vnd.nuera.ecelp4800\":{\"source\":\"iana\",\"extensions\":[\"ecelp4800\"]},\"audio/vnd.nuera.ecelp7470\":{\"source\":\"iana\",\"extensions\":[\"ecelp7470\"]},\"audio/vnd.nuera.ecelp9600\":{\"source\":\"iana\",\"extensions\":[\"ecelp9600\"]},\"audio/vnd.octel.sbc\":{\"source\":\"iana\"},\"audio/vnd.presonus.multitrack\":{\"source\":\"iana\"},\"audio/vnd.qcelp\":{\"source\":\"iana\"},\"audio/vnd.rhetorex.32kadpcm\":{\"source\":\"iana\"},\"audio/vnd.rip\":{\"source\":\"iana\",\"extensions\":[\"rip\"]},\"audio/vnd.rn-realaudio\":{\"compressible\":false},\"audio/vnd.sealedmedia.softseal.mpeg\":{\"source\":\"iana\"},\"audio/vnd.vmx.cvsd\":{\"source\":\"iana\"},\"audio/vnd.wave\":{\"compressible\":false},\"audio/vorbis\":{\"source\":\"iana\",\"compressible\":false},\"audio/vorbis-config\":{\"source\":\"iana\"},\"audio/wav\":{\"compressible\":false,\"extensions\":[\"wav\"]},\"audio/wave\":{\"compressible\":false,\"extensions\":[\"wav\"]},\"audio/webm\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"weba\"]},\"audio/x-aac\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"aac\"]},\"audio/x-aiff\":{\"source\":\"apache\",\"extensions\":[\"aif\",\"aiff\",\"aifc\"]},\"audio/x-caf\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"caf\"]},\"audio/x-flac\":{\"source\":\"apache\",\"extensions\":[\"flac\"]},\"audio/x-m4a\":{\"source\":\"nginx\",\"extensions\":[\"m4a\"]},\"audio/x-matroska\":{\"source\":\"apache\",\"extensions\":[\"mka\"]},\"audio/x-mpegurl\":{\"source\":\"apache\",\"extensions\":[\"m3u\"]},\"audio/x-ms-wax\":{\"source\":\"apache\",\"extensions\":[\"wax\"]},\"audio/x-ms-wma\":{\"source\":\"apache\",\"extensions\":[\"wma\"]},\"audio/x-pn-realaudio\":{\"source\":\"apache\",\"extensions\":[\"ram\",\"ra\"]},\"audio/x-pn-realaudio-plugin\":{\"source\":\"apache\",\"extensions\":[\"rmp\"]},\"audio/x-realaudio\":{\"source\":\"nginx\",\"extensions\":[\"ra\"]},\"audio/x-tta\":{\"source\":\"apache\"},\"audio/x-wav\":{\"source\":\"apache\",\"extensions\":[\"wav\"]},\"audio/xm\":{\"source\":\"apache\",\"extensions\":[\"xm\"]},\"chemical/x-cdx\":{\"source\":\"apache\",\"extensions\":[\"cdx\"]},\"chemical/x-cif\":{\"source\":\"apache\",\"extensions\":[\"cif\"]},\"chemical/x-cmdf\":{\"source\":\"apache\",\"extensions\":[\"cmdf\"]},\"chemical/x-cml\":{\"source\":\"apache\",\"extensions\":[\"cml\"]},\"chemical/x-csml\":{\"source\":\"apache\",\"extensions\":[\"csml\"]},\"chemical/x-pdb\":{\"source\":\"apache\"},\"chemical/x-xyz\":{\"source\":\"apache\",\"extensions\":[\"xyz\"]},\"font/collection\":{\"source\":\"iana\",\"extensions\":[\"ttc\"]},\"font/otf\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"otf\"]},\"font/sfnt\":{\"source\":\"iana\"},\"font/ttf\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"ttf\"]},\"font/woff\":{\"source\":\"iana\",\"extensions\":[\"woff\"]},\"font/woff2\":{\"source\":\"iana\",\"extensions\":[\"woff2\"]},\"image/aces\":{\"source\":\"iana\",\"extensions\":[\"exr\"]},\"image/apng\":{\"compressible\":false,\"extensions\":[\"apng\"]},\"image/avci\":{\"source\":\"iana\"},\"image/avcs\":{\"source\":\"iana\"},\"image/bmp\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"bmp\"]},\"image/cgm\":{\"source\":\"iana\",\"extensions\":[\"cgm\"]},\"image/dicom-rle\":{\"source\":\"iana\",\"extensions\":[\"drle\"]},\"image/emf\":{\"source\":\"iana\",\"extensions\":[\"emf\"]},\"image/fits\":{\"source\":\"iana\",\"extensions\":[\"fits\"]},\"image/g3fax\":{\"source\":\"iana\",\"extensions\":[\"g3\"]},\"image/gif\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"gif\"]},\"image/heic\":{\"source\":\"iana\",\"extensions\":[\"heic\"]},\"image/heic-sequence\":{\"source\":\"iana\",\"extensions\":[\"heics\"]},\"image/heif\":{\"source\":\"iana\",\"extensions\":[\"heif\"]},\"image/heif-sequence\":{\"source\":\"iana\",\"extensions\":[\"heifs\"]},\"image/hej2k\":{\"source\":\"iana\",\"extensions\":[\"hej2\"]},\"image/hsj2\":{\"source\":\"iana\",\"extensions\":[\"hsj2\"]},\"image/ief\":{\"source\":\"iana\",\"extensions\":[\"ief\"]},\"image/jls\":{\"source\":\"iana\",\"extensions\":[\"jls\"]},\"image/jp2\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"jp2\",\"jpg2\"]},\"image/jpeg\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"jpeg\",\"jpg\",\"jpe\"]},\"image/jph\":{\"source\":\"iana\",\"extensions\":[\"jph\"]},\"image/jphc\":{\"source\":\"iana\",\"extensions\":[\"jhc\"]},\"image/jpm\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"jpm\"]},\"image/jpx\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"jpx\",\"jpf\"]},\"image/jxr\":{\"source\":\"iana\",\"extensions\":[\"jxr\"]},\"image/jxra\":{\"source\":\"iana\",\"extensions\":[\"jxra\"]},\"image/jxrs\":{\"source\":\"iana\",\"extensions\":[\"jxrs\"]},\"image/jxs\":{\"source\":\"iana\",\"extensions\":[\"jxs\"]},\"image/jxsc\":{\"source\":\"iana\",\"extensions\":[\"jxsc\"]},\"image/jxsi\":{\"source\":\"iana\",\"extensions\":[\"jxsi\"]},\"image/jxss\":{\"source\":\"iana\",\"extensions\":[\"jxss\"]},\"image/ktx\":{\"source\":\"iana\",\"extensions\":[\"ktx\"]},\"image/naplps\":{\"source\":\"iana\"},\"image/pjpeg\":{\"compressible\":false},\"image/png\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"png\"]},\"image/prs.btif\":{\"source\":\"iana\",\"extensions\":[\"btif\"]},\"image/prs.pti\":{\"source\":\"iana\",\"extensions\":[\"pti\"]},\"image/pwg-raster\":{\"source\":\"iana\"},\"image/sgi\":{\"source\":\"apache\",\"extensions\":[\"sgi\"]},\"image/svg+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"svg\",\"svgz\"]},\"image/t38\":{\"source\":\"iana\",\"extensions\":[\"t38\"]},\"image/tiff\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"tif\",\"tiff\"]},\"image/tiff-fx\":{\"source\":\"iana\",\"extensions\":[\"tfx\"]},\"image/vnd.adobe.photoshop\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"psd\"]},\"image/vnd.airzip.accelerator.azv\":{\"source\":\"iana\",\"extensions\":[\"azv\"]},\"image/vnd.cns.inf2\":{\"source\":\"iana\"},\"image/vnd.dece.graphic\":{\"source\":\"iana\",\"extensions\":[\"uvi\",\"uvvi\",\"uvg\",\"uvvg\"]},\"image/vnd.djvu\":{\"source\":\"iana\",\"extensions\":[\"djvu\",\"djv\"]},\"image/vnd.dvb.subtitle\":{\"source\":\"iana\",\"extensions\":[\"sub\"]},\"image/vnd.dwg\":{\"source\":\"iana\",\"extensions\":[\"dwg\"]},\"image/vnd.dxf\":{\"source\":\"iana\",\"extensions\":[\"dxf\"]},\"image/vnd.fastbidsheet\":{\"source\":\"iana\",\"extensions\":[\"fbs\"]},\"image/vnd.fpx\":{\"source\":\"iana\",\"extensions\":[\"fpx\"]},\"image/vnd.fst\":{\"source\":\"iana\",\"extensions\":[\"fst\"]},\"image/vnd.fujixerox.edmics-mmr\":{\"source\":\"iana\",\"extensions\":[\"mmr\"]},\"image/vnd.fujixerox.edmics-rlc\":{\"source\":\"iana\",\"extensions\":[\"rlc\"]},\"image/vnd.globalgraphics.pgb\":{\"source\":\"iana\"},\"image/vnd.microsoft.icon\":{\"source\":\"iana\",\"extensions\":[\"ico\"]},\"image/vnd.mix\":{\"source\":\"iana\"},\"image/vnd.mozilla.apng\":{\"source\":\"iana\"},\"image/vnd.ms-dds\":{\"extensions\":[\"dds\"]},\"image/vnd.ms-modi\":{\"source\":\"iana\",\"extensions\":[\"mdi\"]},\"image/vnd.ms-photo\":{\"source\":\"apache\",\"extensions\":[\"wdp\"]},\"image/vnd.net-fpx\":{\"source\":\"iana\",\"extensions\":[\"npx\"]},\"image/vnd.radiance\":{\"source\":\"iana\"},\"image/vnd.sealed.png\":{\"source\":\"iana\"},\"image/vnd.sealedmedia.softseal.gif\":{\"source\":\"iana\"},\"image/vnd.sealedmedia.softseal.jpg\":{\"source\":\"iana\"},\"image/vnd.svf\":{\"source\":\"iana\"},\"image/vnd.tencent.tap\":{\"source\":\"iana\",\"extensions\":[\"tap\"]},\"image/vnd.valve.source.texture\":{\"source\":\"iana\",\"extensions\":[\"vtf\"]},\"image/vnd.wap.wbmp\":{\"source\":\"iana\",\"extensions\":[\"wbmp\"]},\"image/vnd.xiff\":{\"source\":\"iana\",\"extensions\":[\"xif\"]},\"image/vnd.zbrush.pcx\":{\"source\":\"iana\",\"extensions\":[\"pcx\"]},\"image/webp\":{\"source\":\"apache\",\"extensions\":[\"webp\"]},\"image/wmf\":{\"source\":\"iana\",\"extensions\":[\"wmf\"]},\"image/x-3ds\":{\"source\":\"apache\",\"extensions\":[\"3ds\"]},\"image/x-cmu-raster\":{\"source\":\"apache\",\"extensions\":[\"ras\"]},\"image/x-cmx\":{\"source\":\"apache\",\"extensions\":[\"cmx\"]},\"image/x-freehand\":{\"source\":\"apache\",\"extensions\":[\"fh\",\"fhc\",\"fh4\",\"fh5\",\"fh7\"]},\"image/x-icon\":{\"source\":\"apache\",\"compressible\":true,\"extensions\":[\"ico\"]},\"image/x-jng\":{\"source\":\"nginx\",\"extensions\":[\"jng\"]},\"image/x-mrsid-image\":{\"source\":\"apache\",\"extensions\":[\"sid\"]},\"image/x-ms-bmp\":{\"source\":\"nginx\",\"compressible\":true,\"extensions\":[\"bmp\"]},\"image/x-pcx\":{\"source\":\"apache\",\"extensions\":[\"pcx\"]},\"image/x-pict\":{\"source\":\"apache\",\"extensions\":[\"pic\",\"pct\"]},\"image/x-portable-anymap\":{\"source\":\"apache\",\"extensions\":[\"pnm\"]},\"image/x-portable-bitmap\":{\"source\":\"apache\",\"extensions\":[\"pbm\"]},\"image/x-portable-graymap\":{\"source\":\"apache\",\"extensions\":[\"pgm\"]},\"image/x-portable-pixmap\":{\"source\":\"apache\",\"extensions\":[\"ppm\"]},\"image/x-rgb\":{\"source\":\"apache\",\"extensions\":[\"rgb\"]},\"image/x-tga\":{\"source\":\"apache\",\"extensions\":[\"tga\"]},\"image/x-xbitmap\":{\"source\":\"apache\",\"extensions\":[\"xbm\"]},\"image/x-xcf\":{\"compressible\":false},\"image/x-xpixmap\":{\"source\":\"apache\",\"extensions\":[\"xpm\"]},\"image/x-xwindowdump\":{\"source\":\"apache\",\"extensions\":[\"xwd\"]},\"message/cpim\":{\"source\":\"iana\"},\"message/delivery-status\":{\"source\":\"iana\"},\"message/disposition-notification\":{\"source\":\"iana\",\"extensions\":[\"disposition-notification\"]},\"message/external-body\":{\"source\":\"iana\"},\"message/feedback-report\":{\"source\":\"iana\"},\"message/global\":{\"source\":\"iana\",\"extensions\":[\"u8msg\"]},\"message/global-delivery-status\":{\"source\":\"iana\",\"extensions\":[\"u8dsn\"]},\"message/global-disposition-notification\":{\"source\":\"iana\",\"extensions\":[\"u8mdn\"]},\"message/global-headers\":{\"source\":\"iana\",\"extensions\":[\"u8hdr\"]},\"message/http\":{\"source\":\"iana\",\"compressible\":false},\"message/imdn+xml\":{\"source\":\"iana\",\"compressible\":true},\"message/news\":{\"source\":\"iana\"},\"message/partial\":{\"source\":\"iana\",\"compressible\":false},\"message/rfc822\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"eml\",\"mime\"]},\"message/s-http\":{\"source\":\"iana\"},\"message/sip\":{\"source\":\"iana\"},\"message/sipfrag\":{\"source\":\"iana\"},\"message/tracking-status\":{\"source\":\"iana\"},\"message/vnd.si.simp\":{\"source\":\"iana\"},\"message/vnd.wfa.wsc\":{\"source\":\"iana\",\"extensions\":[\"wsc\"]},\"model/3mf\":{\"source\":\"iana\",\"extensions\":[\"3mf\"]},\"model/gltf+json\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"gltf\"]},\"model/gltf-binary\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"glb\"]},\"model/iges\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"igs\",\"iges\"]},\"model/mesh\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"msh\",\"mesh\",\"silo\"]},\"model/mtl\":{\"source\":\"iana\",\"extensions\":[\"mtl\"]},\"model/obj\":{\"source\":\"iana\",\"extensions\":[\"obj\"]},\"model/stl\":{\"source\":\"iana\",\"extensions\":[\"stl\"]},\"model/vnd.collada+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"dae\"]},\"model/vnd.dwf\":{\"source\":\"iana\",\"extensions\":[\"dwf\"]},\"model/vnd.flatland.3dml\":{\"source\":\"iana\"},\"model/vnd.gdl\":{\"source\":\"iana\",\"extensions\":[\"gdl\"]},\"model/vnd.gs-gdl\":{\"source\":\"apache\"},\"model/vnd.gs.gdl\":{\"source\":\"iana\"},\"model/vnd.gtw\":{\"source\":\"iana\",\"extensions\":[\"gtw\"]},\"model/vnd.moml+xml\":{\"source\":\"iana\",\"compressible\":true},\"model/vnd.mts\":{\"source\":\"iana\",\"extensions\":[\"mts\"]},\"model/vnd.opengex\":{\"source\":\"iana\",\"extensions\":[\"ogex\"]},\"model/vnd.parasolid.transmit.binary\":{\"source\":\"iana\",\"extensions\":[\"x_b\"]},\"model/vnd.parasolid.transmit.text\":{\"source\":\"iana\",\"extensions\":[\"x_t\"]},\"model/vnd.rosette.annotated-data-model\":{\"source\":\"iana\"},\"model/vnd.usdz+zip\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"usdz\"]},\"model/vnd.valve.source.compiled-map\":{\"source\":\"iana\",\"extensions\":[\"bsp\"]},\"model/vnd.vtu\":{\"source\":\"iana\",\"extensions\":[\"vtu\"]},\"model/vrml\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"wrl\",\"vrml\"]},\"model/x3d+binary\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"x3db\",\"x3dbz\"]},\"model/x3d+fastinfoset\":{\"source\":\"iana\",\"extensions\":[\"x3db\"]},\"model/x3d+vrml\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"x3dv\",\"x3dvz\"]},\"model/x3d+xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"x3d\",\"x3dz\"]},\"model/x3d-vrml\":{\"source\":\"iana\",\"extensions\":[\"x3dv\"]},\"multipart/alternative\":{\"source\":\"iana\",\"compressible\":false},\"multipart/appledouble\":{\"source\":\"iana\"},\"multipart/byteranges\":{\"source\":\"iana\"},\"multipart/digest\":{\"source\":\"iana\"},\"multipart/encrypted\":{\"source\":\"iana\",\"compressible\":false},\"multipart/form-data\":{\"source\":\"iana\",\"compressible\":false},\"multipart/header-set\":{\"source\":\"iana\"},\"multipart/mixed\":{\"source\":\"iana\"},\"multipart/multilingual\":{\"source\":\"iana\"},\"multipart/parallel\":{\"source\":\"iana\"},\"multipart/related\":{\"source\":\"iana\",\"compressible\":false},\"multipart/report\":{\"source\":\"iana\"},\"multipart/signed\":{\"source\":\"iana\",\"compressible\":false},\"multipart/vnd.bint.med-plus\":{\"source\":\"iana\"},\"multipart/voice-message\":{\"source\":\"iana\"},\"multipart/x-mixed-replace\":{\"source\":\"iana\"},\"text/1d-interleaved-parityfec\":{\"source\":\"iana\"},\"text/cache-manifest\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"appcache\",\"manifest\"]},\"text/calendar\":{\"source\":\"iana\",\"extensions\":[\"ics\",\"ifb\"]},\"text/calender\":{\"compressible\":true},\"text/cmd\":{\"compressible\":true},\"text/coffeescript\":{\"extensions\":[\"coffee\",\"litcoffee\"]},\"text/css\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"css\"]},\"text/csv\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"csv\"]},\"text/csv-schema\":{\"source\":\"iana\"},\"text/directory\":{\"source\":\"iana\"},\"text/dns\":{\"source\":\"iana\"},\"text/ecmascript\":{\"source\":\"iana\"},\"text/encaprtp\":{\"source\":\"iana\"},\"text/enriched\":{\"source\":\"iana\"},\"text/flexfec\":{\"source\":\"iana\"},\"text/fwdred\":{\"source\":\"iana\"},\"text/grammar-ref-list\":{\"source\":\"iana\"},\"text/html\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"html\",\"htm\",\"shtml\"]},\"text/jade\":{\"extensions\":[\"jade\"]},\"text/javascript\":{\"source\":\"iana\",\"compressible\":true},\"text/jcr-cnd\":{\"source\":\"iana\"},\"text/jsx\":{\"compressible\":true,\"extensions\":[\"jsx\"]},\"text/less\":{\"compressible\":true,\"extensions\":[\"less\"]},\"text/markdown\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"markdown\",\"md\"]},\"text/mathml\":{\"source\":\"nginx\",\"extensions\":[\"mml\"]},\"text/mdx\":{\"compressible\":true,\"extensions\":[\"mdx\"]},\"text/mizar\":{\"source\":\"iana\"},\"text/n3\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"n3\"]},\"text/parameters\":{\"source\":\"iana\",\"charset\":\"UTF-8\"},\"text/parityfec\":{\"source\":\"iana\"},\"text/plain\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"txt\",\"text\",\"conf\",\"def\",\"list\",\"log\",\"in\",\"ini\"]},\"text/provenance-notation\":{\"source\":\"iana\",\"charset\":\"UTF-8\"},\"text/prs.fallenstein.rst\":{\"source\":\"iana\"},\"text/prs.lines.tag\":{\"source\":\"iana\",\"extensions\":[\"dsc\"]},\"text/prs.prop.logic\":{\"source\":\"iana\"},\"text/raptorfec\":{\"source\":\"iana\"},\"text/red\":{\"source\":\"iana\"},\"text/rfc822-headers\":{\"source\":\"iana\"},\"text/richtext\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rtx\"]},\"text/rtf\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"rtf\"]},\"text/rtp-enc-aescm128\":{\"source\":\"iana\"},\"text/rtploopback\":{\"source\":\"iana\"},\"text/rtx\":{\"source\":\"iana\"},\"text/sgml\":{\"source\":\"iana\",\"extensions\":[\"sgml\",\"sgm\"]},\"text/shex\":{\"extensions\":[\"shex\"]},\"text/slim\":{\"extensions\":[\"slim\",\"slm\"]},\"text/strings\":{\"source\":\"iana\"},\"text/stylus\":{\"extensions\":[\"stylus\",\"styl\"]},\"text/t140\":{\"source\":\"iana\"},\"text/tab-separated-values\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"tsv\"]},\"text/troff\":{\"source\":\"iana\",\"extensions\":[\"t\",\"tr\",\"roff\",\"man\",\"me\",\"ms\"]},\"text/turtle\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"extensions\":[\"ttl\"]},\"text/ulpfec\":{\"source\":\"iana\"},\"text/uri-list\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"uri\",\"uris\",\"urls\"]},\"text/vcard\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"vcard\"]},\"text/vnd.a\":{\"source\":\"iana\"},\"text/vnd.abc\":{\"source\":\"iana\"},\"text/vnd.ascii-art\":{\"source\":\"iana\"},\"text/vnd.curl\":{\"source\":\"iana\",\"extensions\":[\"curl\"]},\"text/vnd.curl.dcurl\":{\"source\":\"apache\",\"extensions\":[\"dcurl\"]},\"text/vnd.curl.mcurl\":{\"source\":\"apache\",\"extensions\":[\"mcurl\"]},\"text/vnd.curl.scurl\":{\"source\":\"apache\",\"extensions\":[\"scurl\"]},\"text/vnd.debian.copyright\":{\"source\":\"iana\",\"charset\":\"UTF-8\"},\"text/vnd.dmclientscript\":{\"source\":\"iana\"},\"text/vnd.dvb.subtitle\":{\"source\":\"iana\",\"extensions\":[\"sub\"]},\"text/vnd.esmertec.theme-descriptor\":{\"source\":\"iana\",\"charset\":\"UTF-8\"},\"text/vnd.ficlab.flt\":{\"source\":\"iana\"},\"text/vnd.fly\":{\"source\":\"iana\",\"extensions\":[\"fly\"]},\"text/vnd.fmi.flexstor\":{\"source\":\"iana\",\"extensions\":[\"flx\"]},\"text/vnd.gml\":{\"source\":\"iana\"},\"text/vnd.graphviz\":{\"source\":\"iana\",\"extensions\":[\"gv\"]},\"text/vnd.hgl\":{\"source\":\"iana\"},\"text/vnd.in3d.3dml\":{\"source\":\"iana\",\"extensions\":[\"3dml\"]},\"text/vnd.in3d.spot\":{\"source\":\"iana\",\"extensions\":[\"spot\"]},\"text/vnd.iptc.newsml\":{\"source\":\"iana\"},\"text/vnd.iptc.nitf\":{\"source\":\"iana\"},\"text/vnd.latex-z\":{\"source\":\"iana\"},\"text/vnd.motorola.reflex\":{\"source\":\"iana\"},\"text/vnd.ms-mediapackage\":{\"source\":\"iana\"},\"text/vnd.net2phone.commcenter.command\":{\"source\":\"iana\"},\"text/vnd.radisys.msml-basic-layout\":{\"source\":\"iana\"},\"text/vnd.senx.warpscript\":{\"source\":\"iana\"},\"text/vnd.si.uricatalogue\":{\"source\":\"iana\"},\"text/vnd.sosi\":{\"source\":\"iana\"},\"text/vnd.sun.j2me.app-descriptor\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"extensions\":[\"jad\"]},\"text/vnd.trolltech.linguist\":{\"source\":\"iana\",\"charset\":\"UTF-8\"},\"text/vnd.wap.si\":{\"source\":\"iana\"},\"text/vnd.wap.sl\":{\"source\":\"iana\"},\"text/vnd.wap.wml\":{\"source\":\"iana\",\"extensions\":[\"wml\"]},\"text/vnd.wap.wmlscript\":{\"source\":\"iana\",\"extensions\":[\"wmls\"]},\"text/vtt\":{\"source\":\"iana\",\"charset\":\"UTF-8\",\"compressible\":true,\"extensions\":[\"vtt\"]},\"text/x-asm\":{\"source\":\"apache\",\"extensions\":[\"s\",\"asm\"]},\"text/x-c\":{\"source\":\"apache\",\"extensions\":[\"c\",\"cc\",\"cxx\",\"cpp\",\"h\",\"hh\",\"dic\"]},\"text/x-component\":{\"source\":\"nginx\",\"extensions\":[\"htc\"]},\"text/x-fortran\":{\"source\":\"apache\",\"extensions\":[\"f\",\"for\",\"f77\",\"f90\"]},\"text/x-gwt-rpc\":{\"compressible\":true},\"text/x-handlebars-template\":{\"extensions\":[\"hbs\"]},\"text/x-java-source\":{\"source\":\"apache\",\"extensions\":[\"java\"]},\"text/x-jquery-tmpl\":{\"compressible\":true},\"text/x-lua\":{\"extensions\":[\"lua\"]},\"text/x-markdown\":{\"compressible\":true,\"extensions\":[\"mkd\"]},\"text/x-nfo\":{\"source\":\"apache\",\"extensions\":[\"nfo\"]},\"text/x-opml\":{\"source\":\"apache\",\"extensions\":[\"opml\"]},\"text/x-org\":{\"compressible\":true,\"extensions\":[\"org\"]},\"text/x-pascal\":{\"source\":\"apache\",\"extensions\":[\"p\",\"pas\"]},\"text/x-processing\":{\"compressible\":true,\"extensions\":[\"pde\"]},\"text/x-sass\":{\"extensions\":[\"sass\"]},\"text/x-scss\":{\"extensions\":[\"scss\"]},\"text/x-setext\":{\"source\":\"apache\",\"extensions\":[\"etx\"]},\"text/x-sfv\":{\"source\":\"apache\",\"extensions\":[\"sfv\"]},\"text/x-suse-ymp\":{\"compressible\":true,\"extensions\":[\"ymp\"]},\"text/x-uuencode\":{\"source\":\"apache\",\"extensions\":[\"uu\"]},\"text/x-vcalendar\":{\"source\":\"apache\",\"extensions\":[\"vcs\"]},\"text/x-vcard\":{\"source\":\"apache\",\"extensions\":[\"vcf\"]},\"text/xml\":{\"source\":\"iana\",\"compressible\":true,\"extensions\":[\"xml\"]},\"text/xml-external-parsed-entity\":{\"source\":\"iana\"},\"text/yaml\":{\"extensions\":[\"yaml\",\"yml\"]},\"video/1d-interleaved-parityfec\":{\"source\":\"iana\"},\"video/3gpp\":{\"source\":\"iana\",\"extensions\":[\"3gp\",\"3gpp\"]},\"video/3gpp-tt\":{\"source\":\"iana\"},\"video/3gpp2\":{\"source\":\"iana\",\"extensions\":[\"3g2\"]},\"video/bmpeg\":{\"source\":\"iana\"},\"video/bt656\":{\"source\":\"iana\"},\"video/celb\":{\"source\":\"iana\"},\"video/dv\":{\"source\":\"iana\"},\"video/encaprtp\":{\"source\":\"iana\"},\"video/flexfec\":{\"source\":\"iana\"},\"video/h261\":{\"source\":\"iana\",\"extensions\":[\"h261\"]},\"video/h263\":{\"source\":\"iana\",\"extensions\":[\"h263\"]},\"video/h263-1998\":{\"source\":\"iana\"},\"video/h263-2000\":{\"source\":\"iana\"},\"video/h264\":{\"source\":\"iana\",\"extensions\":[\"h264\"]},\"video/h264-rcdo\":{\"source\":\"iana\"},\"video/h264-svc\":{\"source\":\"iana\"},\"video/h265\":{\"source\":\"iana\"},\"video/iso.segment\":{\"source\":\"iana\"},\"video/jpeg\":{\"source\":\"iana\",\"extensions\":[\"jpgv\"]},\"video/jpeg2000\":{\"source\":\"iana\"},\"video/jpm\":{\"source\":\"apache\",\"extensions\":[\"jpm\",\"jpgm\"]},\"video/mj2\":{\"source\":\"iana\",\"extensions\":[\"mj2\",\"mjp2\"]},\"video/mp1s\":{\"source\":\"iana\"},\"video/mp2p\":{\"source\":\"iana\"},\"video/mp2t\":{\"source\":\"iana\",\"extensions\":[\"ts\"]},\"video/mp4\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"mp4\",\"mp4v\",\"mpg4\"]},\"video/mp4v-es\":{\"source\":\"iana\"},\"video/mpeg\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"mpeg\",\"mpg\",\"mpe\",\"m1v\",\"m2v\"]},\"video/mpeg4-generic\":{\"source\":\"iana\"},\"video/mpv\":{\"source\":\"iana\"},\"video/nv\":{\"source\":\"iana\"},\"video/ogg\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"ogv\"]},\"video/parityfec\":{\"source\":\"iana\"},\"video/pointer\":{\"source\":\"iana\"},\"video/quicktime\":{\"source\":\"iana\",\"compressible\":false,\"extensions\":[\"qt\",\"mov\"]},\"video/raptorfec\":{\"source\":\"iana\"},\"video/raw\":{\"source\":\"iana\"},\"video/rtp-enc-aescm128\":{\"source\":\"iana\"},\"video/rtploopback\":{\"source\":\"iana\"},\"video/rtx\":{\"source\":\"iana\"},\"video/smpte291\":{\"source\":\"iana\"},\"video/smpte292m\":{\"source\":\"iana\"},\"video/ulpfec\":{\"source\":\"iana\"},\"video/vc1\":{\"source\":\"iana\"},\"video/vc2\":{\"source\":\"iana\"},\"video/vnd.cctv\":{\"source\":\"iana\"},\"video/vnd.dece.hd\":{\"source\":\"iana\",\"extensions\":[\"uvh\",\"uvvh\"]},\"video/vnd.dece.mobile\":{\"source\":\"iana\",\"extensions\":[\"uvm\",\"uvvm\"]},\"video/vnd.dece.mp4\":{\"source\":\"iana\"},\"video/vnd.dece.pd\":{\"source\":\"iana\",\"extensions\":[\"uvp\",\"uvvp\"]},\"video/vnd.dece.sd\":{\"source\":\"iana\",\"extensions\":[\"uvs\",\"uvvs\"]},\"video/vnd.dece.video\":{\"source\":\"iana\",\"extensions\":[\"uvv\",\"uvvv\"]},\"video/vnd.directv.mpeg\":{\"source\":\"iana\"},\"video/vnd.directv.mpeg-tts\":{\"source\":\"iana\"},\"video/vnd.dlna.mpeg-tts\":{\"source\":\"iana\"},\"video/vnd.dvb.file\":{\"source\":\"iana\",\"extensions\":[\"dvb\"]},\"video/vnd.fvt\":{\"source\":\"iana\",\"extensions\":[\"fvt\"]},\"video/vnd.hns.video\":{\"source\":\"iana\"},\"video/vnd.iptvforum.1dparityfec-1010\":{\"source\":\"iana\"},\"video/vnd.iptvforum.1dparityfec-2005\":{\"source\":\"iana\"},\"video/vnd.iptvforum.2dparityfec-1010\":{\"source\":\"iana\"},\"video/vnd.iptvforum.2dparityfec-2005\":{\"source\":\"iana\"},\"video/vnd.iptvforum.ttsavc\":{\"source\":\"iana\"},\"video/vnd.iptvforum.ttsmpeg2\":{\"source\":\"iana\"},\"video/vnd.motorola.video\":{\"source\":\"iana\"},\"video/vnd.motorola.videop\":{\"source\":\"iana\"},\"video/vnd.mpegurl\":{\"source\":\"iana\",\"extensions\":[\"mxu\",\"m4u\"]},\"video/vnd.ms-playready.media.pyv\":{\"source\":\"iana\",\"extensions\":[\"pyv\"]},\"video/vnd.nokia.interleaved-multimedia\":{\"source\":\"iana\"},\"video/vnd.nokia.mp4vr\":{\"source\":\"iana\"},\"video/vnd.nokia.videovoip\":{\"source\":\"iana\"},\"video/vnd.objectvideo\":{\"source\":\"iana\"},\"video/vnd.radgamettools.bink\":{\"source\":\"iana\"},\"video/vnd.radgamettools.smacker\":{\"source\":\"iana\"},\"video/vnd.sealed.mpeg1\":{\"source\":\"iana\"},\"video/vnd.sealed.mpeg4\":{\"source\":\"iana\"},\"video/vnd.sealed.swf\":{\"source\":\"iana\"},\"video/vnd.sealedmedia.softseal.mov\":{\"source\":\"iana\"},\"video/vnd.uvvu.mp4\":{\"source\":\"iana\",\"extensions\":[\"uvu\",\"uvvu\"]},\"video/vnd.vivo\":{\"source\":\"iana\",\"extensions\":[\"viv\"]},\"video/vnd.youtube.yt\":{\"source\":\"iana\"},\"video/vp8\":{\"source\":\"iana\"},\"video/webm\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"webm\"]},\"video/x-f4v\":{\"source\":\"apache\",\"extensions\":[\"f4v\"]},\"video/x-fli\":{\"source\":\"apache\",\"extensions\":[\"fli\"]},\"video/x-flv\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"flv\"]},\"video/x-m4v\":{\"source\":\"apache\",\"extensions\":[\"m4v\"]},\"video/x-matroska\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"mkv\",\"mk3d\",\"mks\"]},\"video/x-mng\":{\"source\":\"apache\",\"extensions\":[\"mng\"]},\"video/x-ms-asf\":{\"source\":\"apache\",\"extensions\":[\"asf\",\"asx\"]},\"video/x-ms-vob\":{\"source\":\"apache\",\"extensions\":[\"vob\"]},\"video/x-ms-wm\":{\"source\":\"apache\",\"extensions\":[\"wm\"]},\"video/x-ms-wmv\":{\"source\":\"apache\",\"compressible\":false,\"extensions\":[\"wmv\"]},\"video/x-ms-wmx\":{\"source\":\"apache\",\"extensions\":[\"wmx\"]},\"video/x-ms-wvx\":{\"source\":\"apache\",\"extensions\":[\"wvx\"]},\"video/x-msvideo\":{\"source\":\"apache\",\"extensions\":[\"avi\"]},\"video/x-sgi-movie\":{\"source\":\"apache\",\"extensions\":[\"movie\"]},\"video/x-smv\":{\"source\":\"apache\",\"extensions\":[\"smv\"]},\"x-conference/x-cooltalk\":{\"source\":\"apache\",\"extensions\":[\"ice\"]},\"x-shader/x-fragment\":{\"compressible\":true},\"x-shader/x-vertex\":{\"compressible\":true}}"); - -/***/ }), - -/***/ "../../node_modules/mime-db/index.js": -/***/ (function(module, exports, __webpack_require__) { - -/*! - * mime-db - * Copyright(c) 2014 Jonathan Ong - * MIT Licensed - */ - -/** - * Module exports. - */ - -module.exports = __webpack_require__("../../node_modules/mime-db/db.json") - - -/***/ }), - -/***/ "../../node_modules/mime-types/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/*! - * mime-types - * Copyright(c) 2014 Jonathan Ong - * Copyright(c) 2015 Douglas Christopher Wilson - * MIT Licensed - */ - - - -/** - * Module dependencies. - * @private - */ - -var db = __webpack_require__("../../node_modules/mime-db/index.js") -var extname = __webpack_require__("path").extname - -/** - * Module variables. - * @private - */ - -var EXTRACT_TYPE_REGEXP = /^\s*([^;\s]*)(?:;|\s|$)/ -var TEXT_TYPE_REGEXP = /^text\//i - -/** - * Module exports. - * @public - */ - -exports.charset = charset -exports.charsets = { lookup: charset } -exports.contentType = contentType -exports.extension = extension -exports.extensions = Object.create(null) -exports.lookup = lookup -exports.types = Object.create(null) - -// Populate the extensions/types maps -populateMaps(exports.extensions, exports.types) - -/** - * Get the default charset for a MIME type. - * - * @param {string} type - * @return {boolean|string} - */ - -function charset (type) { - if (!type || typeof type !== 'string') { - return false - } - - // TODO: use media-typer - var match = EXTRACT_TYPE_REGEXP.exec(type) - var mime = match && db[match[1].toLowerCase()] - - if (mime && mime.charset) { - return mime.charset - } - - // default text/* to utf-8 - if (match && TEXT_TYPE_REGEXP.test(match[1])) { - return 'UTF-8' - } - - return false -} - -/** - * Create a full Content-Type header given a MIME type or extension. - * - * @param {string} str - * @return {boolean|string} - */ - -function contentType (str) { - // TODO: should this even be in this module? - if (!str || typeof str !== 'string') { - return false - } - - var mime = str.indexOf('/') === -1 - ? exports.lookup(str) - : str - - if (!mime) { - return false - } - - // TODO: use content-type or other module - if (mime.indexOf('charset') === -1) { - var charset = exports.charset(mime) - if (charset) mime += '; charset=' + charset.toLowerCase() - } - - return mime -} - -/** - * Get the default extension for a MIME type. - * - * @param {string} type - * @return {boolean|string} - */ - -function extension (type) { - if (!type || typeof type !== 'string') { - return false - } - - // TODO: use media-typer - var match = EXTRACT_TYPE_REGEXP.exec(type) - - // get extensions - var exts = match && exports.extensions[match[1].toLowerCase()] - - if (!exts || !exts.length) { - return false - } - - return exts[0] -} - -/** - * Lookup the MIME type for a file path/extension. - * - * @param {string} path - * @return {boolean|string} - */ - -function lookup (path) { - if (!path || typeof path !== 'string') { - return false - } - - // get the extension ("ext" or ".ext" or full path) - var extension = extname('x.' + path) - .toLowerCase() - .substr(1) - - if (!extension) { - return false - } - - return exports.types[extension] || false -} - -/** - * Populate the extensions and types maps. - * @private - */ - -function populateMaps (extensions, types) { - // source preference (least -> most) - var preference = ['nginx', 'apache', undefined, 'iana'] - - Object.keys(db).forEach(function forEachMimeType (type) { - var mime = db[type] - var exts = mime.extensions - - if (!exts || !exts.length) { - return - } - - // mime -> extensions - extensions[type] = exts - - // extension -> mime - for (var i = 0; i < exts.length; i++) { - var extension = exts[i] - - if (types[extension]) { - var from = preference.indexOf(db[types[extension]].source) - var to = preference.indexOf(mime.source) - - if (types[extension] !== 'application/octet-stream' && - (from > to || (from === to && types[extension].substr(0, 12) === 'application/'))) { - // skip the remapping - continue - } - } - - // set the extension -> mime - types[extension] = type - } - }) -} - - -/***/ }), - -/***/ "../../node_modules/mimic-fn/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const mimicFn = (to, from) => { - for (const prop of Reflect.ownKeys(from)) { - Object.defineProperty(to, prop, Object.getOwnPropertyDescriptor(from, prop)); - } - - return to; -}; - -module.exports = mimicFn; -// TODO: Remove this for the next major release -module.exports.default = mimicFn; - - -/***/ }), - -/***/ "../../node_modules/minimatch/minimatch.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = minimatch -minimatch.Minimatch = Minimatch - -var path = (function () { try { return __webpack_require__("path") } catch (e) {}}()) || { - sep: '/' -} -minimatch.sep = path.sep - -var GLOBSTAR = minimatch.GLOBSTAR = Minimatch.GLOBSTAR = {} -var expand = __webpack_require__("../../node_modules/brace-expansion/index.js") - -var plTypes = { - '!': { open: '(?:(?!(?:', close: '))[^/]*?)'}, - '?': { open: '(?:', close: ')?' }, - '+': { open: '(?:', close: ')+' }, - '*': { open: '(?:', close: ')*' }, - '@': { open: '(?:', close: ')' } -} - -// any single thing other than / -// don't need to escape / when using new RegExp() -var qmark = '[^/]' - -// * => any number of characters -var star = qmark + '*?' - -// ** when dots are allowed. Anything goes, except .. and . -// not (^ or / followed by one or two dots followed by $ or /), -// followed by anything, any number of times. -var twoStarDot = '(?:(?!(?:\\\/|^)(?:\\.{1,2})($|\\\/)).)*?' - -// not a ^ or / followed by a dot, -// followed by anything, any number of times. -var twoStarNoDot = '(?:(?!(?:\\\/|^)\\.).)*?' - -// characters that need to be escaped in RegExp. -var reSpecials = charSet('().*{}+?[]^$\\!') - -// "abc" -> { a:true, b:true, c:true } -function charSet (s) { - return s.split('').reduce(function (set, c) { - set[c] = true - return set - }, {}) -} - -// normalizes slashes. -var slashSplit = /\/+/ - -minimatch.filter = filter -function filter (pattern, options) { - options = options || {} - return function (p, i, list) { - return minimatch(p, pattern, options) - } -} - -function ext (a, b) { - b = b || {} - var t = {} - Object.keys(a).forEach(function (k) { - t[k] = a[k] - }) - Object.keys(b).forEach(function (k) { - t[k] = b[k] - }) - return t -} - -minimatch.defaults = function (def) { - if (!def || typeof def !== 'object' || !Object.keys(def).length) { - return minimatch - } - - var orig = minimatch - - var m = function minimatch (p, pattern, options) { - return orig(p, pattern, ext(def, options)) - } - - m.Minimatch = function Minimatch (pattern, options) { - return new orig.Minimatch(pattern, ext(def, options)) - } - m.Minimatch.defaults = function defaults (options) { - return orig.defaults(ext(def, options)).Minimatch - } - - m.filter = function filter (pattern, options) { - return orig.filter(pattern, ext(def, options)) - } - - m.defaults = function defaults (options) { - return orig.defaults(ext(def, options)) - } - - m.makeRe = function makeRe (pattern, options) { - return orig.makeRe(pattern, ext(def, options)) - } - - m.braceExpand = function braceExpand (pattern, options) { - return orig.braceExpand(pattern, ext(def, options)) - } - - m.match = function (list, pattern, options) { - return orig.match(list, pattern, ext(def, options)) - } - - return m -} - -Minimatch.defaults = function (def) { - return minimatch.defaults(def).Minimatch -} - -function minimatch (p, pattern, options) { - assertValidPattern(pattern) - - if (!options) options = {} - - // shortcut: comments match nothing. - if (!options.nocomment && pattern.charAt(0) === '#') { - return false - } - - return new Minimatch(pattern, options).match(p) -} - -function Minimatch (pattern, options) { - if (!(this instanceof Minimatch)) { - return new Minimatch(pattern, options) - } - - assertValidPattern(pattern) - - if (!options) options = {} - - pattern = pattern.trim() - - // windows support: need to use /, not \ - if (!options.allowWindowsEscape && path.sep !== '/') { - pattern = pattern.split(path.sep).join('/') - } - - this.options = options - this.set = [] - this.pattern = pattern - this.regexp = null - this.negate = false - this.comment = false - this.empty = false - this.partial = !!options.partial - - // make the set of regexps etc. - this.make() -} - -Minimatch.prototype.debug = function () {} - -Minimatch.prototype.make = make -function make () { - var pattern = this.pattern - var options = this.options - - // empty patterns and comments match nothing. - if (!options.nocomment && pattern.charAt(0) === '#') { - this.comment = true - return - } - if (!pattern) { - this.empty = true - return - } - - // step 1: figure out negation, etc. - this.parseNegate() - - // step 2: expand braces - var set = this.globSet = this.braceExpand() - - if (options.debug) this.debug = function debug() { console.error.apply(console, arguments) } - - this.debug(this.pattern, set) - - // step 3: now we have a set, so turn each one into a series of path-portion - // matching patterns. - // These will be regexps, except in the case of "**", which is - // set to the GLOBSTAR object for globstar behavior, - // and will not contain any / characters - set = this.globParts = set.map(function (s) { - return s.split(slashSplit) - }) - - this.debug(this.pattern, set) - - // glob --> regexps - set = set.map(function (s, si, set) { - return s.map(this.parse, this) - }, this) - - this.debug(this.pattern, set) - - // filter out everything that didn't compile properly. - set = set.filter(function (s) { - return s.indexOf(false) === -1 - }) - - this.debug(this.pattern, set) - - this.set = set -} - -Minimatch.prototype.parseNegate = parseNegate -function parseNegate () { - var pattern = this.pattern - var negate = false - var options = this.options - var negateOffset = 0 - - if (options.nonegate) return - - for (var i = 0, l = pattern.length - ; i < l && pattern.charAt(i) === '!' - ; i++) { - negate = !negate - negateOffset++ - } - - if (negateOffset) this.pattern = pattern.substr(negateOffset) - this.negate = negate -} - -// Brace expansion: -// a{b,c}d -> abd acd -// a{b,}c -> abc ac -// a{0..3}d -> a0d a1d a2d a3d -// a{b,c{d,e}f}g -> abg acdfg acefg -// a{b,c}d{e,f}g -> abdeg acdeg abdeg abdfg -// -// Invalid sets are not expanded. -// a{2..}b -> a{2..}b -// a{b}c -> a{b}c -minimatch.braceExpand = function (pattern, options) { - return braceExpand(pattern, options) -} - -Minimatch.prototype.braceExpand = braceExpand - -function braceExpand (pattern, options) { - if (!options) { - if (this instanceof Minimatch) { - options = this.options - } else { - options = {} - } - } - - pattern = typeof pattern === 'undefined' - ? this.pattern : pattern - - assertValidPattern(pattern) - - // Thanks to Yeting Li for - // improving this regexp to avoid a ReDOS vulnerability. - if (options.nobrace || !/\{(?:(?!\{).)*\}/.test(pattern)) { - // shortcut. no need to expand. - return [pattern] - } - - return expand(pattern) -} - -var MAX_PATTERN_LENGTH = 1024 * 64 -var assertValidPattern = function (pattern) { - if (typeof pattern !== 'string') { - throw new TypeError('invalid pattern') - } - - if (pattern.length > MAX_PATTERN_LENGTH) { - throw new TypeError('pattern is too long') - } -} - -// parse a component of the expanded set. -// At this point, no pattern may contain "/" in it -// so we're going to return a 2d array, where each entry is the full -// pattern, split on '/', and then turned into a regular expression. -// A regexp is made at the end which joins each array with an -// escaped /, and another full one which joins each regexp with |. -// -// Following the lead of Bash 4.1, note that "**" only has special meaning -// when it is the *only* thing in a path portion. Otherwise, any series -// of * is equivalent to a single *. Globstar behavior is enabled by -// default, and can be disabled by setting options.noglobstar. -Minimatch.prototype.parse = parse -var SUBPARSE = {} -function parse (pattern, isSub) { - assertValidPattern(pattern) - - var options = this.options - - // shortcuts - if (pattern === '**') { - if (!options.noglobstar) - return GLOBSTAR - else - pattern = '*' - } - if (pattern === '') return '' - - var re = '' - var hasMagic = !!options.nocase - var escaping = false - // ? => one single character - var patternListStack = [] - var negativeLists = [] - var stateChar - var inClass = false - var reClassStart = -1 - var classStart = -1 - // . and .. never match anything that doesn't start with ., - // even when options.dot is set. - var patternStart = pattern.charAt(0) === '.' ? '' // anything - // not (start or / followed by . or .. followed by / or end) - : options.dot ? '(?!(?:^|\\\/)\\.{1,2}(?:$|\\\/))' - : '(?!\\.)' - var self = this - - function clearStateChar () { - if (stateChar) { - // we had some state-tracking character - // that wasn't consumed by this pass. - switch (stateChar) { - case '*': - re += star - hasMagic = true - break - case '?': - re += qmark - hasMagic = true - break - default: - re += '\\' + stateChar - break - } - self.debug('clearStateChar %j %j', stateChar, re) - stateChar = false - } - } - - for (var i = 0, len = pattern.length, c - ; (i < len) && (c = pattern.charAt(i)) - ; i++) { - this.debug('%s\t%s %s %j', pattern, i, re, c) - - // skip over any that are escaped. - if (escaping && reSpecials[c]) { - re += '\\' + c - escaping = false - continue - } - - switch (c) { - /* istanbul ignore next */ - case '/': { - // completely not allowed, even escaped. - // Should already be path-split by now. - return false - } - - case '\\': - clearStateChar() - escaping = true - continue - - // the various stateChar values - // for the "extglob" stuff. - case '?': - case '*': - case '+': - case '@': - case '!': - this.debug('%s\t%s %s %j <-- stateChar', pattern, i, re, c) - - // all of those are literals inside a class, except that - // the glob [!a] means [^a] in regexp - if (inClass) { - this.debug(' in class') - if (c === '!' && i === classStart + 1) c = '^' - re += c - continue - } - - // if we already have a stateChar, then it means - // that there was something like ** or +? in there. - // Handle the stateChar, then proceed with this one. - self.debug('call clearStateChar %j', stateChar) - clearStateChar() - stateChar = c - // if extglob is disabled, then +(asdf|foo) isn't a thing. - // just clear the statechar *now*, rather than even diving into - // the patternList stuff. - if (options.noext) clearStateChar() - continue - - case '(': - if (inClass) { - re += '(' - continue - } - - if (!stateChar) { - re += '\\(' - continue - } - - patternListStack.push({ - type: stateChar, - start: i - 1, - reStart: re.length, - open: plTypes[stateChar].open, - close: plTypes[stateChar].close - }) - // negation is (?:(?!js)[^/]*) - re += stateChar === '!' ? '(?:(?!(?:' : '(?:' - this.debug('plType %j %j', stateChar, re) - stateChar = false - continue - - case ')': - if (inClass || !patternListStack.length) { - re += '\\)' - continue - } - - clearStateChar() - hasMagic = true - var pl = patternListStack.pop() - // negation is (?:(?!js)[^/]*) - // The others are (?:) - re += pl.close - if (pl.type === '!') { - negativeLists.push(pl) - } - pl.reEnd = re.length - continue - - case '|': - if (inClass || !patternListStack.length || escaping) { - re += '\\|' - escaping = false - continue - } - - clearStateChar() - re += '|' - continue - - // these are mostly the same in regexp and glob - case '[': - // swallow any state-tracking char before the [ - clearStateChar() - - if (inClass) { - re += '\\' + c - continue - } - - inClass = true - classStart = i - reClassStart = re.length - re += c - continue - - case ']': - // a right bracket shall lose its special - // meaning and represent itself in - // a bracket expression if it occurs - // first in the list. -- POSIX.2 2.8.3.2 - if (i === classStart + 1 || !inClass) { - re += '\\' + c - escaping = false - continue - } - - // handle the case where we left a class open. - // "[z-a]" is valid, equivalent to "\[z-a\]" - // split where the last [ was, make sure we don't have - // an invalid re. if so, re-walk the contents of the - // would-be class to re-translate any characters that - // were passed through as-is - // TODO: It would probably be faster to determine this - // without a try/catch and a new RegExp, but it's tricky - // to do safely. For now, this is safe and works. - var cs = pattern.substring(classStart + 1, i) - try { - RegExp('[' + cs + ']') - } catch (er) { - // not a valid class! - var sp = this.parse(cs, SUBPARSE) - re = re.substr(0, reClassStart) + '\\[' + sp[0] + '\\]' - hasMagic = hasMagic || sp[1] - inClass = false - continue - } - - // finish up the class. - hasMagic = true - inClass = false - re += c - continue - - default: - // swallow any state char that wasn't consumed - clearStateChar() - - if (escaping) { - // no need - escaping = false - } else if (reSpecials[c] - && !(c === '^' && inClass)) { - re += '\\' - } - - re += c - - } // switch - } // for - - // handle the case where we left a class open. - // "[abc" is valid, equivalent to "\[abc" - if (inClass) { - // split where the last [ was, and escape it - // this is a huge pita. We now have to re-walk - // the contents of the would-be class to re-translate - // any characters that were passed through as-is - cs = pattern.substr(classStart + 1) - sp = this.parse(cs, SUBPARSE) - re = re.substr(0, reClassStart) + '\\[' + sp[0] - hasMagic = hasMagic || sp[1] - } - - // handle the case where we had a +( thing at the *end* - // of the pattern. - // each pattern list stack adds 3 chars, and we need to go through - // and escape any | chars that were passed through as-is for the regexp. - // Go through and escape them, taking care not to double-escape any - // | chars that were already escaped. - for (pl = patternListStack.pop(); pl; pl = patternListStack.pop()) { - var tail = re.slice(pl.reStart + pl.open.length) - this.debug('setting tail', re, pl) - // maybe some even number of \, then maybe 1 \, followed by a | - tail = tail.replace(/((?:\\{2}){0,64})(\\?)\|/g, function (_, $1, $2) { - if (!$2) { - // the | isn't already escaped, so escape it. - $2 = '\\' - } - - // need to escape all those slashes *again*, without escaping the - // one that we need for escaping the | character. As it works out, - // escaping an even number of slashes can be done by simply repeating - // it exactly after itself. That's why this trick works. - // - // I am sorry that you have to see this. - return $1 + $1 + $2 + '|' - }) - - this.debug('tail=%j\n %s', tail, tail, pl, re) - var t = pl.type === '*' ? star - : pl.type === '?' ? qmark - : '\\' + pl.type - - hasMagic = true - re = re.slice(0, pl.reStart) + t + '\\(' + tail - } - - // handle trailing things that only matter at the very end. - clearStateChar() - if (escaping) { - // trailing \\ - re += '\\\\' - } - - // only need to apply the nodot start if the re starts with - // something that could conceivably capture a dot - var addPatternStart = false - switch (re.charAt(0)) { - case '[': case '.': case '(': addPatternStart = true - } - - // Hack to work around lack of negative lookbehind in JS - // A pattern like: *.!(x).!(y|z) needs to ensure that a name - // like 'a.xyz.yz' doesn't match. So, the first negative - // lookahead, has to look ALL the way ahead, to the end of - // the pattern. - for (var n = negativeLists.length - 1; n > -1; n--) { - var nl = negativeLists[n] - - var nlBefore = re.slice(0, nl.reStart) - var nlFirst = re.slice(nl.reStart, nl.reEnd - 8) - var nlLast = re.slice(nl.reEnd - 8, nl.reEnd) - var nlAfter = re.slice(nl.reEnd) - - nlLast += nlAfter - - // Handle nested stuff like *(*.js|!(*.json)), where open parens - // mean that we should *not* include the ) in the bit that is considered - // "after" the negated section. - var openParensBefore = nlBefore.split('(').length - 1 - var cleanAfter = nlAfter - for (i = 0; i < openParensBefore; i++) { - cleanAfter = cleanAfter.replace(/\)[+*?]?/, '') - } - nlAfter = cleanAfter - - var dollar = '' - if (nlAfter === '' && isSub !== SUBPARSE) { - dollar = '$' - } - var newRe = nlBefore + nlFirst + nlAfter + dollar + nlLast - re = newRe - } - - // if the re is not "" at this point, then we need to make sure - // it doesn't match against an empty path part. - // Otherwise a/* will match a/, which it should not. - if (re !== '' && hasMagic) { - re = '(?=.)' + re - } - - if (addPatternStart) { - re = patternStart + re - } - - // parsing just a piece of a larger pattern. - if (isSub === SUBPARSE) { - return [re, hasMagic] - } - - // skip the regexp for non-magical patterns - // unescape anything in it, though, so that it'll be - // an exact match against a file etc. - if (!hasMagic) { - return globUnescape(pattern) - } - - var flags = options.nocase ? 'i' : '' - try { - var regExp = new RegExp('^' + re + '$', flags) - } catch (er) /* istanbul ignore next - should be impossible */ { - // If it was an invalid regular expression, then it can't match - // anything. This trick looks for a character after the end of - // the string, which is of course impossible, except in multi-line - // mode, but it's not a /m regex. - return new RegExp('$.') - } - - regExp._glob = pattern - regExp._src = re - - return regExp -} - -minimatch.makeRe = function (pattern, options) { - return new Minimatch(pattern, options || {}).makeRe() -} - -Minimatch.prototype.makeRe = makeRe -function makeRe () { - if (this.regexp || this.regexp === false) return this.regexp - - // at this point, this.set is a 2d array of partial - // pattern strings, or "**". - // - // It's better to use .match(). This function shouldn't - // be used, really, but it's pretty convenient sometimes, - // when you just want to work with a regex. - var set = this.set - - if (!set.length) { - this.regexp = false - return this.regexp - } - var options = this.options - - var twoStar = options.noglobstar ? star - : options.dot ? twoStarDot - : twoStarNoDot - var flags = options.nocase ? 'i' : '' - - var re = set.map(function (pattern) { - return pattern.map(function (p) { - return (p === GLOBSTAR) ? twoStar - : (typeof p === 'string') ? regExpEscape(p) - : p._src - }).join('\\\/') - }).join('|') - - // must match entire pattern - // ending in a * or ** will make it less strict. - re = '^(?:' + re + ')$' - - // can match anything, as long as it's not this. - if (this.negate) re = '^(?!' + re + ').*$' - - try { - this.regexp = new RegExp(re, flags) - } catch (ex) /* istanbul ignore next - should be impossible */ { - this.regexp = false - } - return this.regexp -} - -minimatch.match = function (list, pattern, options) { - options = options || {} - var mm = new Minimatch(pattern, options) - list = list.filter(function (f) { - return mm.match(f) - }) - if (mm.options.nonull && !list.length) { - list.push(pattern) - } - return list -} - -Minimatch.prototype.match = function match (f, partial) { - if (typeof partial === 'undefined') partial = this.partial - this.debug('match', f, this.pattern) - // short-circuit in the case of busted things. - // comments, etc. - if (this.comment) return false - if (this.empty) return f === '' - - if (f === '/' && partial) return true - - var options = this.options - - // windows: need to use /, not \ - if (path.sep !== '/') { - f = f.split(path.sep).join('/') - } - - // treat the test path as a set of pathparts. - f = f.split(slashSplit) - this.debug(this.pattern, 'split', f) - - // just ONE of the pattern sets in this.set needs to match - // in order for it to be valid. If negating, then just one - // match means that we have failed. - // Either way, return on the first hit. - - var set = this.set - this.debug(this.pattern, 'set', set) - - // Find the basename of the path by looking for the last non-empty segment - var filename - var i - for (i = f.length - 1; i >= 0; i--) { - filename = f[i] - if (filename) break - } - - for (i = 0; i < set.length; i++) { - var pattern = set[i] - var file = f - if (options.matchBase && pattern.length === 1) { - file = [filename] - } - var hit = this.matchOne(file, pattern, partial) - if (hit) { - if (options.flipNegate) return true - return !this.negate - } - } - - // didn't get any hits. this is success if it's a negative - // pattern, failure otherwise. - if (options.flipNegate) return false - return this.negate -} - -// set partial to true to test if, for example, -// "/a/b" matches the start of "/*/b/*/d" -// Partial means, if you run out of file before you run -// out of pattern, then that's fine, as long as all -// the parts match. -Minimatch.prototype.matchOne = function (file, pattern, partial) { - var options = this.options - - this.debug('matchOne', - { 'this': this, file: file, pattern: pattern }) - - this.debug('matchOne', file.length, pattern.length) - - for (var fi = 0, - pi = 0, - fl = file.length, - pl = pattern.length - ; (fi < fl) && (pi < pl) - ; fi++, pi++) { - this.debug('matchOne loop') - var p = pattern[pi] - var f = file[fi] - - this.debug(pattern, p, f) - - // should be impossible. - // some invalid regexp stuff in the set. - /* istanbul ignore if */ - if (p === false) return false - - if (p === GLOBSTAR) { - this.debug('GLOBSTAR', [pattern, p, f]) - - // "**" - // a/**/b/**/c would match the following: - // a/b/x/y/z/c - // a/x/y/z/b/c - // a/b/x/b/x/c - // a/b/c - // To do this, take the rest of the pattern after - // the **, and see if it would match the file remainder. - // If so, return success. - // If not, the ** "swallows" a segment, and try again. - // This is recursively awful. - // - // a/**/b/**/c matching a/b/x/y/z/c - // - a matches a - // - doublestar - // - matchOne(b/x/y/z/c, b/**/c) - // - b matches b - // - doublestar - // - matchOne(x/y/z/c, c) -> no - // - matchOne(y/z/c, c) -> no - // - matchOne(z/c, c) -> no - // - matchOne(c, c) yes, hit - var fr = fi - var pr = pi + 1 - if (pr === pl) { - this.debug('** at the end') - // a ** at the end will just swallow the rest. - // We have found a match. - // however, it will not swallow /.x, unless - // options.dot is set. - // . and .. are *never* matched by **, for explosively - // exponential reasons. - for (; fi < fl; fi++) { - if (file[fi] === '.' || file[fi] === '..' || - (!options.dot && file[fi].charAt(0) === '.')) return false - } - return true - } - - // ok, let's see if we can swallow whatever we can. - while (fr < fl) { - var swallowee = file[fr] - - this.debug('\nglobstar while', file, fr, pattern, pr, swallowee) - - // XXX remove this slice. Just pass the start index. - if (this.matchOne(file.slice(fr), pattern.slice(pr), partial)) { - this.debug('globstar found match!', fr, fl, swallowee) - // found a match. - return true - } else { - // can't swallow "." or ".." ever. - // can only swallow ".foo" when explicitly asked. - if (swallowee === '.' || swallowee === '..' || - (!options.dot && swallowee.charAt(0) === '.')) { - this.debug('dot detected!', file, fr, pattern, pr) - break - } - - // ** swallows a segment, and continue. - this.debug('globstar swallow a segment, and continue') - fr++ - } - } - - // no match was found. - // However, in partial mode, we can't say this is necessarily over. - // If there's more *pattern* left, then - /* istanbul ignore if */ - if (partial) { - // ran out of file - this.debug('\n>>> no match, partial?', file, fr, pattern, pr) - if (fr === fl) return true - } - return false - } - - // something other than ** - // non-magic patterns just have to match exactly - // patterns with magic have been turned into regexps. - var hit - if (typeof p === 'string') { - hit = f === p - this.debug('string match', p, f, hit) - } else { - hit = f.match(p) - this.debug('pattern match', p, f, hit) - } - - if (!hit) return false - } - - // Note: ending in / means that we'll get a final "" - // at the end of the pattern. This can only match a - // corresponding "" at the end of the file. - // If the file ends in /, then it can only match a - // a pattern that ends in /, unless the pattern just - // doesn't have any more for it. But, a/b/ should *not* - // match "a/b/*", even though "" matches against the - // [^/]*? pattern, except in partial mode, where it might - // simply not be reached yet. - // However, a/b/ should still satisfy a/* - - // now either we fell off the end of the pattern, or we're done. - if (fi === fl && pi === pl) { - // ran out of pattern and filename at the same time. - // an exact hit! - return true - } else if (fi === fl) { - // ran out of file, but still had pattern left. - // this is ok if we're doing the match as part of - // a glob fs traversal. - return partial - } else /* istanbul ignore else */ if (pi === pl) { - // ran out of pattern, still have file left. - // this is only acceptable if we're on the very last - // empty segment of a file with a trailing slash. - // a/* should match a/b/ - return (fi === fl - 1) && (file[fi] === '') - } - - // should be unreachable. - /* istanbul ignore next */ - throw new Error('wtf?') -} - -// replace stuff like \* with * -function globUnescape (s) { - return s.replace(/\\(.)/g, '$1') -} - -function regExpEscape (s) { - return s.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, '\\$&') -} - - -/***/ }), - -/***/ "../../node_modules/minimist/index.js": -/***/ (function(module, exports) { - -module.exports = function (args, opts) { - if (!opts) opts = {}; - - var flags = { bools : {}, strings : {}, unknownFn: null }; - - if (typeof opts['unknown'] === 'function') { - flags.unknownFn = opts['unknown']; - } - - if (typeof opts['boolean'] === 'boolean' && opts['boolean']) { - flags.allBools = true; - } else { - [].concat(opts['boolean']).filter(Boolean).forEach(function (key) { - flags.bools[key] = true; - }); - } - - var aliases = {}; - Object.keys(opts.alias || {}).forEach(function (key) { - aliases[key] = [].concat(opts.alias[key]); - aliases[key].forEach(function (x) { - aliases[x] = [key].concat(aliases[key].filter(function (y) { - return x !== y; - })); - }); - }); - - [].concat(opts.string).filter(Boolean).forEach(function (key) { - flags.strings[key] = true; - if (aliases[key]) { - flags.strings[aliases[key]] = true; - } - }); - - var defaults = opts['default'] || {}; - - var argv = { _ : [] }; - Object.keys(flags.bools).forEach(function (key) { - setArg(key, defaults[key] === undefined ? false : defaults[key]); - }); - - var notFlags = []; - - if (args.indexOf('--') !== -1) { - notFlags = args.slice(args.indexOf('--')+1); - args = args.slice(0, args.indexOf('--')); - } - - function argDefined(key, arg) { - return (flags.allBools && /^--[^=]+$/.test(arg)) || - flags.strings[key] || flags.bools[key] || aliases[key]; - } - - function setArg (key, val, arg) { - if (arg && flags.unknownFn && !argDefined(key, arg)) { - if (flags.unknownFn(arg) === false) return; - } - - var value = !flags.strings[key] && isNumber(val) - ? Number(val) : val - ; - setKey(argv, key.split('.'), value); - - (aliases[key] || []).forEach(function (x) { - setKey(argv, x.split('.'), value); - }); - } - - function setKey (obj, keys, value) { - var o = obj; - for (var i = 0; i < keys.length-1; i++) { - var key = keys[i]; - if (isConstructorOrProto(o, key)) return; - if (o[key] === undefined) o[key] = {}; - if (o[key] === Object.prototype || o[key] === Number.prototype - || o[key] === String.prototype) o[key] = {}; - if (o[key] === Array.prototype) o[key] = []; - o = o[key]; - } - - var key = keys[keys.length - 1]; - if (isConstructorOrProto(o, key)) return; - if (o === Object.prototype || o === Number.prototype - || o === String.prototype) o = {}; - if (o === Array.prototype) o = []; - if (o[key] === undefined || flags.bools[key] || typeof o[key] === 'boolean') { - o[key] = value; - } - else if (Array.isArray(o[key])) { - o[key].push(value); - } - else { - o[key] = [ o[key], value ]; - } - } - - function aliasIsBoolean(key) { - return aliases[key].some(function (x) { - return flags.bools[x]; - }); - } - - for (var i = 0; i < args.length; i++) { - var arg = args[i]; - - if (/^--.+=/.test(arg)) { - // Using [\s\S] instead of . because js doesn't support the - // 'dotall' regex modifier. See: - // http://stackoverflow.com/a/1068308/13216 - var m = arg.match(/^--([^=]+)=([\s\S]*)$/); - var key = m[1]; - var value = m[2]; - if (flags.bools[key]) { - value = value !== 'false'; - } - setArg(key, value, arg); - } - else if (/^--no-.+/.test(arg)) { - var key = arg.match(/^--no-(.+)/)[1]; - setArg(key, false, arg); - } - else if (/^--.+/.test(arg)) { - var key = arg.match(/^--(.+)/)[1]; - var next = args[i + 1]; - if (next !== undefined && !/^-/.test(next) - && !flags.bools[key] - && !flags.allBools - && (aliases[key] ? !aliasIsBoolean(key) : true)) { - setArg(key, next, arg); - i++; - } - else if (/^(true|false)$/.test(next)) { - setArg(key, next === 'true', arg); - i++; - } - else { - setArg(key, flags.strings[key] ? '' : true, arg); - } - } - else if (/^-[^-]+/.test(arg)) { - var letters = arg.slice(1,-1).split(''); - - var broken = false; - for (var j = 0; j < letters.length; j++) { - var next = arg.slice(j+2); - - if (next === '-') { - setArg(letters[j], next, arg) - continue; - } - - if (/[A-Za-z]/.test(letters[j]) && /=/.test(next)) { - setArg(letters[j], next.split('=')[1], arg); - broken = true; - break; - } - - if (/[A-Za-z]/.test(letters[j]) - && /-?\d+(\.\d*)?(e-?\d+)?$/.test(next)) { - setArg(letters[j], next, arg); - broken = true; - break; - } - - if (letters[j+1] && letters[j+1].match(/\W/)) { - setArg(letters[j], arg.slice(j+2), arg); - broken = true; - break; - } - else { - setArg(letters[j], flags.strings[letters[j]] ? '' : true, arg); - } - } - - var key = arg.slice(-1)[0]; - if (!broken && key !== '-') { - if (args[i+1] && !/^(-|--)[^-]/.test(args[i+1]) - && !flags.bools[key] - && (aliases[key] ? !aliasIsBoolean(key) : true)) { - setArg(key, args[i+1], arg); - i++; - } - else if (args[i+1] && /^(true|false)$/.test(args[i+1])) { - setArg(key, args[i+1] === 'true', arg); - i++; - } - else { - setArg(key, flags.strings[key] ? '' : true, arg); - } - } - } - else { - if (!flags.unknownFn || flags.unknownFn(arg) !== false) { - argv._.push( - flags.strings['_'] || !isNumber(arg) ? arg : Number(arg) - ); - } - if (opts.stopEarly) { - argv._.push.apply(argv._, args.slice(i + 1)); - break; - } - } - } - - Object.keys(defaults).forEach(function (key) { - if (!hasKey(argv, key.split('.'))) { - setKey(argv, key.split('.'), defaults[key]); - - (aliases[key] || []).forEach(function (x) { - setKey(argv, x.split('.'), defaults[key]); - }); - } - }); - - if (opts['--']) { - argv['--'] = new Array(); - notFlags.forEach(function(key) { - argv['--'].push(key); - }); - } - else { - notFlags.forEach(function(key) { - argv._.push(key); - }); - } - - return argv; -}; - -function hasKey (obj, keys) { - var o = obj; - keys.slice(0,-1).forEach(function (key) { - o = (o[key] || {}); - }); - - var key = keys[keys.length - 1]; - return key in o; -} - -function isNumber (x) { - if (typeof x === 'number') return true; - if (/^0x[0-9a-f]+$/i.test(x)) return true; - return /^[-+]?(?:\d+(?:\.\d*)?|\.\d+)(e[-+]?\d+)?$/.test(x); -} - - -function isConstructorOrProto (obj, key) { - return key === 'constructor' && typeof obj[key] === 'function' || key === '__proto__'; -} - - -/***/ }), - -/***/ "../../node_modules/mkdirp/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var path = __webpack_require__("path"); -var fs = __webpack_require__("fs"); -var _0777 = parseInt('0777', 8); - -module.exports = mkdirP.mkdirp = mkdirP.mkdirP = mkdirP; - -function mkdirP (p, opts, f, made) { - if (typeof opts === 'function') { - f = opts; - opts = {}; - } - else if (!opts || typeof opts !== 'object') { - opts = { mode: opts }; - } - - var mode = opts.mode; - var xfs = opts.fs || fs; - - if (mode === undefined) { - mode = _0777 & (~process.umask()); - } - if (!made) made = null; - - var cb = f || function () {}; - p = path.resolve(p); - - xfs.mkdir(p, mode, function (er) { - if (!er) { - made = made || p; - return cb(null, made); - } - switch (er.code) { - case 'ENOENT': - if (path.dirname(p) === p) return cb(er); - mkdirP(path.dirname(p), opts, function (er, made) { - if (er) cb(er, made); - else mkdirP(p, opts, cb, made); - }); - break; - - // In the case of any other error, just see if there's a dir - // there already. If so, then hooray! If not, then something - // is borked. - default: - xfs.stat(p, function (er2, stat) { - // if the stat fails, then that's super weird. - // let the original error be the failure reason. - if (er2 || !stat.isDirectory()) cb(er, made) - else cb(null, made); - }); - break; - } - }); -} - -mkdirP.sync = function sync (p, opts, made) { - if (!opts || typeof opts !== 'object') { - opts = { mode: opts }; - } - - var mode = opts.mode; - var xfs = opts.fs || fs; - - if (mode === undefined) { - mode = _0777 & (~process.umask()); - } - if (!made) made = null; - - p = path.resolve(p); - - try { - xfs.mkdirSync(p, mode); - made = made || p; - } - catch (err0) { - switch (err0.code) { - case 'ENOENT' : - made = sync(path.dirname(p), opts, made); - sync(p, opts, made); - break; - - // In the case of any other error, just see if there's a dir - // there already. If so, then hooray! If not, then something - // is borked. - default: - var stat; - try { - stat = xfs.statSync(p); - } - catch (err1) { - throw err0; - } - if (!stat.isDirectory()) throw err0; - break; - } - } - - return made; -}; - - -/***/ }), - -/***/ "../../node_modules/multimatch/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const minimatch = __webpack_require__("../../node_modules/minimatch/minimatch.js"); -const arrayUnion = __webpack_require__("../../node_modules/array-union/index.js"); -const arrayDiffer = __webpack_require__("../../node_modules/array-differ/index.js"); -const arrify = __webpack_require__("../../node_modules/arrify/index.js"); - -module.exports = (list, patterns, options = {}) => { - list = arrify(list); - patterns = arrify(patterns); - - if (list.length === 0 || patterns.length === 0) { - return []; - } - - return patterns.reduce((result, pattern) => { - let process = arrayUnion; - - if (pattern[0] === '!') { - pattern = pattern.slice(1); - process = arrayDiffer; - } - - return process(result, minimatch.match(list, pattern, options)); - }, []); -}; - - -/***/ }), - -/***/ "../../node_modules/mute-stream/mute.js": -/***/ (function(module, exports, __webpack_require__) { - -var Stream = __webpack_require__("stream") - -module.exports = MuteStream - -// var out = new MuteStream(process.stdout) -// argument auto-pipes -function MuteStream (opts) { - Stream.apply(this) - opts = opts || {} - this.writable = this.readable = true - this.muted = false - this.on('pipe', this._onpipe) - this.replace = opts.replace - - // For readline-type situations - // This much at the start of a line being redrawn after a ctrl char - // is seen (such as backspace) won't be redrawn as the replacement - this._prompt = opts.prompt || null - this._hadControl = false -} - -MuteStream.prototype = Object.create(Stream.prototype) - -Object.defineProperty(MuteStream.prototype, 'constructor', { - value: MuteStream, - enumerable: false -}) - -MuteStream.prototype.mute = function () { - this.muted = true -} - -MuteStream.prototype.unmute = function () { - this.muted = false -} - -Object.defineProperty(MuteStream.prototype, '_onpipe', { - value: onPipe, - enumerable: false, - writable: true, - configurable: true -}) - -function onPipe (src) { - this._src = src -} - -Object.defineProperty(MuteStream.prototype, 'isTTY', { - get: getIsTTY, - set: setIsTTY, - enumerable: true, - configurable: true -}) - -function getIsTTY () { - return( (this._dest) ? this._dest.isTTY - : (this._src) ? this._src.isTTY - : false - ) -} - -// basically just get replace the getter/setter with a regular value -function setIsTTY (isTTY) { - Object.defineProperty(this, 'isTTY', { - value: isTTY, - enumerable: true, - writable: true, - configurable: true - }) -} - -Object.defineProperty(MuteStream.prototype, 'rows', { - get: function () { - return( this._dest ? this._dest.rows - : this._src ? this._src.rows - : undefined ) - }, enumerable: true, configurable: true }) - -Object.defineProperty(MuteStream.prototype, 'columns', { - get: function () { - return( this._dest ? this._dest.columns - : this._src ? this._src.columns - : undefined ) - }, enumerable: true, configurable: true }) - - -MuteStream.prototype.pipe = function (dest, options) { - this._dest = dest - return Stream.prototype.pipe.call(this, dest, options) -} - -MuteStream.prototype.pause = function () { - if (this._src) return this._src.pause() -} - -MuteStream.prototype.resume = function () { - if (this._src) return this._src.resume() -} - -MuteStream.prototype.write = function (c) { - if (this.muted) { - if (!this.replace) return true - if (c.match(/^\u001b/)) { - if(c.indexOf(this._prompt) === 0) { - c = c.substr(this._prompt.length); - c = c.replace(/./g, this.replace); - c = this._prompt + c; - } - this._hadControl = true - return this.emit('data', c) - } else { - if (this._prompt && this._hadControl && - c.indexOf(this._prompt) === 0) { - this._hadControl = false - this.emit('data', this._prompt) - c = c.substr(this._prompt.length) - } - c = c.toString().replace(/./g, this.replace) - } - } - this.emit('data', c) -} - -MuteStream.prototype.end = function (c) { - if (this.muted) { - if (c && this.replace) { - c = c.toString().replace(/./g, this.replace) - } else { - c = null - } - } - if (c) this.emit('data', c) - this.emit('end') -} - -function proxy (fn) { return function () { - var d = this._dest - var s = this._src - if (d && d[fn]) d[fn].apply(d, arguments) - if (s && s[fn]) s[fn].apply(s, arguments) -}} - -MuteStream.prototype.destroy = proxy('destroy') -MuteStream.prototype.destroySoon = proxy('destroySoon') -MuteStream.prototype.close = proxy('close') - - -/***/ }), - -/***/ "../../node_modules/ncp/lib/ncp.js": -/***/ (function(module, exports, __webpack_require__) { - -var fs = __webpack_require__("fs"), - path = __webpack_require__("path"); - -module.exports = ncp; -ncp.ncp = ncp; - -function ncp (source, dest, options, callback) { - var cback = callback; - - if (!callback) { - cback = options; - options = {}; - } - - var basePath = process.cwd(), - currentPath = path.resolve(basePath, source), - targetPath = path.resolve(basePath, dest), - filter = options.filter, - rename = options.rename, - transform = options.transform, - clobber = options.clobber !== false, - modified = options.modified, - dereference = options.dereference, - errs = null, - started = 0, - finished = 0, - running = 0, - limit = options.limit || ncp.limit || 16; - - limit = (limit < 1) ? 1 : (limit > 512) ? 512 : limit; - - startCopy(currentPath); - - function startCopy(source) { - started++; - if (filter) { - if (filter instanceof RegExp) { - if (!filter.test(source)) { - return cb(true); - } - } - else if (typeof filter === 'function') { - if (!filter(source)) { - return cb(true); - } - } - } - return getStats(source); - } - - function getStats(source) { - var stat = dereference ? fs.stat : fs.lstat; - if (running >= limit) { - return setImmediate(function () { - getStats(source); - }); - } - running++; - stat(source, function (err, stats) { - var item = {}; - if (err) { - return onError(err); - } - - // We need to get the mode from the stats object and preserve it. - item.name = source; - item.mode = stats.mode; - item.mtime = stats.mtime; //modified time - item.atime = stats.atime; //access time - - if (stats.isDirectory()) { - return onDir(item); - } - else if (stats.isFile()) { - return onFile(item); - } - else if (stats.isSymbolicLink()) { - // Symlinks don't really need to know about the mode. - return onLink(source); - } - }); - } - - function onFile(file) { - var target = file.name.replace(currentPath, targetPath); - if(rename) { - target = rename(target); - } - isWritable(target, function (writable) { - if (writable) { - return copyFile(file, target); - } - if(clobber) { - rmFile(target, function () { - copyFile(file, target); - }); - } - if (modified) { - var stat = dereference ? fs.stat : fs.lstat; - stat(target, function(err, stats) { - //if souce modified time greater to target modified time copy file - if (file.mtime.getTime()>stats.mtime.getTime()) - copyFile(file, target); - else return cb(); - }); - } - else { - return cb(); - } - }); - } - - function copyFile(file, target) { - var readStream = fs.createReadStream(file.name), - writeStream = fs.createWriteStream(target, { mode: file.mode }); - - readStream.on('error', onError); - writeStream.on('error', onError); - - if(transform) { - transform(readStream, writeStream, file); - } else { - writeStream.on('open', function() { - readStream.pipe(writeStream); - }); - } - writeStream.once('finish', function() { - if (modified) { - //target file modified date sync. - fs.utimesSync(target, file.atime, file.mtime); - cb(); - } - else cb(); - }); - } - - function rmFile(file, done) { - fs.unlink(file, function (err) { - if (err) { - return onError(err); - } - return done(); - }); - } - - function onDir(dir) { - var target = dir.name.replace(currentPath, targetPath); - isWritable(target, function (writable) { - if (writable) { - return mkDir(dir, target); - } - copyDir(dir.name); - }); - } - - function mkDir(dir, target) { - fs.mkdir(target, dir.mode, function (err) { - if (err) { - return onError(err); - } - copyDir(dir.name); - }); - } - - function copyDir(dir) { - fs.readdir(dir, function (err, items) { - if (err) { - return onError(err); - } - items.forEach(function (item) { - startCopy(path.join(dir, item)); - }); - return cb(); - }); - } - - function onLink(link) { - var target = link.replace(currentPath, targetPath); - fs.readlink(link, function (err, resolvedPath) { - if (err) { - return onError(err); - } - checkLink(resolvedPath, target); - }); - } - - function checkLink(resolvedPath, target) { - if (dereference) { - resolvedPath = path.resolve(basePath, resolvedPath); - } - isWritable(target, function (writable) { - if (writable) { - return makeLink(resolvedPath, target); - } - fs.readlink(target, function (err, targetDest) { - if (err) { - return onError(err); - } - if (dereference) { - targetDest = path.resolve(basePath, targetDest); - } - if (targetDest === resolvedPath) { - return cb(); - } - return rmFile(target, function () { - makeLink(resolvedPath, target); - }); - }); - }); - } - - function makeLink(linkPath, target) { - fs.symlink(linkPath, target, function (err) { - if (err) { - return onError(err); - } - return cb(); - }); - } - - function isWritable(path, done) { - fs.lstat(path, function (err) { - if (err) { - if (err.code === 'ENOENT') return done(true); - return done(false); - } - return done(false); - }); - } - - function onError(err) { - if (options.stopOnError) { - return cback(err); - } - else if (!errs && options.errs) { - errs = fs.createWriteStream(options.errs); - } - else if (!errs) { - errs = []; - } - if (typeof errs.write === 'undefined') { - errs.push(err); - } - else { - errs.write(err.stack + '\n\n'); - } - return cb(); - } - - function cb(skipped) { - if (!skipped) running--; - finished++; - if ((started === finished) && (running === 0)) { - if (cback !== undefined ) { - return errs ? cback(errs) : cback(null); - } - } - } -} - - - - -/***/ }), - -/***/ "../../node_modules/normalize-package-data/lib/extract_description.js": -/***/ (function(module, exports) { - -module.exports = extractDescription - -// Extracts description from contents of a readme file in markdown format -function extractDescription (d) { - if (!d) return; - if (d === "ERROR: No README data found!") return; - // the first block of text before the first heading - // that isn't the first line heading - d = d.trim().split('\n') - for (var s = 0; d[s] && d[s].trim().match(/^(#|$)/); s ++); - var l = d.length - for (var e = s + 1; e < l && d[e].trim(); e ++); - return d.slice(s, e).join(' ').trim() -} - - -/***/ }), - -/***/ "../../node_modules/normalize-package-data/lib/fixer.js": -/***/ (function(module, exports, __webpack_require__) { - -var semver = __webpack_require__("../../node_modules/normalize-package-data/node_modules/semver/semver.js") -var validateLicense = __webpack_require__("../../node_modules/validate-npm-package-license/index.js"); -var hostedGitInfo = __webpack_require__("../../node_modules/hosted-git-info/index.js") -var isBuiltinModule = __webpack_require__("../../node_modules/resolve/index.js").isCore -var depTypes = ["dependencies","devDependencies","optionalDependencies"] -var extractDescription = __webpack_require__("../../node_modules/normalize-package-data/lib/extract_description.js") -var url = __webpack_require__("url") -var typos = __webpack_require__("../../node_modules/normalize-package-data/lib/typos.json") - -var fixer = module.exports = { - // default warning function - warn: function() {}, - - fixRepositoryField: function(data) { - if (data.repositories) { - this.warn("repositories"); - data.repository = data.repositories[0] - } - if (!data.repository) return this.warn("missingRepository") - if (typeof data.repository === "string") { - data.repository = { - type: "git", - url: data.repository - } - } - var r = data.repository.url || "" - if (r) { - var hosted = hostedGitInfo.fromUrl(r) - if (hosted) { - r = data.repository.url - = hosted.getDefaultRepresentation() == "shortcut" ? hosted.https() : hosted.toString() - } - } - - if (r.match(/github.com\/[^\/]+\/[^\/]+\.git\.git$/)) { - this.warn("brokenGitUrl", r) - } - } - -, fixTypos: function(data) { - Object.keys(typos.topLevel).forEach(function (d) { - if (data.hasOwnProperty(d)) { - this.warn("typo", d, typos.topLevel[d]) - } - }, this) - } - -, fixScriptsField: function(data) { - if (!data.scripts) return - if (typeof data.scripts !== "object") { - this.warn("nonObjectScripts") - delete data.scripts - return - } - Object.keys(data.scripts).forEach(function (k) { - if (typeof data.scripts[k] !== "string") { - this.warn("nonStringScript") - delete data.scripts[k] - } else if (typos.script[k] && !data.scripts[typos.script[k]]) { - this.warn("typo", k, typos.script[k], "scripts") - } - }, this) - } - -, fixFilesField: function(data) { - var files = data.files - if (files && !Array.isArray(files)) { - this.warn("nonArrayFiles") - delete data.files - } else if (data.files) { - data.files = data.files.filter(function(file) { - if (!file || typeof file !== "string") { - this.warn("invalidFilename", file) - return false - } else { - return true - } - }, this) - } - } - -, fixBinField: function(data) { - if (!data.bin) return; - if (typeof data.bin === "string") { - var b = {} - var match - if (match = data.name.match(/^@[^/]+[/](.*)$/)) { - b[match[1]] = data.bin - } else { - b[data.name] = data.bin - } - data.bin = b - } - } - -, fixManField: function(data) { - if (!data.man) return; - if (typeof data.man === "string") { - data.man = [ data.man ] - } - } -, fixBundleDependenciesField: function(data) { - var bdd = "bundledDependencies" - var bd = "bundleDependencies" - if (data[bdd] && !data[bd]) { - data[bd] = data[bdd] - delete data[bdd] - } - if (data[bd] && !Array.isArray(data[bd])) { - this.warn("nonArrayBundleDependencies") - delete data[bd] - } else if (data[bd]) { - data[bd] = data[bd].filter(function(bd) { - if (!bd || typeof bd !== 'string') { - this.warn("nonStringBundleDependency", bd) - return false - } else { - if (!data.dependencies) { - data.dependencies = {} - } - if (!data.dependencies.hasOwnProperty(bd)) { - this.warn("nonDependencyBundleDependency", bd) - data.dependencies[bd] = "*" - } - return true - } - }, this) - } - } - -, fixDependencies: function(data, strict) { - var loose = !strict - objectifyDeps(data, this.warn) - addOptionalDepsToDeps(data, this.warn) - this.fixBundleDependenciesField(data) - - ;['dependencies','devDependencies'].forEach(function(deps) { - if (!(deps in data)) return - if (!data[deps] || typeof data[deps] !== "object") { - this.warn("nonObjectDependencies", deps) - delete data[deps] - return - } - Object.keys(data[deps]).forEach(function (d) { - var r = data[deps][d] - if (typeof r !== 'string') { - this.warn("nonStringDependency", d, JSON.stringify(r)) - delete data[deps][d] - } - var hosted = hostedGitInfo.fromUrl(data[deps][d]) - if (hosted) data[deps][d] = hosted.toString() - }, this) - }, this) - } - -, fixModulesField: function (data) { - if (data.modules) { - this.warn("deprecatedModules") - delete data.modules - } - } - -, fixKeywordsField: function (data) { - if (typeof data.keywords === "string") { - data.keywords = data.keywords.split(/,\s+/) - } - if (data.keywords && !Array.isArray(data.keywords)) { - delete data.keywords - this.warn("nonArrayKeywords") - } else if (data.keywords) { - data.keywords = data.keywords.filter(function(kw) { - if (typeof kw !== "string" || !kw) { - this.warn("nonStringKeyword"); - return false - } else { - return true - } - }, this) - } - } - -, fixVersionField: function(data, strict) { - // allow "loose" semver 1.0 versions in non-strict mode - // enforce strict semver 2.0 compliance in strict mode - var loose = !strict - if (!data.version) { - data.version = "" - return true - } - if (!semver.valid(data.version, loose)) { - throw new Error('Invalid version: "'+ data.version + '"') - } - data.version = semver.clean(data.version, loose) - return true - } - -, fixPeople: function(data) { - modifyPeople(data, unParsePerson) - modifyPeople(data, parsePerson) - } - -, fixNameField: function(data, options) { - if (typeof options === "boolean") options = {strict: options} - else if (typeof options === "undefined") options = {} - var strict = options.strict - if (!data.name && !strict) { - data.name = "" - return - } - if (typeof data.name !== "string") { - throw new Error("name field must be a string.") - } - if (!strict) - data.name = data.name.trim() - ensureValidName(data.name, strict, options.allowLegacyCase) - if (isBuiltinModule(data.name)) - this.warn("conflictingName", data.name) - } - - -, fixDescriptionField: function (data) { - if (data.description && typeof data.description !== 'string') { - this.warn("nonStringDescription") - delete data.description - } - if (data.readme && !data.description) - data.description = extractDescription(data.readme) - if(data.description === undefined) delete data.description; - if (!data.description) this.warn("missingDescription") - } - -, fixReadmeField: function (data) { - if (!data.readme) { - this.warn("missingReadme") - data.readme = "ERROR: No README data found!" - } - } - -, fixBugsField: function(data) { - if (!data.bugs && data.repository && data.repository.url) { - var hosted = hostedGitInfo.fromUrl(data.repository.url) - if(hosted && hosted.bugs()) { - data.bugs = {url: hosted.bugs()} - } - } - else if(data.bugs) { - var emailRe = /^.+@.*\..+$/ - if(typeof data.bugs == "string") { - if(emailRe.test(data.bugs)) - data.bugs = {email:data.bugs} - else if(url.parse(data.bugs).protocol) - data.bugs = {url: data.bugs} - else - this.warn("nonEmailUrlBugsString") - } - else { - bugsTypos(data.bugs, this.warn) - var oldBugs = data.bugs - data.bugs = {} - if(oldBugs.url) { - if(typeof(oldBugs.url) == "string" && url.parse(oldBugs.url).protocol) - data.bugs.url = oldBugs.url - else - this.warn("nonUrlBugsUrlField") - } - if(oldBugs.email) { - if(typeof(oldBugs.email) == "string" && emailRe.test(oldBugs.email)) - data.bugs.email = oldBugs.email - else - this.warn("nonEmailBugsEmailField") - } - } - if(!data.bugs.email && !data.bugs.url) { - delete data.bugs - this.warn("emptyNormalizedBugs") - } - } - } - -, fixHomepageField: function(data) { - if (!data.homepage && data.repository && data.repository.url) { - var hosted = hostedGitInfo.fromUrl(data.repository.url) - if (hosted && hosted.docs()) data.homepage = hosted.docs() - } - if (!data.homepage) return - - if(typeof data.homepage !== "string") { - this.warn("nonUrlHomepage") - return delete data.homepage - } - if(!url.parse(data.homepage).protocol) { - data.homepage = "http://" + data.homepage - } - } - -, fixLicenseField: function(data) { - if (!data.license) { - return this.warn("missingLicense") - } else{ - if ( - typeof(data.license) !== 'string' || - data.license.length < 1 || - data.license.trim() === '' - ) { - this.warn("invalidLicense") - } else { - if (!validateLicense(data.license).validForNewPackages) - this.warn("invalidLicense") - } - } - } -} - -function isValidScopedPackageName(spec) { - if (spec.charAt(0) !== '@') return false - - var rest = spec.slice(1).split('/') - if (rest.length !== 2) return false - - return rest[0] && rest[1] && - rest[0] === encodeURIComponent(rest[0]) && - rest[1] === encodeURIComponent(rest[1]) -} - -function isCorrectlyEncodedName(spec) { - return !spec.match(/[\/@\s\+%:]/) && - spec === encodeURIComponent(spec) -} - -function ensureValidName (name, strict, allowLegacyCase) { - if (name.charAt(0) === "." || - !(isValidScopedPackageName(name) || isCorrectlyEncodedName(name)) || - (strict && (!allowLegacyCase) && name !== name.toLowerCase()) || - name.toLowerCase() === "node_modules" || - name.toLowerCase() === "favicon.ico") { - throw new Error("Invalid name: " + JSON.stringify(name)) - } -} - -function modifyPeople (data, fn) { - if (data.author) data.author = fn(data.author) - ;["maintainers", "contributors"].forEach(function (set) { - if (!Array.isArray(data[set])) return; - data[set] = data[set].map(fn) - }) - return data -} - -function unParsePerson (person) { - if (typeof person === "string") return person - var name = person.name || "" - var u = person.url || person.web - var url = u ? (" ("+u+")") : "" - var e = person.email || person.mail - var email = e ? (" <"+e+">") : "" - return name+email+url -} - -function parsePerson (person) { - if (typeof person !== "string") return person - var name = person.match(/^([^\(<]+)/) - var url = person.match(/\(([^\)]+)\)/) - var email = person.match(/<([^>]+)>/) - var obj = {} - if (name && name[0].trim()) obj.name = name[0].trim() - if (email) obj.email = email[1]; - if (url) obj.url = url[1]; - return obj -} - -function addOptionalDepsToDeps (data, warn) { - var o = data.optionalDependencies - if (!o) return; - var d = data.dependencies || {} - Object.keys(o).forEach(function (k) { - d[k] = o[k] - }) - data.dependencies = d -} - -function depObjectify (deps, type, warn) { - if (!deps) return {} - if (typeof deps === "string") { - deps = deps.trim().split(/[\n\r\s\t ,]+/) - } - if (!Array.isArray(deps)) return deps - warn("deprecatedArrayDependencies", type) - var o = {} - deps.filter(function (d) { - return typeof d === "string" - }).forEach(function(d) { - d = d.trim().split(/(:?[@\s><=])/) - var dn = d.shift() - var dv = d.join("") - dv = dv.trim() - dv = dv.replace(/^@/, "") - o[dn] = dv - }) - return o -} - -function objectifyDeps (data, warn) { - depTypes.forEach(function (type) { - if (!data[type]) return; - data[type] = depObjectify(data[type], type, warn) - }) -} - -function bugsTypos(bugs, warn) { - if (!bugs) return - Object.keys(bugs).forEach(function (k) { - if (typos.bugs[k]) { - warn("typo", k, typos.bugs[k], "bugs") - bugs[typos.bugs[k]] = bugs[k] - delete bugs[k] - } - }) -} - - -/***/ }), - -/***/ "../../node_modules/normalize-package-data/lib/make_warning.js": -/***/ (function(module, exports, __webpack_require__) { - -var util = __webpack_require__("util") -var messages = __webpack_require__("../../node_modules/normalize-package-data/lib/warning_messages.json") - -module.exports = function() { - var args = Array.prototype.slice.call(arguments, 0) - var warningName = args.shift() - if (warningName == "typo") { - return makeTypoWarning.apply(null,args) - } - else { - var msgTemplate = messages[warningName] ? messages[warningName] : warningName + ": '%s'" - args.unshift(msgTemplate) - return util.format.apply(null, args) - } -} - -function makeTypoWarning (providedName, probableName, field) { - if (field) { - providedName = field + "['" + providedName + "']" - probableName = field + "['" + probableName + "']" - } - return util.format(messages.typo, providedName, probableName) -} - - -/***/ }), - -/***/ "../../node_modules/normalize-package-data/lib/normalize.js": -/***/ (function(module, exports, __webpack_require__) { - -module.exports = normalize - -var fixer = __webpack_require__("../../node_modules/normalize-package-data/lib/fixer.js") -normalize.fixer = fixer - -var makeWarning = __webpack_require__("../../node_modules/normalize-package-data/lib/make_warning.js") - -var fieldsToFix = ['name','version','description','repository','modules','scripts' - ,'files','bin','man','bugs','keywords','readme','homepage','license'] -var otherThingsToFix = ['dependencies','people', 'typos'] - -var thingsToFix = fieldsToFix.map(function(fieldName) { - return ucFirst(fieldName) + "Field" -}) -// two ways to do this in CoffeeScript on only one line, sub-70 chars: -// thingsToFix = fieldsToFix.map (name) -> ucFirst(name) + "Field" -// thingsToFix = (ucFirst(name) + "Field" for name in fieldsToFix) -thingsToFix = thingsToFix.concat(otherThingsToFix) - -function normalize (data, warn, strict) { - if(warn === true) warn = null, strict = true - if(!strict) strict = false - if(!warn || data.private) warn = function(msg) { /* noop */ } - - if (data.scripts && - data.scripts.install === "node-gyp rebuild" && - !data.scripts.preinstall) { - data.gypfile = true - } - fixer.warn = function() { warn(makeWarning.apply(null, arguments)) } - thingsToFix.forEach(function(thingName) { - fixer["fix" + ucFirst(thingName)](data, strict) - }) - data._id = data.name + "@" + data.version -} - -function ucFirst (string) { - return string.charAt(0).toUpperCase() + string.slice(1); -} - - -/***/ }), - -/***/ "../../node_modules/normalize-package-data/lib/typos.json": -/***/ (function(module) { - -module.exports = JSON.parse("{\"topLevel\":{\"dependancies\":\"dependencies\",\"dependecies\":\"dependencies\",\"depdenencies\":\"dependencies\",\"devEependencies\":\"devDependencies\",\"depends\":\"dependencies\",\"dev-dependencies\":\"devDependencies\",\"devDependences\":\"devDependencies\",\"devDepenencies\":\"devDependencies\",\"devdependencies\":\"devDependencies\",\"repostitory\":\"repository\",\"repo\":\"repository\",\"prefereGlobal\":\"preferGlobal\",\"hompage\":\"homepage\",\"hampage\":\"homepage\",\"autohr\":\"author\",\"autor\":\"author\",\"contributers\":\"contributors\",\"publicationConfig\":\"publishConfig\",\"script\":\"scripts\"},\"bugs\":{\"web\":\"url\",\"name\":\"url\"},\"script\":{\"server\":\"start\",\"tests\":\"test\"}}"); - -/***/ }), - -/***/ "../../node_modules/normalize-package-data/lib/warning_messages.json": -/***/ (function(module) { - -module.exports = JSON.parse("{\"repositories\":\"'repositories' (plural) Not supported. Please pick one as the 'repository' field\",\"missingRepository\":\"No repository field.\",\"brokenGitUrl\":\"Probably broken git url: %s\",\"nonObjectScripts\":\"scripts must be an object\",\"nonStringScript\":\"script values must be string commands\",\"nonArrayFiles\":\"Invalid 'files' member\",\"invalidFilename\":\"Invalid filename in 'files' list: %s\",\"nonArrayBundleDependencies\":\"Invalid 'bundleDependencies' list. Must be array of package names\",\"nonStringBundleDependency\":\"Invalid bundleDependencies member: %s\",\"nonDependencyBundleDependency\":\"Non-dependency in bundleDependencies: %s\",\"nonObjectDependencies\":\"%s field must be an object\",\"nonStringDependency\":\"Invalid dependency: %s %s\",\"deprecatedArrayDependencies\":\"specifying %s as array is deprecated\",\"deprecatedModules\":\"modules field is deprecated\",\"nonArrayKeywords\":\"keywords should be an array of strings\",\"nonStringKeyword\":\"keywords should be an array of strings\",\"conflictingName\":\"%s is also the name of a node core module.\",\"nonStringDescription\":\"'description' field should be a string\",\"missingDescription\":\"No description\",\"missingReadme\":\"No README data\",\"missingLicense\":\"No license field.\",\"nonEmailUrlBugsString\":\"Bug string field must be url, email, or {email,url}\",\"nonUrlBugsUrlField\":\"bugs.url field must be a string url. Deleted.\",\"nonEmailBugsEmailField\":\"bugs.email field must be a string email. Deleted.\",\"emptyNormalizedBugs\":\"Normalized value of bugs field is an empty object. Deleted.\",\"nonUrlHomepage\":\"homepage field must be a string url. Deleted.\",\"invalidLicense\":\"license should be a valid SPDX license expression\",\"typo\":\"%s should probably be %s.\"}"); - -/***/ }), - -/***/ "../../node_modules/normalize-package-data/node_modules/semver/semver.js": -/***/ (function(module, exports) { - -exports = module.exports = SemVer - -var debug -/* istanbul ignore next */ -if (typeof process === 'object' && - process.env && - process.env.NODE_DEBUG && - /\bsemver\b/i.test(process.env.NODE_DEBUG)) { - debug = function () { - var args = Array.prototype.slice.call(arguments, 0) - args.unshift('SEMVER') - console.log.apply(console, args) - } -} else { - debug = function () {} -} - -// Note: this is the semver.org version of the spec that it implements -// Not necessarily the package version of this code. -exports.SEMVER_SPEC_VERSION = '2.0.0' - -var MAX_LENGTH = 256 -var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || - /* istanbul ignore next */ 9007199254740991 - -// Max safe segment length for coercion. -var MAX_SAFE_COMPONENT_LENGTH = 16 - -// The actual regexps go on exports.re -var re = exports.re = [] -var src = exports.src = [] -var R = 0 - -// The following Regular Expressions can be used for tokenizing, -// validating, and parsing SemVer version strings. - -// ## Numeric Identifier -// A single `0`, or a non-zero digit followed by zero or more digits. - -var NUMERICIDENTIFIER = R++ -src[NUMERICIDENTIFIER] = '0|[1-9]\\d*' -var NUMERICIDENTIFIERLOOSE = R++ -src[NUMERICIDENTIFIERLOOSE] = '[0-9]+' - -// ## Non-numeric Identifier -// Zero or more digits, followed by a letter or hyphen, and then zero or -// more letters, digits, or hyphens. - -var NONNUMERICIDENTIFIER = R++ -src[NONNUMERICIDENTIFIER] = '\\d*[a-zA-Z-][a-zA-Z0-9-]*' - -// ## Main Version -// Three dot-separated numeric identifiers. - -var MAINVERSION = R++ -src[MAINVERSION] = '(' + src[NUMERICIDENTIFIER] + ')\\.' + - '(' + src[NUMERICIDENTIFIER] + ')\\.' + - '(' + src[NUMERICIDENTIFIER] + ')' - -var MAINVERSIONLOOSE = R++ -src[MAINVERSIONLOOSE] = '(' + src[NUMERICIDENTIFIERLOOSE] + ')\\.' + - '(' + src[NUMERICIDENTIFIERLOOSE] + ')\\.' + - '(' + src[NUMERICIDENTIFIERLOOSE] + ')' - -// ## Pre-release Version Identifier -// A numeric identifier, or a non-numeric identifier. - -var PRERELEASEIDENTIFIER = R++ -src[PRERELEASEIDENTIFIER] = '(?:' + src[NUMERICIDENTIFIER] + - '|' + src[NONNUMERICIDENTIFIER] + ')' - -var PRERELEASEIDENTIFIERLOOSE = R++ -src[PRERELEASEIDENTIFIERLOOSE] = '(?:' + src[NUMERICIDENTIFIERLOOSE] + - '|' + src[NONNUMERICIDENTIFIER] + ')' - -// ## Pre-release Version -// Hyphen, followed by one or more dot-separated pre-release version -// identifiers. - -var PRERELEASE = R++ -src[PRERELEASE] = '(?:-(' + src[PRERELEASEIDENTIFIER] + - '(?:\\.' + src[PRERELEASEIDENTIFIER] + ')*))' - -var PRERELEASELOOSE = R++ -src[PRERELEASELOOSE] = '(?:-?(' + src[PRERELEASEIDENTIFIERLOOSE] + - '(?:\\.' + src[PRERELEASEIDENTIFIERLOOSE] + ')*))' - -// ## Build Metadata Identifier -// Any combination of digits, letters, or hyphens. - -var BUILDIDENTIFIER = R++ -src[BUILDIDENTIFIER] = '[0-9A-Za-z-]+' - -// ## Build Metadata -// Plus sign, followed by one or more period-separated build metadata -// identifiers. - -var BUILD = R++ -src[BUILD] = '(?:\\+(' + src[BUILDIDENTIFIER] + - '(?:\\.' + src[BUILDIDENTIFIER] + ')*))' - -// ## Full Version String -// A main version, followed optionally by a pre-release version and -// build metadata. - -// Note that the only major, minor, patch, and pre-release sections of -// the version string are capturing groups. The build metadata is not a -// capturing group, because it should not ever be used in version -// comparison. - -var FULL = R++ -var FULLPLAIN = 'v?' + src[MAINVERSION] + - src[PRERELEASE] + '?' + - src[BUILD] + '?' - -src[FULL] = '^' + FULLPLAIN + '$' - -// like full, but allows v1.2.3 and =1.2.3, which people do sometimes. -// also, 1.0.0alpha1 (prerelease without the hyphen) which is pretty -// common in the npm registry. -var LOOSEPLAIN = '[v=\\s]*' + src[MAINVERSIONLOOSE] + - src[PRERELEASELOOSE] + '?' + - src[BUILD] + '?' - -var LOOSE = R++ -src[LOOSE] = '^' + LOOSEPLAIN + '$' - -var GTLT = R++ -src[GTLT] = '((?:<|>)?=?)' - -// Something like "2.*" or "1.2.x". -// Note that "x.x" is a valid xRange identifer, meaning "any version" -// Only the first item is strictly required. -var XRANGEIDENTIFIERLOOSE = R++ -src[XRANGEIDENTIFIERLOOSE] = src[NUMERICIDENTIFIERLOOSE] + '|x|X|\\*' -var XRANGEIDENTIFIER = R++ -src[XRANGEIDENTIFIER] = src[NUMERICIDENTIFIER] + '|x|X|\\*' - -var XRANGEPLAIN = R++ -src[XRANGEPLAIN] = '[v=\\s]*(' + src[XRANGEIDENTIFIER] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIER] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIER] + ')' + - '(?:' + src[PRERELEASE] + ')?' + - src[BUILD] + '?' + - ')?)?' - -var XRANGEPLAINLOOSE = R++ -src[XRANGEPLAINLOOSE] = '[v=\\s]*(' + src[XRANGEIDENTIFIERLOOSE] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIERLOOSE] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIERLOOSE] + ')' + - '(?:' + src[PRERELEASELOOSE] + ')?' + - src[BUILD] + '?' + - ')?)?' - -var XRANGE = R++ -src[XRANGE] = '^' + src[GTLT] + '\\s*' + src[XRANGEPLAIN] + '$' -var XRANGELOOSE = R++ -src[XRANGELOOSE] = '^' + src[GTLT] + '\\s*' + src[XRANGEPLAINLOOSE] + '$' - -// Coercion. -// Extract anything that could conceivably be a part of a valid semver -var COERCE = R++ -src[COERCE] = '(?:^|[^\\d])' + - '(\\d{1,' + MAX_SAFE_COMPONENT_LENGTH + '})' + - '(?:\\.(\\d{1,' + MAX_SAFE_COMPONENT_LENGTH + '}))?' + - '(?:\\.(\\d{1,' + MAX_SAFE_COMPONENT_LENGTH + '}))?' + - '(?:$|[^\\d])' - -// Tilde ranges. -// Meaning is "reasonably at or greater than" -var LONETILDE = R++ -src[LONETILDE] = '(?:~>?)' - -var TILDETRIM = R++ -src[TILDETRIM] = '(\\s*)' + src[LONETILDE] + '\\s+' -re[TILDETRIM] = new RegExp(src[TILDETRIM], 'g') -var tildeTrimReplace = '$1~' - -var TILDE = R++ -src[TILDE] = '^' + src[LONETILDE] + src[XRANGEPLAIN] + '$' -var TILDELOOSE = R++ -src[TILDELOOSE] = '^' + src[LONETILDE] + src[XRANGEPLAINLOOSE] + '$' - -// Caret ranges. -// Meaning is "at least and backwards compatible with" -var LONECARET = R++ -src[LONECARET] = '(?:\\^)' - -var CARETTRIM = R++ -src[CARETTRIM] = '(\\s*)' + src[LONECARET] + '\\s+' -re[CARETTRIM] = new RegExp(src[CARETTRIM], 'g') -var caretTrimReplace = '$1^' - -var CARET = R++ -src[CARET] = '^' + src[LONECARET] + src[XRANGEPLAIN] + '$' -var CARETLOOSE = R++ -src[CARETLOOSE] = '^' + src[LONECARET] + src[XRANGEPLAINLOOSE] + '$' - -// A simple gt/lt/eq thing, or just "" to indicate "any version" -var COMPARATORLOOSE = R++ -src[COMPARATORLOOSE] = '^' + src[GTLT] + '\\s*(' + LOOSEPLAIN + ')$|^$' -var COMPARATOR = R++ -src[COMPARATOR] = '^' + src[GTLT] + '\\s*(' + FULLPLAIN + ')$|^$' - -// An expression to strip any whitespace between the gtlt and the thing -// it modifies, so that `> 1.2.3` ==> `>1.2.3` -var COMPARATORTRIM = R++ -src[COMPARATORTRIM] = '(\\s*)' + src[GTLT] + - '\\s*(' + LOOSEPLAIN + '|' + src[XRANGEPLAIN] + ')' - -// this one has to use the /g flag -re[COMPARATORTRIM] = new RegExp(src[COMPARATORTRIM], 'g') -var comparatorTrimReplace = '$1$2$3' - -// Something like `1.2.3 - 1.2.4` -// Note that these all use the loose form, because they'll be -// checked against either the strict or loose comparator form -// later. -var HYPHENRANGE = R++ -src[HYPHENRANGE] = '^\\s*(' + src[XRANGEPLAIN] + ')' + - '\\s+-\\s+' + - '(' + src[XRANGEPLAIN] + ')' + - '\\s*$' - -var HYPHENRANGELOOSE = R++ -src[HYPHENRANGELOOSE] = '^\\s*(' + src[XRANGEPLAINLOOSE] + ')' + - '\\s+-\\s+' + - '(' + src[XRANGEPLAINLOOSE] + ')' + - '\\s*$' - -// Star ranges basically just allow anything at all. -var STAR = R++ -src[STAR] = '(<|>)?=?\\s*\\*' - -// Compile to actual regexp objects. -// All are flag-free, unless they were created above with a flag. -for (var i = 0; i < R; i++) { - debug(i, src[i]) - if (!re[i]) { - re[i] = new RegExp(src[i]) - } -} - -exports.parse = parse -function parse (version, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - if (version instanceof SemVer) { - return version - } - - if (typeof version !== 'string') { - return null - } - - if (version.length > MAX_LENGTH) { - return null - } - - var r = options.loose ? re[LOOSE] : re[FULL] - if (!r.test(version)) { - return null - } - - try { - return new SemVer(version, options) - } catch (er) { - return null - } -} - -exports.valid = valid -function valid (version, options) { - var v = parse(version, options) - return v ? v.version : null -} - -exports.clean = clean -function clean (version, options) { - var s = parse(version.trim().replace(/^[=v]+/, ''), options) - return s ? s.version : null -} - -exports.SemVer = SemVer - -function SemVer (version, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - if (version instanceof SemVer) { - if (version.loose === options.loose) { - return version - } else { - version = version.version - } - } else if (typeof version !== 'string') { - throw new TypeError('Invalid Version: ' + version) - } - - if (version.length > MAX_LENGTH) { - throw new TypeError('version is longer than ' + MAX_LENGTH + ' characters') - } - - if (!(this instanceof SemVer)) { - return new SemVer(version, options) - } - - debug('SemVer', version, options) - this.options = options - this.loose = !!options.loose - - var m = version.trim().match(options.loose ? re[LOOSE] : re[FULL]) - - if (!m) { - throw new TypeError('Invalid Version: ' + version) - } - - this.raw = version - - // these are actually numbers - this.major = +m[1] - this.minor = +m[2] - this.patch = +m[3] - - if (this.major > MAX_SAFE_INTEGER || this.major < 0) { - throw new TypeError('Invalid major version') - } - - if (this.minor > MAX_SAFE_INTEGER || this.minor < 0) { - throw new TypeError('Invalid minor version') - } - - if (this.patch > MAX_SAFE_INTEGER || this.patch < 0) { - throw new TypeError('Invalid patch version') - } - - // numberify any prerelease numeric ids - if (!m[4]) { - this.prerelease = [] - } else { - this.prerelease = m[4].split('.').map(function (id) { - if (/^[0-9]+$/.test(id)) { - var num = +id - if (num >= 0 && num < MAX_SAFE_INTEGER) { - return num - } - } - return id - }) - } - - this.build = m[5] ? m[5].split('.') : [] - this.format() -} - -SemVer.prototype.format = function () { - this.version = this.major + '.' + this.minor + '.' + this.patch - if (this.prerelease.length) { - this.version += '-' + this.prerelease.join('.') - } - return this.version -} - -SemVer.prototype.toString = function () { - return this.version -} - -SemVer.prototype.compare = function (other) { - debug('SemVer.compare', this.version, this.options, other) - if (!(other instanceof SemVer)) { - other = new SemVer(other, this.options) - } - - return this.compareMain(other) || this.comparePre(other) -} - -SemVer.prototype.compareMain = function (other) { - if (!(other instanceof SemVer)) { - other = new SemVer(other, this.options) - } - - return compareIdentifiers(this.major, other.major) || - compareIdentifiers(this.minor, other.minor) || - compareIdentifiers(this.patch, other.patch) -} - -SemVer.prototype.comparePre = function (other) { - if (!(other instanceof SemVer)) { - other = new SemVer(other, this.options) - } - - // NOT having a prerelease is > having one - if (this.prerelease.length && !other.prerelease.length) { - return -1 - } else if (!this.prerelease.length && other.prerelease.length) { - return 1 - } else if (!this.prerelease.length && !other.prerelease.length) { - return 0 - } - - var i = 0 - do { - var a = this.prerelease[i] - var b = other.prerelease[i] - debug('prerelease compare', i, a, b) - if (a === undefined && b === undefined) { - return 0 - } else if (b === undefined) { - return 1 - } else if (a === undefined) { - return -1 - } else if (a === b) { - continue - } else { - return compareIdentifiers(a, b) - } - } while (++i) -} - -// preminor will bump the version up to the next minor release, and immediately -// down to pre-release. premajor and prepatch work the same way. -SemVer.prototype.inc = function (release, identifier) { - switch (release) { - case 'premajor': - this.prerelease.length = 0 - this.patch = 0 - this.minor = 0 - this.major++ - this.inc('pre', identifier) - break - case 'preminor': - this.prerelease.length = 0 - this.patch = 0 - this.minor++ - this.inc('pre', identifier) - break - case 'prepatch': - // If this is already a prerelease, it will bump to the next version - // drop any prereleases that might already exist, since they are not - // relevant at this point. - this.prerelease.length = 0 - this.inc('patch', identifier) - this.inc('pre', identifier) - break - // If the input is a non-prerelease version, this acts the same as - // prepatch. - case 'prerelease': - if (this.prerelease.length === 0) { - this.inc('patch', identifier) - } - this.inc('pre', identifier) - break - - case 'major': - // If this is a pre-major version, bump up to the same major version. - // Otherwise increment major. - // 1.0.0-5 bumps to 1.0.0 - // 1.1.0 bumps to 2.0.0 - if (this.minor !== 0 || - this.patch !== 0 || - this.prerelease.length === 0) { - this.major++ - } - this.minor = 0 - this.patch = 0 - this.prerelease = [] - break - case 'minor': - // If this is a pre-minor version, bump up to the same minor version. - // Otherwise increment minor. - // 1.2.0-5 bumps to 1.2.0 - // 1.2.1 bumps to 1.3.0 - if (this.patch !== 0 || this.prerelease.length === 0) { - this.minor++ - } - this.patch = 0 - this.prerelease = [] - break - case 'patch': - // If this is not a pre-release version, it will increment the patch. - // If it is a pre-release it will bump up to the same patch version. - // 1.2.0-5 patches to 1.2.0 - // 1.2.0 patches to 1.2.1 - if (this.prerelease.length === 0) { - this.patch++ - } - this.prerelease = [] - break - // This probably shouldn't be used publicly. - // 1.0.0 "pre" would become 1.0.0-0 which is the wrong direction. - case 'pre': - if (this.prerelease.length === 0) { - this.prerelease = [0] - } else { - var i = this.prerelease.length - while (--i >= 0) { - if (typeof this.prerelease[i] === 'number') { - this.prerelease[i]++ - i = -2 - } - } - if (i === -1) { - // didn't increment anything - this.prerelease.push(0) - } - } - if (identifier) { - // 1.2.0-beta.1 bumps to 1.2.0-beta.2, - // 1.2.0-beta.fooblz or 1.2.0-beta bumps to 1.2.0-beta.0 - if (this.prerelease[0] === identifier) { - if (isNaN(this.prerelease[1])) { - this.prerelease = [identifier, 0] - } - } else { - this.prerelease = [identifier, 0] - } - } - break - - default: - throw new Error('invalid increment argument: ' + release) - } - this.format() - this.raw = this.version - return this -} - -exports.inc = inc -function inc (version, release, loose, identifier) { - if (typeof (loose) === 'string') { - identifier = loose - loose = undefined - } - - try { - return new SemVer(version, loose).inc(release, identifier).version - } catch (er) { - return null - } -} - -exports.diff = diff -function diff (version1, version2) { - if (eq(version1, version2)) { - return null - } else { - var v1 = parse(version1) - var v2 = parse(version2) - var prefix = '' - if (v1.prerelease.length || v2.prerelease.length) { - prefix = 'pre' - var defaultResult = 'prerelease' - } - for (var key in v1) { - if (key === 'major' || key === 'minor' || key === 'patch') { - if (v1[key] !== v2[key]) { - return prefix + key - } - } - } - return defaultResult // may be undefined - } -} - -exports.compareIdentifiers = compareIdentifiers - -var numeric = /^[0-9]+$/ -function compareIdentifiers (a, b) { - var anum = numeric.test(a) - var bnum = numeric.test(b) - - if (anum && bnum) { - a = +a - b = +b - } - - return a === b ? 0 - : (anum && !bnum) ? -1 - : (bnum && !anum) ? 1 - : a < b ? -1 - : 1 -} - -exports.rcompareIdentifiers = rcompareIdentifiers -function rcompareIdentifiers (a, b) { - return compareIdentifiers(b, a) -} - -exports.major = major -function major (a, loose) { - return new SemVer(a, loose).major -} - -exports.minor = minor -function minor (a, loose) { - return new SemVer(a, loose).minor -} - -exports.patch = patch -function patch (a, loose) { - return new SemVer(a, loose).patch -} - -exports.compare = compare -function compare (a, b, loose) { - return new SemVer(a, loose).compare(new SemVer(b, loose)) -} - -exports.compareLoose = compareLoose -function compareLoose (a, b) { - return compare(a, b, true) -} - -exports.rcompare = rcompare -function rcompare (a, b, loose) { - return compare(b, a, loose) -} - -exports.sort = sort -function sort (list, loose) { - return list.sort(function (a, b) { - return exports.compare(a, b, loose) - }) -} - -exports.rsort = rsort -function rsort (list, loose) { - return list.sort(function (a, b) { - return exports.rcompare(a, b, loose) - }) -} - -exports.gt = gt -function gt (a, b, loose) { - return compare(a, b, loose) > 0 -} - -exports.lt = lt -function lt (a, b, loose) { - return compare(a, b, loose) < 0 -} - -exports.eq = eq -function eq (a, b, loose) { - return compare(a, b, loose) === 0 -} - -exports.neq = neq -function neq (a, b, loose) { - return compare(a, b, loose) !== 0 -} - -exports.gte = gte -function gte (a, b, loose) { - return compare(a, b, loose) >= 0 -} - -exports.lte = lte -function lte (a, b, loose) { - return compare(a, b, loose) <= 0 -} - -exports.cmp = cmp -function cmp (a, op, b, loose) { - switch (op) { - case '===': - if (typeof a === 'object') - a = a.version - if (typeof b === 'object') - b = b.version - return a === b - - case '!==': - if (typeof a === 'object') - a = a.version - if (typeof b === 'object') - b = b.version - return a !== b - - case '': - case '=': - case '==': - return eq(a, b, loose) - - case '!=': - return neq(a, b, loose) - - case '>': - return gt(a, b, loose) - - case '>=': - return gte(a, b, loose) - - case '<': - return lt(a, b, loose) - - case '<=': - return lte(a, b, loose) - - default: - throw new TypeError('Invalid operator: ' + op) - } -} - -exports.Comparator = Comparator -function Comparator (comp, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - if (comp instanceof Comparator) { - if (comp.loose === !!options.loose) { - return comp - } else { - comp = comp.value - } - } - - if (!(this instanceof Comparator)) { - return new Comparator(comp, options) - } - - debug('comparator', comp, options) - this.options = options - this.loose = !!options.loose - this.parse(comp) - - if (this.semver === ANY) { - this.value = '' - } else { - this.value = this.operator + this.semver.version - } - - debug('comp', this) -} - -var ANY = {} -Comparator.prototype.parse = function (comp) { - var r = this.options.loose ? re[COMPARATORLOOSE] : re[COMPARATOR] - var m = comp.match(r) - - if (!m) { - throw new TypeError('Invalid comparator: ' + comp) - } - - this.operator = m[1] - if (this.operator === '=') { - this.operator = '' - } - - // if it literally is just '>' or '' then allow anything. - if (!m[2]) { - this.semver = ANY - } else { - this.semver = new SemVer(m[2], this.options.loose) - } -} - -Comparator.prototype.toString = function () { - return this.value -} - -Comparator.prototype.test = function (version) { - debug('Comparator.test', version, this.options.loose) - - if (this.semver === ANY) { - return true - } - - if (typeof version === 'string') { - version = new SemVer(version, this.options) - } - - return cmp(version, this.operator, this.semver, this.options) -} - -Comparator.prototype.intersects = function (comp, options) { - if (!(comp instanceof Comparator)) { - throw new TypeError('a Comparator is required') - } - - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - var rangeTmp - - if (this.operator === '') { - rangeTmp = new Range(comp.value, options) - return satisfies(this.value, rangeTmp, options) - } else if (comp.operator === '') { - rangeTmp = new Range(this.value, options) - return satisfies(comp.semver, rangeTmp, options) - } - - var sameDirectionIncreasing = - (this.operator === '>=' || this.operator === '>') && - (comp.operator === '>=' || comp.operator === '>') - var sameDirectionDecreasing = - (this.operator === '<=' || this.operator === '<') && - (comp.operator === '<=' || comp.operator === '<') - var sameSemVer = this.semver.version === comp.semver.version - var differentDirectionsInclusive = - (this.operator === '>=' || this.operator === '<=') && - (comp.operator === '>=' || comp.operator === '<=') - var oppositeDirectionsLessThan = - cmp(this.semver, '<', comp.semver, options) && - ((this.operator === '>=' || this.operator === '>') && - (comp.operator === '<=' || comp.operator === '<')) - var oppositeDirectionsGreaterThan = - cmp(this.semver, '>', comp.semver, options) && - ((this.operator === '<=' || this.operator === '<') && - (comp.operator === '>=' || comp.operator === '>')) - - return sameDirectionIncreasing || sameDirectionDecreasing || - (sameSemVer && differentDirectionsInclusive) || - oppositeDirectionsLessThan || oppositeDirectionsGreaterThan -} - -exports.Range = Range -function Range (range, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - if (range instanceof Range) { - if (range.loose === !!options.loose && - range.includePrerelease === !!options.includePrerelease) { - return range - } else { - return new Range(range.raw, options) - } - } - - if (range instanceof Comparator) { - return new Range(range.value, options) - } - - if (!(this instanceof Range)) { - return new Range(range, options) - } - - this.options = options - this.loose = !!options.loose - this.includePrerelease = !!options.includePrerelease - - // First, split based on boolean or || - this.raw = range - this.set = range.split(/\s*\|\|\s*/).map(function (range) { - return this.parseRange(range.trim()) - }, this).filter(function (c) { - // throw out any that are not relevant for whatever reason - return c.length - }) - - if (!this.set.length) { - throw new TypeError('Invalid SemVer Range: ' + range) - } - - this.format() -} - -Range.prototype.format = function () { - this.range = this.set.map(function (comps) { - return comps.join(' ').trim() - }).join('||').trim() - return this.range -} - -Range.prototype.toString = function () { - return this.range -} - -Range.prototype.parseRange = function (range) { - var loose = this.options.loose - range = range.trim() - // `1.2.3 - 1.2.4` => `>=1.2.3 <=1.2.4` - var hr = loose ? re[HYPHENRANGELOOSE] : re[HYPHENRANGE] - range = range.replace(hr, hyphenReplace) - debug('hyphen replace', range) - // `> 1.2.3 < 1.2.5` => `>1.2.3 <1.2.5` - range = range.replace(re[COMPARATORTRIM], comparatorTrimReplace) - debug('comparator trim', range, re[COMPARATORTRIM]) - - // `~ 1.2.3` => `~1.2.3` - range = range.replace(re[TILDETRIM], tildeTrimReplace) - - // `^ 1.2.3` => `^1.2.3` - range = range.replace(re[CARETTRIM], caretTrimReplace) - - // normalize spaces - range = range.split(/\s+/).join(' ') - - // At this point, the range is completely trimmed and - // ready to be split into comparators. - - var compRe = loose ? re[COMPARATORLOOSE] : re[COMPARATOR] - var set = range.split(' ').map(function (comp) { - return parseComparator(comp, this.options) - }, this).join(' ').split(/\s+/) - if (this.options.loose) { - // in loose mode, throw out any that are not valid comparators - set = set.filter(function (comp) { - return !!comp.match(compRe) - }) - } - set = set.map(function (comp) { - return new Comparator(comp, this.options) - }, this) - - return set -} - -Range.prototype.intersects = function (range, options) { - if (!(range instanceof Range)) { - throw new TypeError('a Range is required') - } - - return this.set.some(function (thisComparators) { - return thisComparators.every(function (thisComparator) { - return range.set.some(function (rangeComparators) { - return rangeComparators.every(function (rangeComparator) { - return thisComparator.intersects(rangeComparator, options) - }) - }) - }) - }) -} - -// Mostly just for testing and legacy API reasons -exports.toComparators = toComparators -function toComparators (range, options) { - return new Range(range, options).set.map(function (comp) { - return comp.map(function (c) { - return c.value - }).join(' ').trim().split(' ') - }) -} - -// comprised of xranges, tildes, stars, and gtlt's at this point. -// already replaced the hyphen ranges -// turn into a set of JUST comparators. -function parseComparator (comp, options) { - debug('comp', comp, options) - comp = replaceCarets(comp, options) - debug('caret', comp) - comp = replaceTildes(comp, options) - debug('tildes', comp) - comp = replaceXRanges(comp, options) - debug('xrange', comp) - comp = replaceStars(comp, options) - debug('stars', comp) - return comp -} - -function isX (id) { - return !id || id.toLowerCase() === 'x' || id === '*' -} - -// ~, ~> --> * (any, kinda silly) -// ~2, ~2.x, ~2.x.x, ~>2, ~>2.x ~>2.x.x --> >=2.0.0 <3.0.0 -// ~2.0, ~2.0.x, ~>2.0, ~>2.0.x --> >=2.0.0 <2.1.0 -// ~1.2, ~1.2.x, ~>1.2, ~>1.2.x --> >=1.2.0 <1.3.0 -// ~1.2.3, ~>1.2.3 --> >=1.2.3 <1.3.0 -// ~1.2.0, ~>1.2.0 --> >=1.2.0 <1.3.0 -function replaceTildes (comp, options) { - return comp.trim().split(/\s+/).map(function (comp) { - return replaceTilde(comp, options) - }).join(' ') -} - -function replaceTilde (comp, options) { - var r = options.loose ? re[TILDELOOSE] : re[TILDE] - return comp.replace(r, function (_, M, m, p, pr) { - debug('tilde', comp, _, M, m, p, pr) - var ret - - if (isX(M)) { - ret = '' - } else if (isX(m)) { - ret = '>=' + M + '.0.0 <' + (+M + 1) + '.0.0' - } else if (isX(p)) { - // ~1.2 == >=1.2.0 <1.3.0 - ret = '>=' + M + '.' + m + '.0 <' + M + '.' + (+m + 1) + '.0' - } else if (pr) { - debug('replaceTilde pr', pr) - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + M + '.' + (+m + 1) + '.0' - } else { - // ~1.2.3 == >=1.2.3 <1.3.0 - ret = '>=' + M + '.' + m + '.' + p + - ' <' + M + '.' + (+m + 1) + '.0' - } - - debug('tilde return', ret) - return ret - }) -} - -// ^ --> * (any, kinda silly) -// ^2, ^2.x, ^2.x.x --> >=2.0.0 <3.0.0 -// ^2.0, ^2.0.x --> >=2.0.0 <3.0.0 -// ^1.2, ^1.2.x --> >=1.2.0 <2.0.0 -// ^1.2.3 --> >=1.2.3 <2.0.0 -// ^1.2.0 --> >=1.2.0 <2.0.0 -function replaceCarets (comp, options) { - return comp.trim().split(/\s+/).map(function (comp) { - return replaceCaret(comp, options) - }).join(' ') -} - -function replaceCaret (comp, options) { - debug('caret', comp, options) - var r = options.loose ? re[CARETLOOSE] : re[CARET] - return comp.replace(r, function (_, M, m, p, pr) { - debug('caret', comp, _, M, m, p, pr) - var ret - - if (isX(M)) { - ret = '' - } else if (isX(m)) { - ret = '>=' + M + '.0.0 <' + (+M + 1) + '.0.0' - } else if (isX(p)) { - if (M === '0') { - ret = '>=' + M + '.' + m + '.0 <' + M + '.' + (+m + 1) + '.0' - } else { - ret = '>=' + M + '.' + m + '.0 <' + (+M + 1) + '.0.0' - } - } else if (pr) { - debug('replaceCaret pr', pr) - if (M === '0') { - if (m === '0') { - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + M + '.' + m + '.' + (+p + 1) - } else { - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + M + '.' + (+m + 1) + '.0' - } - } else { - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + (+M + 1) + '.0.0' - } - } else { - debug('no pr') - if (M === '0') { - if (m === '0') { - ret = '>=' + M + '.' + m + '.' + p + - ' <' + M + '.' + m + '.' + (+p + 1) - } else { - ret = '>=' + M + '.' + m + '.' + p + - ' <' + M + '.' + (+m + 1) + '.0' - } - } else { - ret = '>=' + M + '.' + m + '.' + p + - ' <' + (+M + 1) + '.0.0' - } - } - - debug('caret return', ret) - return ret - }) -} - -function replaceXRanges (comp, options) { - debug('replaceXRanges', comp, options) - return comp.split(/\s+/).map(function (comp) { - return replaceXRange(comp, options) - }).join(' ') -} - -function replaceXRange (comp, options) { - comp = comp.trim() - var r = options.loose ? re[XRANGELOOSE] : re[XRANGE] - return comp.replace(r, function (ret, gtlt, M, m, p, pr) { - debug('xRange', comp, ret, gtlt, M, m, p, pr) - var xM = isX(M) - var xm = xM || isX(m) - var xp = xm || isX(p) - var anyX = xp - - if (gtlt === '=' && anyX) { - gtlt = '' - } - - if (xM) { - if (gtlt === '>' || gtlt === '<') { - // nothing is allowed - ret = '<0.0.0' - } else { - // nothing is forbidden - ret = '*' - } - } else if (gtlt && anyX) { - // we know patch is an x, because we have any x at all. - // replace X with 0 - if (xm) { - m = 0 - } - p = 0 - - if (gtlt === '>') { - // >1 => >=2.0.0 - // >1.2 => >=1.3.0 - // >1.2.3 => >= 1.2.4 - gtlt = '>=' - if (xm) { - M = +M + 1 - m = 0 - p = 0 - } else { - m = +m + 1 - p = 0 - } - } else if (gtlt === '<=') { - // <=0.7.x is actually <0.8.0, since any 0.7.x should - // pass. Similarly, <=7.x is actually <8.0.0, etc. - gtlt = '<' - if (xm) { - M = +M + 1 - } else { - m = +m + 1 - } - } - - ret = gtlt + M + '.' + m + '.' + p - } else if (xm) { - ret = '>=' + M + '.0.0 <' + (+M + 1) + '.0.0' - } else if (xp) { - ret = '>=' + M + '.' + m + '.0 <' + M + '.' + (+m + 1) + '.0' - } - - debug('xRange return', ret) - - return ret - }) -} - -// Because * is AND-ed with everything else in the comparator, -// and '' means "any version", just remove the *s entirely. -function replaceStars (comp, options) { - debug('replaceStars', comp, options) - // Looseness is ignored here. star is always as loose as it gets! - return comp.trim().replace(re[STAR], '') -} - -// This function is passed to string.replace(re[HYPHENRANGE]) -// M, m, patch, prerelease, build -// 1.2 - 3.4.5 => >=1.2.0 <=3.4.5 -// 1.2.3 - 3.4 => >=1.2.0 <3.5.0 Any 3.4.x will do -// 1.2 - 3.4 => >=1.2.0 <3.5.0 -function hyphenReplace ($0, - from, fM, fm, fp, fpr, fb, - to, tM, tm, tp, tpr, tb) { - if (isX(fM)) { - from = '' - } else if (isX(fm)) { - from = '>=' + fM + '.0.0' - } else if (isX(fp)) { - from = '>=' + fM + '.' + fm + '.0' - } else { - from = '>=' + from - } - - if (isX(tM)) { - to = '' - } else if (isX(tm)) { - to = '<' + (+tM + 1) + '.0.0' - } else if (isX(tp)) { - to = '<' + tM + '.' + (+tm + 1) + '.0' - } else if (tpr) { - to = '<=' + tM + '.' + tm + '.' + tp + '-' + tpr - } else { - to = '<=' + to - } - - return (from + ' ' + to).trim() -} - -// if ANY of the sets match ALL of its comparators, then pass -Range.prototype.test = function (version) { - if (!version) { - return false - } - - if (typeof version === 'string') { - version = new SemVer(version, this.options) - } - - for (var i = 0; i < this.set.length; i++) { - if (testSet(this.set[i], version, this.options)) { - return true - } - } - return false -} - -function testSet (set, version, options) { - for (var i = 0; i < set.length; i++) { - if (!set[i].test(version)) { - return false - } - } - - if (version.prerelease.length && !options.includePrerelease) { - // Find the set of versions that are allowed to have prereleases - // For example, ^1.2.3-pr.1 desugars to >=1.2.3-pr.1 <2.0.0 - // That should allow `1.2.3-pr.2` to pass. - // However, `1.2.4-alpha.notready` should NOT be allowed, - // even though it's within the range set by the comparators. - for (i = 0; i < set.length; i++) { - debug(set[i].semver) - if (set[i].semver === ANY) { - continue - } - - if (set[i].semver.prerelease.length > 0) { - var allowed = set[i].semver - if (allowed.major === version.major && - allowed.minor === version.minor && - allowed.patch === version.patch) { - return true - } - } - } - - // Version has a -pre, but it's not one of the ones we like. - return false - } - - return true -} - -exports.satisfies = satisfies -function satisfies (version, range, options) { - try { - range = new Range(range, options) - } catch (er) { - return false - } - return range.test(version) -} - -exports.maxSatisfying = maxSatisfying -function maxSatisfying (versions, range, options) { - var max = null - var maxSV = null - try { - var rangeObj = new Range(range, options) - } catch (er) { - return null - } - versions.forEach(function (v) { - if (rangeObj.test(v)) { - // satisfies(v, range, options) - if (!max || maxSV.compare(v) === -1) { - // compare(max, v, true) - max = v - maxSV = new SemVer(max, options) - } - } - }) - return max -} - -exports.minSatisfying = minSatisfying -function minSatisfying (versions, range, options) { - var min = null - var minSV = null - try { - var rangeObj = new Range(range, options) - } catch (er) { - return null - } - versions.forEach(function (v) { - if (rangeObj.test(v)) { - // satisfies(v, range, options) - if (!min || minSV.compare(v) === 1) { - // compare(min, v, true) - min = v - minSV = new SemVer(min, options) - } - } - }) - return min -} - -exports.minVersion = minVersion -function minVersion (range, loose) { - range = new Range(range, loose) - - var minver = new SemVer('0.0.0') - if (range.test(minver)) { - return minver - } - - minver = new SemVer('0.0.0-0') - if (range.test(minver)) { - return minver - } - - minver = null - for (var i = 0; i < range.set.length; ++i) { - var comparators = range.set[i] - - comparators.forEach(function (comparator) { - // Clone to avoid manipulating the comparator's semver object. - var compver = new SemVer(comparator.semver.version) - switch (comparator.operator) { - case '>': - if (compver.prerelease.length === 0) { - compver.patch++ - } else { - compver.prerelease.push(0) - } - compver.raw = compver.format() - /* fallthrough */ - case '': - case '>=': - if (!minver || gt(minver, compver)) { - minver = compver - } - break - case '<': - case '<=': - /* Ignore maximum versions */ - break - /* istanbul ignore next */ - default: - throw new Error('Unexpected operation: ' + comparator.operator) - } - }) - } - - if (minver && range.test(minver)) { - return minver - } - - return null -} - -exports.validRange = validRange -function validRange (range, options) { - try { - // Return '*' instead of '' so that truthiness works. - // This will throw if it's invalid anyway - return new Range(range, options).range || '*' - } catch (er) { - return null - } -} - -// Determine if version is less than all the versions possible in the range -exports.ltr = ltr -function ltr (version, range, options) { - return outside(version, range, '<', options) -} - -// Determine if version is greater than all the versions possible in the range. -exports.gtr = gtr -function gtr (version, range, options) { - return outside(version, range, '>', options) -} - -exports.outside = outside -function outside (version, range, hilo, options) { - version = new SemVer(version, options) - range = new Range(range, options) - - var gtfn, ltefn, ltfn, comp, ecomp - switch (hilo) { - case '>': - gtfn = gt - ltefn = lte - ltfn = lt - comp = '>' - ecomp = '>=' - break - case '<': - gtfn = lt - ltefn = gte - ltfn = gt - comp = '<' - ecomp = '<=' - break - default: - throw new TypeError('Must provide a hilo val of "<" or ">"') - } - - // If it satisifes the range it is not outside - if (satisfies(version, range, options)) { - return false - } - - // From now on, variable terms are as if we're in "gtr" mode. - // but note that everything is flipped for the "ltr" function. - - for (var i = 0; i < range.set.length; ++i) { - var comparators = range.set[i] - - var high = null - var low = null - - comparators.forEach(function (comparator) { - if (comparator.semver === ANY) { - comparator = new Comparator('>=0.0.0') - } - high = high || comparator - low = low || comparator - if (gtfn(comparator.semver, high.semver, options)) { - high = comparator - } else if (ltfn(comparator.semver, low.semver, options)) { - low = comparator - } - }) - - // If the edge version comparator has a operator then our version - // isn't outside it - if (high.operator === comp || high.operator === ecomp) { - return false - } - - // If the lowest version comparator has an operator and our version - // is less than it then it isn't higher than the range - if ((!low.operator || low.operator === comp) && - ltefn(version, low.semver)) { - return false - } else if (low.operator === ecomp && ltfn(version, low.semver)) { - return false - } - } - return true -} - -exports.prerelease = prerelease -function prerelease (version, options) { - var parsed = parse(version, options) - return (parsed && parsed.prerelease.length) ? parsed.prerelease : null -} - -exports.intersects = intersects -function intersects (r1, r2, options) { - r1 = new Range(r1, options) - r2 = new Range(r2, options) - return r1.intersects(r2) -} - -exports.coerce = coerce -function coerce (version) { - if (version instanceof SemVer) { - return version - } - - if (typeof version !== 'string') { - return null - } - - var match = version.match(re[COERCE]) - - if (match == null) { - return null - } - - return parse(match[1] + - '.' + (match[2] || '0') + - '.' + (match[3] || '0')) -} - - -/***/ }), - -/***/ "../../node_modules/normalize-path/index.js": -/***/ (function(module, exports) { - -/*! - * normalize-path - * - * Copyright (c) 2014-2018, Jon Schlinkert. - * Released under the MIT License. - */ - -module.exports = function(path, stripTrailing) { - if (typeof path !== 'string') { - throw new TypeError('expected path to be a string'); - } - - if (path === '\\' || path === '/') return '/'; - - var len = path.length; - if (len <= 1) return path; - - // ensure that win32 namespaces has two leading slashes, so that the path is - // handled properly by the win32 version of path.parse() after being normalized - // https://msdn.microsoft.com/library/windows/desktop/aa365247(v=vs.85).aspx#namespaces - var prefix = ''; - if (len > 4 && path[3] === '\\') { - var ch = path[2]; - if ((ch === '?' || ch === '.') && path.slice(0, 2) === '\\\\') { - path = path.slice(2); - prefix = '//'; - } - } - - var segs = path.split(/[/\\]+/); - if (stripTrailing !== false && segs[segs.length - 1] === '') { - segs.pop(); - } - return prefix + segs.join('/'); -}; - - -/***/ }), - -/***/ "../../node_modules/npm-run-path/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); -const pathKey = __webpack_require__("../../node_modules/npm-run-path/node_modules/path-key/index.js"); - -const npmRunPath = options => { - options = { - cwd: process.cwd(), - path: process.env[pathKey()], - execPath: process.execPath, - ...options - }; - - let previous; - let cwdPath = path.resolve(options.cwd); - const result = []; - - while (previous !== cwdPath) { - result.push(path.join(cwdPath, 'node_modules/.bin')); - previous = cwdPath; - cwdPath = path.resolve(cwdPath, '..'); - } - - // Ensure the running `node` binary is used - const execPathDir = path.resolve(options.cwd, options.execPath, '..'); - result.push(execPathDir); - - return result.concat(options.path).join(path.delimiter); -}; - -module.exports = npmRunPath; -// TODO: Remove this for the next major release -module.exports.default = npmRunPath; - -module.exports.env = options => { - options = { - env: process.env, - ...options - }; - - const env = {...options.env}; - const path = pathKey({env}); - - options.path = env[path]; - env[path] = module.exports(options); - - return env; -}; - - -/***/ }), - -/***/ "../../node_modules/npm-run-path/node_modules/path-key/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const pathKey = (options = {}) => { - const environment = options.env || process.env; - const platform = options.platform || process.platform; - - if (platform !== 'win32') { - return 'PATH'; - } - - return Object.keys(environment).find(key => key.toUpperCase() === 'PATH') || 'Path'; -}; - -module.exports = pathKey; -// TODO: Remove this for the next major release -module.exports.default = pathKey; - - -/***/ }), - -/***/ "../../node_modules/once/once.js": -/***/ (function(module, exports, __webpack_require__) { - -var wrappy = __webpack_require__("../../node_modules/wrappy/wrappy.js") -module.exports = wrappy(once) -module.exports.strict = wrappy(onceStrict) - -once.proto = once(function () { - Object.defineProperty(Function.prototype, 'once', { - value: function () { - return once(this) - }, - configurable: true - }) - - Object.defineProperty(Function.prototype, 'onceStrict', { - value: function () { - return onceStrict(this) - }, - configurable: true - }) -}) - -function once (fn) { - var f = function () { - if (f.called) return f.value - f.called = true - return f.value = fn.apply(this, arguments) - } - f.called = false - return f -} - -function onceStrict (fn) { - var f = function () { - if (f.called) - throw new Error(f.onceError) - f.called = true - return f.value = fn.apply(this, arguments) - } - var name = fn.name || 'Function wrapped with `once`' - f.onceError = name + " shouldn't be called more than once" - f.called = false - return f -} - - -/***/ }), - -/***/ "../../node_modules/onetime/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const mimicFn = __webpack_require__("../../node_modules/mimic-fn/index.js"); - -const calledFunctions = new WeakMap(); - -const onetime = (function_, options = {}) => { - if (typeof function_ !== 'function') { - throw new TypeError('Expected a function'); - } - - let returnValue; - let callCount = 0; - const functionName = function_.displayName || function_.name || ''; - - const onetime = function (...arguments_) { - calledFunctions.set(onetime, ++callCount); - - if (callCount === 1) { - returnValue = function_.apply(this, arguments_); - function_ = null; - } else if (options.throw === true) { - throw new Error(`Function \`${functionName}\` can only be called once`); - } - - return returnValue; - }; - - mimicFn(onetime, function_); - calledFunctions.set(onetime, callCount); - - return onetime; -}; - -module.exports = onetime; -// TODO: Remove this for the next major release -module.exports.default = onetime; - -module.exports.callCount = function_ => { - if (!calledFunctions.has(function_)) { - throw new Error(`The given function \`${function_.name}\` is not wrapped by the \`onetime\` package`); - } - - return calledFunctions.get(function_); -}; - - -/***/ }), - -/***/ "../../node_modules/ora/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const readline = __webpack_require__("readline"); -const chalk = __webpack_require__("../../node_modules/ora/node_modules/chalk/source/index.js"); -const cliCursor = __webpack_require__("../../node_modules/cli-cursor/index.js"); -const cliSpinners = __webpack_require__("../../node_modules/cli-spinners/index.js"); -const logSymbols = __webpack_require__("../../node_modules/ora/node_modules/log-symbols/index.js"); -const stripAnsi = __webpack_require__("../../node_modules/strip-ansi/index.js"); -const wcwidth = __webpack_require__("../../node_modules/wcwidth/index.js"); -const isInteractive = __webpack_require__("../../node_modules/is-interactive/index.js"); -const MuteStream = __webpack_require__("../../node_modules/mute-stream/mute.js"); - -const TEXT = Symbol('text'); -const PREFIX_TEXT = Symbol('prefixText'); - -const ASCII_ETX_CODE = 0x03; // Ctrl+C emits this code - -class StdinDiscarder { - constructor() { - this.requests = 0; - - this.mutedStream = new MuteStream(); - this.mutedStream.pipe(process.stdout); - this.mutedStream.mute(); - - const self = this; - this.ourEmit = function (event, data, ...args) { - const {stdin} = process; - if (self.requests > 0 || stdin.emit === self.ourEmit) { - if (event === 'keypress') { // Fixes readline behavior - return; - } - - if (event === 'data' && data.includes(ASCII_ETX_CODE)) { - process.emit('SIGINT'); - } - - Reflect.apply(self.oldEmit, this, [event, data, ...args]); - } else { - Reflect.apply(process.stdin.emit, this, [event, data, ...args]); - } - }; - } - - start() { - this.requests++; - - if (this.requests === 1) { - this.realStart(); - } - } - - stop() { - if (this.requests <= 0) { - throw new Error('`stop` called more times than `start`'); - } - - this.requests--; - - if (this.requests === 0) { - this.realStop(); - } - } - - realStart() { - // No known way to make it work reliably on Windows - if (process.platform === 'win32') { - return; - } - - this.rl = readline.createInterface({ - input: process.stdin, - output: this.mutedStream - }); - - this.rl.on('SIGINT', () => { - if (process.listenerCount('SIGINT') === 0) { - process.emit('SIGINT'); - } else { - this.rl.close(); - process.kill(process.pid, 'SIGINT'); - } - }); - } - - realStop() { - if (process.platform === 'win32') { - return; - } - - this.rl.close(); - this.rl = undefined; - } -} - -let stdinDiscarder; - -class Ora { - constructor(options) { - if (!stdinDiscarder) { - stdinDiscarder = new StdinDiscarder(); - } - - if (typeof options === 'string') { - options = { - text: options - }; - } - - this.options = { - text: '', - color: 'cyan', - stream: process.stderr, - discardStdin: true, - ...options - }; - - this.spinner = this.options.spinner; - - this.color = this.options.color; - this.hideCursor = this.options.hideCursor !== false; - this.interval = this.options.interval || this.spinner.interval || 100; - this.stream = this.options.stream; - this.id = undefined; - this.isEnabled = typeof this.options.isEnabled === 'boolean' ? this.options.isEnabled : isInteractive({stream: this.stream}); - - // Set *after* `this.stream` - this.text = this.options.text; - this.prefixText = this.options.prefixText; - this.linesToClear = 0; - this.indent = this.options.indent; - this.discardStdin = this.options.discardStdin; - this.isDiscardingStdin = false; - } - - get indent() { - return this._indent; - } - - set indent(indent = 0) { - if (!(indent >= 0 && Number.isInteger(indent))) { - throw new Error('The `indent` option must be an integer from 0 and up'); - } - - this._indent = indent; - } - - _updateInterval(interval) { - if (interval !== undefined) { - this.interval = interval; - } - } - - get spinner() { - return this._spinner; - } - - set spinner(spinner) { - this.frameIndex = 0; - - if (typeof spinner === 'object') { - if (spinner.frames === undefined) { - throw new Error('The given spinner must have a `frames` property'); - } - - this._spinner = spinner; - } else if (process.platform === 'win32') { - this._spinner = cliSpinners.line; - } else if (spinner === undefined) { - // Set default spinner - this._spinner = cliSpinners.dots; - } else if (cliSpinners[spinner]) { - this._spinner = cliSpinners[spinner]; - } else { - throw new Error(`There is no built-in spinner named '${spinner}'. See https://github.com/sindresorhus/cli-spinners/blob/master/spinners.json for a full list.`); - } - - this._updateInterval(this._spinner.interval); - } - - get text() { - return this[TEXT]; - } - - get prefixText() { - return this[PREFIX_TEXT]; - } - - get isSpinning() { - return this.id !== undefined; - } - - updateLineCount() { - const columns = this.stream.columns || 80; - const fullPrefixText = (typeof this[PREFIX_TEXT] === 'string') ? this[PREFIX_TEXT] + '-' : ''; - this.lineCount = stripAnsi(fullPrefixText + '--' + this[TEXT]).split('\n').reduce((count, line) => { - return count + Math.max(1, Math.ceil(wcwidth(line) / columns)); - }, 0); - } - - set text(value) { - this[TEXT] = value; - this.updateLineCount(); - } - - set prefixText(value) { - this[PREFIX_TEXT] = value; - this.updateLineCount(); - } - - frame() { - const {frames} = this.spinner; - let frame = frames[this.frameIndex]; - - if (this.color) { - frame = chalk[this.color](frame); - } - - this.frameIndex = ++this.frameIndex % frames.length; - const fullPrefixText = (typeof this.prefixText === 'string' && this.prefixText !== '') ? this.prefixText + ' ' : ''; - const fullText = typeof this.text === 'string' ? ' ' + this.text : ''; - - return fullPrefixText + frame + fullText; - } - - clear() { - if (!this.isEnabled || !this.stream.isTTY) { - return this; - } - - for (let i = 0; i < this.linesToClear; i++) { - if (i > 0) { - this.stream.moveCursor(0, -1); - } - - this.stream.clearLine(); - this.stream.cursorTo(this.indent); - } - - this.linesToClear = 0; - - return this; - } - - render() { - this.clear(); - this.stream.write(this.frame()); - this.linesToClear = this.lineCount; - - return this; - } - - start(text) { - if (text) { - this.text = text; - } - - if (!this.isEnabled) { - if (this.text) { - this.stream.write(`- ${this.text}\n`); - } - - return this; - } - - if (this.isSpinning) { - return this; - } - - if (this.hideCursor) { - cliCursor.hide(this.stream); - } - - if (this.discardStdin && process.stdin.isTTY) { - this.isDiscardingStdin = true; - stdinDiscarder.start(); - } - - this.render(); - this.id = setInterval(this.render.bind(this), this.interval); - - return this; - } - - stop() { - if (!this.isEnabled) { - return this; - } - - clearInterval(this.id); - this.id = undefined; - this.frameIndex = 0; - this.clear(); - if (this.hideCursor) { - cliCursor.show(this.stream); - } - - if (this.discardStdin && process.stdin.isTTY && this.isDiscardingStdin) { - stdinDiscarder.stop(); - this.isDiscardingStdin = false; - } - - return this; - } - - succeed(text) { - return this.stopAndPersist({symbol: logSymbols.success, text}); - } - - fail(text) { - return this.stopAndPersist({symbol: logSymbols.error, text}); - } - - warn(text) { - return this.stopAndPersist({symbol: logSymbols.warning, text}); - } - - info(text) { - return this.stopAndPersist({symbol: logSymbols.info, text}); - } - - stopAndPersist(options = {}) { - const prefixText = options.prefixText || this.prefixText; - const fullPrefixText = (typeof prefixText === 'string' && prefixText !== '') ? prefixText + ' ' : ''; - const text = options.text || this.text; - const fullText = (typeof text === 'string') ? ' ' + text : ''; - - this.stop(); - this.stream.write(`${fullPrefixText}${options.symbol || ' '}${fullText}\n`); - - return this; - } -} - -const oraFactory = function (options) { - return new Ora(options); -}; - -module.exports = oraFactory; - -module.exports.promise = (action, options) => { - // eslint-disable-next-line promise/prefer-await-to-then - if (typeof action.then !== 'function') { - throw new TypeError('Parameter `action` must be a Promise'); - } - - const spinner = new Ora(options); - spinner.start(); - - (async () => { - try { - await action; - spinner.succeed(); - } catch (_) { - spinner.fail(); - } - })(); - - return spinner; -}; - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/chalk/source/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const ansiStyles = __webpack_require__("../../node_modules/ansi-styles/index.js"); -const {stdout: stdoutColor, stderr: stderrColor} = __webpack_require__("../../node_modules/supports-color/index.js"); -const { - stringReplaceAll, - stringEncaseCRLFWithFirstIndex -} = __webpack_require__("../../node_modules/ora/node_modules/chalk/source/util.js"); - -// `supportsColor.level` → `ansiStyles.color[name]` mapping -const levelMapping = [ - 'ansi', - 'ansi', - 'ansi256', - 'ansi16m' -]; - -const styles = Object.create(null); - -const applyOptions = (object, options = {}) => { - if (options.level > 3 || options.level < 0) { - throw new Error('The `level` option should be an integer from 0 to 3'); - } - - // Detect level if not set manually - const colorLevel = stdoutColor ? stdoutColor.level : 0; - object.level = options.level === undefined ? colorLevel : options.level; -}; - -class ChalkClass { - constructor(options) { - return chalkFactory(options); - } -} - -const chalkFactory = options => { - const chalk = {}; - applyOptions(chalk, options); - - chalk.template = (...arguments_) => chalkTag(chalk.template, ...arguments_); - - Object.setPrototypeOf(chalk, Chalk.prototype); - Object.setPrototypeOf(chalk.template, chalk); - - chalk.template.constructor = () => { - throw new Error('`chalk.constructor()` is deprecated. Use `new chalk.Instance()` instead.'); - }; - - chalk.template.Instance = ChalkClass; - - return chalk.template; -}; - -function Chalk(options) { - return chalkFactory(options); -} - -for (const [styleName, style] of Object.entries(ansiStyles)) { - styles[styleName] = { - get() { - const builder = createBuilder(this, createStyler(style.open, style.close, this._styler), this._isEmpty); - Object.defineProperty(this, styleName, {value: builder}); - return builder; - } - }; -} - -styles.visible = { - get() { - const builder = createBuilder(this, this._styler, true); - Object.defineProperty(this, 'visible', {value: builder}); - return builder; - } -}; - -const usedModels = ['rgb', 'hex', 'keyword', 'hsl', 'hsv', 'hwb', 'ansi', 'ansi256']; - -for (const model of usedModels) { - styles[model] = { - get() { - const {level} = this; - return function (...arguments_) { - const styler = createStyler(ansiStyles.color[levelMapping[level]][model](...arguments_), ansiStyles.color.close, this._styler); - return createBuilder(this, styler, this._isEmpty); - }; - } - }; -} - -for (const model of usedModels) { - const bgModel = 'bg' + model[0].toUpperCase() + model.slice(1); - styles[bgModel] = { - get() { - const {level} = this; - return function (...arguments_) { - const styler = createStyler(ansiStyles.bgColor[levelMapping[level]][model](...arguments_), ansiStyles.bgColor.close, this._styler); - return createBuilder(this, styler, this._isEmpty); - }; - } - }; -} - -const proto = Object.defineProperties(() => {}, { - ...styles, - level: { - enumerable: true, - get() { - return this._generator.level; - }, - set(level) { - this._generator.level = level; - } - } -}); - -const createStyler = (open, close, parent) => { - let openAll; - let closeAll; - if (parent === undefined) { - openAll = open; - closeAll = close; - } else { - openAll = parent.openAll + open; - closeAll = close + parent.closeAll; - } - - return { - open, - close, - openAll, - closeAll, - parent - }; -}; - -const createBuilder = (self, _styler, _isEmpty) => { - const builder = (...arguments_) => { - // Single argument is hot path, implicit coercion is faster than anything - // eslint-disable-next-line no-implicit-coercion - return applyStyle(builder, (arguments_.length === 1) ? ('' + arguments_[0]) : arguments_.join(' ')); - }; - - // `__proto__` is used because we must return a function, but there is - // no way to create a function with a different prototype - builder.__proto__ = proto; // eslint-disable-line no-proto - - builder._generator = self; - builder._styler = _styler; - builder._isEmpty = _isEmpty; - - return builder; -}; - -const applyStyle = (self, string) => { - if (self.level <= 0 || !string) { - return self._isEmpty ? '' : string; - } - - let styler = self._styler; - - if (styler === undefined) { - return string; - } - - const {openAll, closeAll} = styler; - if (string.indexOf('\u001B') !== -1) { - while (styler !== undefined) { - // Replace any instances already present with a re-opening code - // otherwise only the part of the string until said closing code - // will be colored, and the rest will simply be 'plain'. - string = stringReplaceAll(string, styler.close, styler.open); - - styler = styler.parent; - } - } - - // We can move both next actions out of loop, because remaining actions in loop won't have - // any/visible effect on parts we add here. Close the styling before a linebreak and reopen - // after next line to fix a bleed issue on macOS: https://github.com/chalk/chalk/pull/92 - const lfIndex = string.indexOf('\n'); - if (lfIndex !== -1) { - string = stringEncaseCRLFWithFirstIndex(string, closeAll, openAll, lfIndex); - } - - return openAll + string + closeAll; -}; - -let template; -const chalkTag = (chalk, ...strings) => { - const [firstString] = strings; - - if (!Array.isArray(firstString)) { - // If chalk() was called by itself or with a string, - // return the string itself as a string. - return strings.join(' '); - } - - const arguments_ = strings.slice(1); - const parts = [firstString.raw[0]]; - - for (let i = 1; i < firstString.length; i++) { - parts.push( - String(arguments_[i - 1]).replace(/[{}\\]/g, '\\$&'), - String(firstString.raw[i]) - ); - } - - if (template === undefined) { - template = __webpack_require__("../../node_modules/ora/node_modules/chalk/source/templates.js"); - } - - return template(chalk, parts.join('')); -}; - -Object.defineProperties(Chalk.prototype, styles); - -const chalk = Chalk(); // eslint-disable-line new-cap -chalk.supportsColor = stdoutColor; -chalk.stderr = Chalk({level: stderrColor ? stderrColor.level : 0}); // eslint-disable-line new-cap -chalk.stderr.supportsColor = stderrColor; - -// For TypeScript -chalk.Level = { - None: 0, - Basic: 1, - Ansi256: 2, - TrueColor: 3, - 0: 'None', - 1: 'Basic', - 2: 'Ansi256', - 3: 'TrueColor' -}; - -module.exports = chalk; - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/chalk/source/templates.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const TEMPLATE_REGEX = /(?:\\(u(?:[a-f\d]{4}|\{[a-f\d]{1,6}\})|x[a-f\d]{2}|.))|(?:\{(~)?(\w+(?:\([^)]*\))?(?:\.\w+(?:\([^)]*\))?)*)(?:[ \t]|(?=\r?\n)))|(\})|((?:.|[\r\n\f])+?)/gi; -const STYLE_REGEX = /(?:^|\.)(\w+)(?:\(([^)]*)\))?/g; -const STRING_REGEX = /^(['"])((?:\\.|(?!\1)[^\\])*)\1$/; -const ESCAPE_REGEX = /\\(u(?:[a-f\d]{4}|\{[a-f\d]{1,6}\})|x[a-f\d]{2}|.)|([^\\])/gi; - -const ESCAPES = new Map([ - ['n', '\n'], - ['r', '\r'], - ['t', '\t'], - ['b', '\b'], - ['f', '\f'], - ['v', '\v'], - ['0', '\0'], - ['\\', '\\'], - ['e', '\u001B'], - ['a', '\u0007'] -]); - -function unescape(c) { - const u = c[0] === 'u'; - const bracket = c[1] === '{'; - - if ((u && !bracket && c.length === 5) || (c[0] === 'x' && c.length === 3)) { - return String.fromCharCode(parseInt(c.slice(1), 16)); - } - - if (u && bracket) { - return String.fromCodePoint(parseInt(c.slice(2, -1), 16)); - } - - return ESCAPES.get(c) || c; -} - -function parseArguments(name, arguments_) { - const results = []; - const chunks = arguments_.trim().split(/\s*,\s*/g); - let matches; - - for (const chunk of chunks) { - const number = Number(chunk); - if (!Number.isNaN(number)) { - results.push(number); - } else if ((matches = chunk.match(STRING_REGEX))) { - results.push(matches[2].replace(ESCAPE_REGEX, (m, escape, character) => escape ? unescape(escape) : character)); - } else { - throw new Error(`Invalid Chalk template style argument: ${chunk} (in style '${name}')`); - } - } - - return results; -} - -function parseStyle(style) { - STYLE_REGEX.lastIndex = 0; - - const results = []; - let matches; - - while ((matches = STYLE_REGEX.exec(style)) !== null) { - const name = matches[1]; - - if (matches[2]) { - const args = parseArguments(name, matches[2]); - results.push([name].concat(args)); - } else { - results.push([name]); - } - } - - return results; -} - -function buildStyle(chalk, styles) { - const enabled = {}; - - for (const layer of styles) { - for (const style of layer.styles) { - enabled[style[0]] = layer.inverse ? null : style.slice(1); - } - } - - let current = chalk; - for (const [styleName, styles] of Object.entries(enabled)) { - if (!Array.isArray(styles)) { - continue; - } - - if (!(styleName in current)) { - throw new Error(`Unknown Chalk style: ${styleName}`); - } - - current = styles.length > 0 ? current[styleName](...styles) : current[styleName]; - } - - return current; -} - -module.exports = (chalk, temporary) => { - const styles = []; - const chunks = []; - let chunk = []; - - // eslint-disable-next-line max-params - temporary.replace(TEMPLATE_REGEX, (m, escapeCharacter, inverse, style, close, character) => { - if (escapeCharacter) { - chunk.push(unescape(escapeCharacter)); - } else if (style) { - const string = chunk.join(''); - chunk = []; - chunks.push(styles.length === 0 ? string : buildStyle(chalk, styles)(string)); - styles.push({inverse, styles: parseStyle(style)}); - } else if (close) { - if (styles.length === 0) { - throw new Error('Found extraneous } in Chalk template literal'); - } - - chunks.push(buildStyle(chalk, styles)(chunk.join(''))); - chunk = []; - styles.pop(); - } else { - chunk.push(character); - } - }); - - chunks.push(chunk.join('')); - - if (styles.length > 0) { - const errMsg = `Chalk template literal is missing ${styles.length} closing bracket${styles.length === 1 ? '' : 's'} (\`}\`)`; - throw new Error(errMsg); - } - - return chunks.join(''); -}; - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/chalk/source/util.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const stringReplaceAll = (string, substring, replacer) => { - let index = string.indexOf(substring); - if (index === -1) { - return string; - } - - const substringLength = substring.length; - let endIndex = 0; - let returnValue = ''; - do { - returnValue += string.substr(endIndex, index - endIndex) + substring + replacer; - endIndex = index + substringLength; - index = string.indexOf(substring, endIndex); - } while (index !== -1); - - returnValue += string.substr(endIndex); - return returnValue; -}; - -const stringEncaseCRLFWithFirstIndex = (string, prefix, postfix, index) => { - let endIndex = 0; - let returnValue = ''; - do { - const gotCR = string[index - 1] === '\r'; - returnValue += string.substr(endIndex, (gotCR ? index - 1 : index) - endIndex) + prefix + (gotCR ? '\r\n' : '\n') + postfix; - endIndex = index + 1; - index = string.indexOf('\n', endIndex); - } while (index !== -1); - - returnValue += string.substr(endIndex); - return returnValue; -}; - -module.exports = { - stringReplaceAll, - stringEncaseCRLFWithFirstIndex -}; - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/has-flag/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = (flag, argv) => { - argv = argv || process.argv; - const prefix = flag.startsWith('-') ? '' : (flag.length === 1 ? '-' : '--'); - const pos = argv.indexOf(prefix + flag); - const terminatorPos = argv.indexOf('--'); - return pos !== -1 && (terminatorPos === -1 ? true : pos < terminatorPos); -}; - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/log-symbols/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const chalk = __webpack_require__("../../node_modules/ora/node_modules/log-symbols/node_modules/chalk/index.js"); - -const isSupported = process.platform !== 'win32' || process.env.CI || process.env.TERM === 'xterm-256color'; - -const main = { - info: chalk.blue('ℹ'), - success: chalk.green('✔'), - warning: chalk.yellow('⚠'), - error: chalk.red('✖') -}; - -const fallbacks = { - info: chalk.blue('i'), - success: chalk.green('√'), - warning: chalk.yellow('‼'), - error: chalk.red('×') -}; - -module.exports = isSupported ? main : fallbacks; - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/log-symbols/node_modules/ansi-styles/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/* WEBPACK VAR INJECTION */(function(module) { -const colorConvert = __webpack_require__("../../node_modules/color-convert/index.js"); - -const wrapAnsi16 = (fn, offset) => function () { - const code = fn.apply(colorConvert, arguments); - return `\u001B[${code + offset}m`; -}; - -const wrapAnsi256 = (fn, offset) => function () { - const code = fn.apply(colorConvert, arguments); - return `\u001B[${38 + offset};5;${code}m`; -}; - -const wrapAnsi16m = (fn, offset) => function () { - const rgb = fn.apply(colorConvert, arguments); - return `\u001B[${38 + offset};2;${rgb[0]};${rgb[1]};${rgb[2]}m`; -}; - -function assembleStyles() { - const codes = new Map(); - const styles = { - modifier: { - reset: [0, 0], - // 21 isn't widely supported and 22 does the same thing - bold: [1, 22], - dim: [2, 22], - italic: [3, 23], - underline: [4, 24], - inverse: [7, 27], - hidden: [8, 28], - strikethrough: [9, 29] - }, - color: { - black: [30, 39], - red: [31, 39], - green: [32, 39], - yellow: [33, 39], - blue: [34, 39], - magenta: [35, 39], - cyan: [36, 39], - white: [37, 39], - gray: [90, 39], - - // Bright color - redBright: [91, 39], - greenBright: [92, 39], - yellowBright: [93, 39], - blueBright: [94, 39], - magentaBright: [95, 39], - cyanBright: [96, 39], - whiteBright: [97, 39] - }, - bgColor: { - bgBlack: [40, 49], - bgRed: [41, 49], - bgGreen: [42, 49], - bgYellow: [43, 49], - bgBlue: [44, 49], - bgMagenta: [45, 49], - bgCyan: [46, 49], - bgWhite: [47, 49], - - // Bright color - bgBlackBright: [100, 49], - bgRedBright: [101, 49], - bgGreenBright: [102, 49], - bgYellowBright: [103, 49], - bgBlueBright: [104, 49], - bgMagentaBright: [105, 49], - bgCyanBright: [106, 49], - bgWhiteBright: [107, 49] - } - }; - - // Fix humans - styles.color.grey = styles.color.gray; - - for (const groupName of Object.keys(styles)) { - const group = styles[groupName]; - - for (const styleName of Object.keys(group)) { - const style = group[styleName]; - - styles[styleName] = { - open: `\u001B[${style[0]}m`, - close: `\u001B[${style[1]}m` - }; - - group[styleName] = styles[styleName]; - - codes.set(style[0], style[1]); - } - - Object.defineProperty(styles, groupName, { - value: group, - enumerable: false - }); - - Object.defineProperty(styles, 'codes', { - value: codes, - enumerable: false - }); - } - - const ansi2ansi = n => n; - const rgb2rgb = (r, g, b) => [r, g, b]; - - styles.color.close = '\u001B[39m'; - styles.bgColor.close = '\u001B[49m'; - - styles.color.ansi = { - ansi: wrapAnsi16(ansi2ansi, 0) - }; - styles.color.ansi256 = { - ansi256: wrapAnsi256(ansi2ansi, 0) - }; - styles.color.ansi16m = { - rgb: wrapAnsi16m(rgb2rgb, 0) - }; - - styles.bgColor.ansi = { - ansi: wrapAnsi16(ansi2ansi, 10) - }; - styles.bgColor.ansi256 = { - ansi256: wrapAnsi256(ansi2ansi, 10) - }; - styles.bgColor.ansi16m = { - rgb: wrapAnsi16m(rgb2rgb, 10) - }; - - for (let key of Object.keys(colorConvert)) { - if (typeof colorConvert[key] !== 'object') { - continue; - } - - const suite = colorConvert[key]; - - if (key === 'ansi16') { - key = 'ansi'; - } - - if ('ansi16' in suite) { - styles.color.ansi[key] = wrapAnsi16(suite.ansi16, 0); - styles.bgColor.ansi[key] = wrapAnsi16(suite.ansi16, 10); - } - - if ('ansi256' in suite) { - styles.color.ansi256[key] = wrapAnsi256(suite.ansi256, 0); - styles.bgColor.ansi256[key] = wrapAnsi256(suite.ansi256, 10); - } - - if ('rgb' in suite) { - styles.color.ansi16m[key] = wrapAnsi16m(suite.rgb, 0); - styles.bgColor.ansi16m[key] = wrapAnsi16m(suite.rgb, 10); - } - } - - return styles; -} - -// Make the export immutable -Object.defineProperty(module, 'exports', { - enumerable: true, - get: assembleStyles -}); - -/* WEBPACK VAR INJECTION */}.call(this, __webpack_require__("../../node_modules/webpack/buildin/module.js")(module))) - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/log-symbols/node_modules/chalk/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const escapeStringRegexp = __webpack_require__("../../node_modules/escape-string-regexp/index.js"); -const ansiStyles = __webpack_require__("../../node_modules/ora/node_modules/log-symbols/node_modules/ansi-styles/index.js"); -const stdoutColor = __webpack_require__("../../node_modules/ora/node_modules/log-symbols/node_modules/supports-color/index.js").stdout; - -const template = __webpack_require__("../../node_modules/ora/node_modules/log-symbols/node_modules/chalk/templates.js"); - -const isSimpleWindowsTerm = process.platform === 'win32' && !(process.env.TERM || '').toLowerCase().startsWith('xterm'); - -// `supportsColor.level` → `ansiStyles.color[name]` mapping -const levelMapping = ['ansi', 'ansi', 'ansi256', 'ansi16m']; - -// `color-convert` models to exclude from the Chalk API due to conflicts and such -const skipModels = new Set(['gray']); - -const styles = Object.create(null); - -function applyOptions(obj, options) { - options = options || {}; - - // Detect level if not set manually - const scLevel = stdoutColor ? stdoutColor.level : 0; - obj.level = options.level === undefined ? scLevel : options.level; - obj.enabled = 'enabled' in options ? options.enabled : obj.level > 0; -} - -function Chalk(options) { - // We check for this.template here since calling `chalk.constructor()` - // by itself will have a `this` of a previously constructed chalk object - if (!this || !(this instanceof Chalk) || this.template) { - const chalk = {}; - applyOptions(chalk, options); - - chalk.template = function () { - const args = [].slice.call(arguments); - return chalkTag.apply(null, [chalk.template].concat(args)); - }; - - Object.setPrototypeOf(chalk, Chalk.prototype); - Object.setPrototypeOf(chalk.template, chalk); - - chalk.template.constructor = Chalk; - - return chalk.template; - } - - applyOptions(this, options); -} - -// Use bright blue on Windows as the normal blue color is illegible -if (isSimpleWindowsTerm) { - ansiStyles.blue.open = '\u001B[94m'; -} - -for (const key of Object.keys(ansiStyles)) { - ansiStyles[key].closeRe = new RegExp(escapeStringRegexp(ansiStyles[key].close), 'g'); - - styles[key] = { - get() { - const codes = ansiStyles[key]; - return build.call(this, this._styles ? this._styles.concat(codes) : [codes], this._empty, key); - } - }; -} - -styles.visible = { - get() { - return build.call(this, this._styles || [], true, 'visible'); - } -}; - -ansiStyles.color.closeRe = new RegExp(escapeStringRegexp(ansiStyles.color.close), 'g'); -for (const model of Object.keys(ansiStyles.color.ansi)) { - if (skipModels.has(model)) { - continue; - } - - styles[model] = { - get() { - const level = this.level; - return function () { - const open = ansiStyles.color[levelMapping[level]][model].apply(null, arguments); - const codes = { - open, - close: ansiStyles.color.close, - closeRe: ansiStyles.color.closeRe - }; - return build.call(this, this._styles ? this._styles.concat(codes) : [codes], this._empty, model); - }; - } - }; -} - -ansiStyles.bgColor.closeRe = new RegExp(escapeStringRegexp(ansiStyles.bgColor.close), 'g'); -for (const model of Object.keys(ansiStyles.bgColor.ansi)) { - if (skipModels.has(model)) { - continue; - } - - const bgModel = 'bg' + model[0].toUpperCase() + model.slice(1); - styles[bgModel] = { - get() { - const level = this.level; - return function () { - const open = ansiStyles.bgColor[levelMapping[level]][model].apply(null, arguments); - const codes = { - open, - close: ansiStyles.bgColor.close, - closeRe: ansiStyles.bgColor.closeRe - }; - return build.call(this, this._styles ? this._styles.concat(codes) : [codes], this._empty, model); - }; - } - }; -} - -const proto = Object.defineProperties(() => {}, styles); - -function build(_styles, _empty, key) { - const builder = function () { - return applyStyle.apply(builder, arguments); - }; - - builder._styles = _styles; - builder._empty = _empty; - - const self = this; - - Object.defineProperty(builder, 'level', { - enumerable: true, - get() { - return self.level; - }, - set(level) { - self.level = level; - } - }); - - Object.defineProperty(builder, 'enabled', { - enumerable: true, - get() { - return self.enabled; - }, - set(enabled) { - self.enabled = enabled; - } - }); - - // See below for fix regarding invisible grey/dim combination on Windows - builder.hasGrey = this.hasGrey || key === 'gray' || key === 'grey'; - - // `__proto__` is used because we must return a function, but there is - // no way to create a function with a different prototype - builder.__proto__ = proto; // eslint-disable-line no-proto - - return builder; -} - -function applyStyle() { - // Support varags, but simply cast to string in case there's only one arg - const args = arguments; - const argsLen = args.length; - let str = String(arguments[0]); - - if (argsLen === 0) { - return ''; - } - - if (argsLen > 1) { - // Don't slice `arguments`, it prevents V8 optimizations - for (let a = 1; a < argsLen; a++) { - str += ' ' + args[a]; - } - } - - if (!this.enabled || this.level <= 0 || !str) { - return this._empty ? '' : str; - } - - // Turns out that on Windows dimmed gray text becomes invisible in cmd.exe, - // see https://github.com/chalk/chalk/issues/58 - // If we're on Windows and we're dealing with a gray color, temporarily make 'dim' a noop. - const originalDim = ansiStyles.dim.open; - if (isSimpleWindowsTerm && this.hasGrey) { - ansiStyles.dim.open = ''; - } - - for (const code of this._styles.slice().reverse()) { - // Replace any instances already present with a re-opening code - // otherwise only the part of the string until said closing code - // will be colored, and the rest will simply be 'plain'. - str = code.open + str.replace(code.closeRe, code.open) + code.close; - - // Close the styling before a linebreak and reopen - // after next line to fix a bleed issue on macOS - // https://github.com/chalk/chalk/pull/92 - str = str.replace(/\r?\n/g, `${code.close}$&${code.open}`); - } - - // Reset the original `dim` if we changed it to work around the Windows dimmed gray issue - ansiStyles.dim.open = originalDim; - - return str; -} - -function chalkTag(chalk, strings) { - if (!Array.isArray(strings)) { - // If chalk() was called by itself or with a string, - // return the string itself as a string. - return [].slice.call(arguments, 1).join(' '); - } - - const args = [].slice.call(arguments, 2); - const parts = [strings.raw[0]]; - - for (let i = 1; i < strings.length; i++) { - parts.push(String(args[i - 1]).replace(/[{}\\]/g, '\\$&')); - parts.push(String(strings.raw[i])); - } - - return template(chalk, parts.join('')); -} - -Object.defineProperties(Chalk.prototype, styles); - -module.exports = Chalk(); // eslint-disable-line new-cap -module.exports.supportsColor = stdoutColor; -module.exports.default = module.exports; // For TypeScript - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/log-symbols/node_modules/chalk/templates.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const TEMPLATE_REGEX = /(?:\\(u[a-f\d]{4}|x[a-f\d]{2}|.))|(?:\{(~)?(\w+(?:\([^)]*\))?(?:\.\w+(?:\([^)]*\))?)*)(?:[ \t]|(?=\r?\n)))|(\})|((?:.|[\r\n\f])+?)/gi; -const STYLE_REGEX = /(?:^|\.)(\w+)(?:\(([^)]*)\))?/g; -const STRING_REGEX = /^(['"])((?:\\.|(?!\1)[^\\])*)\1$/; -const ESCAPE_REGEX = /\\(u[a-f\d]{4}|x[a-f\d]{2}|.)|([^\\])/gi; - -const ESCAPES = new Map([ - ['n', '\n'], - ['r', '\r'], - ['t', '\t'], - ['b', '\b'], - ['f', '\f'], - ['v', '\v'], - ['0', '\0'], - ['\\', '\\'], - ['e', '\u001B'], - ['a', '\u0007'] -]); - -function unescape(c) { - if ((c[0] === 'u' && c.length === 5) || (c[0] === 'x' && c.length === 3)) { - return String.fromCharCode(parseInt(c.slice(1), 16)); - } - - return ESCAPES.get(c) || c; -} - -function parseArguments(name, args) { - const results = []; - const chunks = args.trim().split(/\s*,\s*/g); - let matches; - - for (const chunk of chunks) { - if (!isNaN(chunk)) { - results.push(Number(chunk)); - } else if ((matches = chunk.match(STRING_REGEX))) { - results.push(matches[2].replace(ESCAPE_REGEX, (m, escape, chr) => escape ? unescape(escape) : chr)); - } else { - throw new Error(`Invalid Chalk template style argument: ${chunk} (in style '${name}')`); - } - } - - return results; -} - -function parseStyle(style) { - STYLE_REGEX.lastIndex = 0; - - const results = []; - let matches; - - while ((matches = STYLE_REGEX.exec(style)) !== null) { - const name = matches[1]; - - if (matches[2]) { - const args = parseArguments(name, matches[2]); - results.push([name].concat(args)); - } else { - results.push([name]); - } - } - - return results; -} - -function buildStyle(chalk, styles) { - const enabled = {}; - - for (const layer of styles) { - for (const style of layer.styles) { - enabled[style[0]] = layer.inverse ? null : style.slice(1); - } - } - - let current = chalk; - for (const styleName of Object.keys(enabled)) { - if (Array.isArray(enabled[styleName])) { - if (!(styleName in current)) { - throw new Error(`Unknown Chalk style: ${styleName}`); - } - - if (enabled[styleName].length > 0) { - current = current[styleName].apply(current, enabled[styleName]); - } else { - current = current[styleName]; - } - } - } - - return current; -} - -module.exports = (chalk, tmp) => { - const styles = []; - const chunks = []; - let chunk = []; - - // eslint-disable-next-line max-params - tmp.replace(TEMPLATE_REGEX, (m, escapeChar, inverse, style, close, chr) => { - if (escapeChar) { - chunk.push(unescape(escapeChar)); - } else if (style) { - const str = chunk.join(''); - chunk = []; - chunks.push(styles.length === 0 ? str : buildStyle(chalk, styles)(str)); - styles.push({inverse, styles: parseStyle(style)}); - } else if (close) { - if (styles.length === 0) { - throw new Error('Found extraneous } in Chalk template literal'); - } - - chunks.push(buildStyle(chalk, styles)(chunk.join(''))); - chunk = []; - styles.pop(); - } else { - chunk.push(chr); - } - }); - - chunks.push(chunk.join('')); - - if (styles.length > 0) { - const errMsg = `Chalk template literal is missing ${styles.length} closing bracket${styles.length === 1 ? '' : 's'} (\`}\`)`; - throw new Error(errMsg); - } - - return chunks.join(''); -}; - - -/***/ }), - -/***/ "../../node_modules/ora/node_modules/log-symbols/node_modules/supports-color/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const os = __webpack_require__("os"); -const hasFlag = __webpack_require__("../../node_modules/ora/node_modules/has-flag/index.js"); - -const env = process.env; - -let forceColor; -if (hasFlag('no-color') || - hasFlag('no-colors') || - hasFlag('color=false')) { - forceColor = false; -} else if (hasFlag('color') || - hasFlag('colors') || - hasFlag('color=true') || - hasFlag('color=always')) { - forceColor = true; -} -if ('FORCE_COLOR' in env) { - forceColor = env.FORCE_COLOR.length === 0 || parseInt(env.FORCE_COLOR, 10) !== 0; -} - -function translateLevel(level) { - if (level === 0) { - return false; - } - - return { - level, - hasBasic: true, - has256: level >= 2, - has16m: level >= 3 - }; -} - -function supportsColor(stream) { - if (forceColor === false) { - return 0; - } - - if (hasFlag('color=16m') || - hasFlag('color=full') || - hasFlag('color=truecolor')) { - return 3; - } - - if (hasFlag('color=256')) { - return 2; - } - - if (stream && !stream.isTTY && forceColor !== true) { - return 0; - } - - const min = forceColor ? 1 : 0; - - if (process.platform === 'win32') { - // Node.js 7.5.0 is the first version of Node.js to include a patch to - // libuv that enables 256 color output on Windows. Anything earlier and it - // won't work. However, here we target Node.js 8 at minimum as it is an LTS - // release, and Node.js 7 is not. Windows 10 build 10586 is the first Windows - // release that supports 256 colors. Windows 10 build 14931 is the first release - // that supports 16m/TrueColor. - const osRelease = os.release().split('.'); - if ( - Number(process.versions.node.split('.')[0]) >= 8 && - Number(osRelease[0]) >= 10 && - Number(osRelease[2]) >= 10586 - ) { - return Number(osRelease[2]) >= 14931 ? 3 : 2; - } - - return 1; - } - - if ('CI' in env) { - if (['TRAVIS', 'CIRCLECI', 'APPVEYOR', 'GITLAB_CI'].some(sign => sign in env) || env.CI_NAME === 'codeship') { - return 1; - } - - return min; - } - - if ('TEAMCITY_VERSION' in env) { - return /^(9\.(0*[1-9]\d*)\.|\d{2,}\.)/.test(env.TEAMCITY_VERSION) ? 1 : 0; - } - - if (env.COLORTERM === 'truecolor') { - return 3; - } - - if ('TERM_PROGRAM' in env) { - const version = parseInt((env.TERM_PROGRAM_VERSION || '').split('.')[0], 10); - - switch (env.TERM_PROGRAM) { - case 'iTerm.app': - return version >= 3 ? 3 : 2; - case 'Apple_Terminal': - return 2; - // No default - } - } - - if (/-256(color)?$/i.test(env.TERM)) { - return 2; - } - - if (/^screen|^xterm|^vt100|^vt220|^rxvt|color|ansi|cygwin|linux/i.test(env.TERM)) { - return 1; - } - - if ('COLORTERM' in env) { - return 1; - } - - if (env.TERM === 'dumb') { - return min; - } - - return min; -} - -function getSupportLevel(stream) { - const level = supportsColor(stream); - return translateLevel(level); -} - -module.exports = { - supportsColor: getSupportLevel, - stdout: getSupportLevel(process.stdout), - stderr: getSupportLevel(process.stderr) -}; - - -/***/ }), - -/***/ "../../node_modules/parse-json/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const errorEx = __webpack_require__("../../node_modules/error-ex/index.js"); -const fallback = __webpack_require__("../../node_modules/json-parse-better-errors/index.js"); -const {default: LinesAndColumns} = __webpack_require__("../../node_modules/lines-and-columns/dist/index.mjs"); -const {codeFrameColumns} = __webpack_require__("../../node_modules/@babel/code-frame/lib/index.js"); - -const JSONError = errorEx('JSONError', { - fileName: errorEx.append('in %s'), - codeFrame: errorEx.append('\n\n%s\n') -}); - -module.exports = (string, reviver, filename) => { - if (typeof reviver === 'string') { - filename = reviver; - reviver = null; - } - - try { - try { - return JSON.parse(string, reviver); - } catch (error) { - fallback(string, reviver); - throw error; - } - } catch (error) { - error.message = error.message.replace(/\n/g, ''); - const indexMatch = error.message.match(/in JSON at position (\d+) while parsing near/); - - const jsonError = new JSONError(error); - if (filename) { - jsonError.fileName = filename; - } - - if (indexMatch && indexMatch.length > 0) { - const lines = new LinesAndColumns(string); - const index = Number(indexMatch[1]); - const location = lines.locationForIndex(index); - - const codeFrame = codeFrameColumns( - string, - {start: {line: location.line + 1, column: location.column + 1}}, - {highlightCode: true} - ); - - jsonError.codeFrame = codeFrame; - } - - throw jsonError; - } -}; - - -/***/ }), - -/***/ "../../node_modules/path-is-absolute/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -function posix(path) { - return path.charAt(0) === '/'; -} - -function win32(path) { - // https://github.com/nodejs/node/blob/b3fcc245fb25539909ef1d5eaa01dbf92e168633/lib/path.js#L56 - var splitDeviceRe = /^([a-zA-Z]:|[\\\/]{2}[^\\\/]+[\\\/]+[^\\\/]+)?([\\\/])?([\s\S]*?)$/; - var result = splitDeviceRe.exec(path); - var device = result[1] || ''; - var isUnc = Boolean(device && device.charAt(1) !== ':'); - - // UNC paths are always absolute - return Boolean(result[2] || isUnc); -} - -module.exports = process.platform === 'win32' ? win32 : posix; -module.exports.posix = posix; -module.exports.win32 = win32; - - -/***/ }), - -/***/ "../../node_modules/path-parse/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var isWindows = process.platform === 'win32'; - -// Regex to split a windows path into into [dir, root, basename, name, ext] -var splitWindowsRe = - /^(((?:[a-zA-Z]:|[\\\/]{2}[^\\\/]+[\\\/]+[^\\\/]+)?[\\\/]?)(?:[^\\\/]*[\\\/])*)((\.{1,2}|[^\\\/]+?|)(\.[^.\/\\]*|))[\\\/]*$/; - -var win32 = {}; - -function win32SplitPath(filename) { - return splitWindowsRe.exec(filename).slice(1); -} - -win32.parse = function(pathString) { - if (typeof pathString !== 'string') { - throw new TypeError( - "Parameter 'pathString' must be a string, not " + typeof pathString - ); - } - var allParts = win32SplitPath(pathString); - if (!allParts || allParts.length !== 5) { - throw new TypeError("Invalid path '" + pathString + "'"); - } - return { - root: allParts[1], - dir: allParts[0] === allParts[1] ? allParts[0] : allParts[0].slice(0, -1), - base: allParts[2], - ext: allParts[4], - name: allParts[3] - }; -}; - - - -// Split a filename into [dir, root, basename, name, ext], unix version -// 'root' is just a slash, or nothing. -var splitPathRe = - /^((\/?)(?:[^\/]*\/)*)((\.{1,2}|[^\/]+?|)(\.[^.\/]*|))[\/]*$/; -var posix = {}; - - -function posixSplitPath(filename) { - return splitPathRe.exec(filename).slice(1); -} - - -posix.parse = function(pathString) { - if (typeof pathString !== 'string') { - throw new TypeError( - "Parameter 'pathString' must be a string, not " + typeof pathString - ); - } - var allParts = posixSplitPath(pathString); - if (!allParts || allParts.length !== 5) { - throw new TypeError("Invalid path '" + pathString + "'"); - } - - return { - root: allParts[1], - dir: allParts[0].slice(0, -1), - base: allParts[2], - ext: allParts[4], - name: allParts[3], - }; -}; - - -if (isWindows) - module.exports = win32.parse; -else /* posix */ - module.exports = posix.parse; - -module.exports.posix = posix.parse; -module.exports.win32 = win32.parse; - - -/***/ }), - -/***/ "../../node_modules/path-type/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {promisify} = __webpack_require__("util"); -const fs = __webpack_require__("fs"); - -async function isType(fsStatType, statsMethodName, filePath) { - if (typeof filePath !== 'string') { - throw new TypeError(`Expected a string, got ${typeof filePath}`); - } - - try { - const stats = await promisify(fs[fsStatType])(filePath); - return stats[statsMethodName](); - } catch (error) { - if (error.code === 'ENOENT') { - return false; - } - - throw error; - } -} - -function isTypeSync(fsStatType, statsMethodName, filePath) { - if (typeof filePath !== 'string') { - throw new TypeError(`Expected a string, got ${typeof filePath}`); - } - - try { - return fs[fsStatType](filePath)[statsMethodName](); - } catch (error) { - if (error.code === 'ENOENT') { - return false; - } - - throw error; - } -} - -exports.isFile = isType.bind(null, 'stat', 'isFile'); -exports.isDirectory = isType.bind(null, 'stat', 'isDirectory'); -exports.isSymlink = isType.bind(null, 'lstat', 'isSymbolicLink'); -exports.isFileSync = isTypeSync.bind(null, 'statSync', 'isFile'); -exports.isDirectorySync = isTypeSync.bind(null, 'statSync', 'isDirectory'); -exports.isSymlinkSync = isTypeSync.bind(null, 'lstatSync', 'isSymbolicLink'); - - -/***/ }), - -/***/ "../../node_modules/picomatch/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = __webpack_require__("../../node_modules/picomatch/lib/picomatch.js"); - - -/***/ }), - -/***/ "../../node_modules/picomatch/lib/constants.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const path = __webpack_require__("path"); -const WIN_SLASH = '\\\\/'; -const WIN_NO_SLASH = `[^${WIN_SLASH}]`; - -/** - * Posix glob regex - */ - -const DOT_LITERAL = '\\.'; -const PLUS_LITERAL = '\\+'; -const QMARK_LITERAL = '\\?'; -const SLASH_LITERAL = '\\/'; -const ONE_CHAR = '(?=.)'; -const QMARK = '[^/]'; -const END_ANCHOR = `(?:${SLASH_LITERAL}|$)`; -const START_ANCHOR = `(?:^|${SLASH_LITERAL})`; -const DOTS_SLASH = `${DOT_LITERAL}{1,2}${END_ANCHOR}`; -const NO_DOT = `(?!${DOT_LITERAL})`; -const NO_DOTS = `(?!${START_ANCHOR}${DOTS_SLASH})`; -const NO_DOT_SLASH = `(?!${DOT_LITERAL}{0,1}${END_ANCHOR})`; -const NO_DOTS_SLASH = `(?!${DOTS_SLASH})`; -const QMARK_NO_DOT = `[^.${SLASH_LITERAL}]`; -const STAR = `${QMARK}*?`; - -const POSIX_CHARS = { - DOT_LITERAL, - PLUS_LITERAL, - QMARK_LITERAL, - SLASH_LITERAL, - ONE_CHAR, - QMARK, - END_ANCHOR, - DOTS_SLASH, - NO_DOT, - NO_DOTS, - NO_DOT_SLASH, - NO_DOTS_SLASH, - QMARK_NO_DOT, - STAR, - START_ANCHOR -}; - -/** - * Windows glob regex - */ - -const WINDOWS_CHARS = { - ...POSIX_CHARS, - - SLASH_LITERAL: `[${WIN_SLASH}]`, - QMARK: WIN_NO_SLASH, - STAR: `${WIN_NO_SLASH}*?`, - DOTS_SLASH: `${DOT_LITERAL}{1,2}(?:[${WIN_SLASH}]|$)`, - NO_DOT: `(?!${DOT_LITERAL})`, - NO_DOTS: `(?!(?:^|[${WIN_SLASH}])${DOT_LITERAL}{1,2}(?:[${WIN_SLASH}]|$))`, - NO_DOT_SLASH: `(?!${DOT_LITERAL}{0,1}(?:[${WIN_SLASH}]|$))`, - NO_DOTS_SLASH: `(?!${DOT_LITERAL}{1,2}(?:[${WIN_SLASH}]|$))`, - QMARK_NO_DOT: `[^.${WIN_SLASH}]`, - START_ANCHOR: `(?:^|[${WIN_SLASH}])`, - END_ANCHOR: `(?:[${WIN_SLASH}]|$)` -}; - -/** - * POSIX Bracket Regex - */ - -const POSIX_REGEX_SOURCE = { - alnum: 'a-zA-Z0-9', - alpha: 'a-zA-Z', - ascii: '\\x00-\\x7F', - blank: ' \\t', - cntrl: '\\x00-\\x1F\\x7F', - digit: '0-9', - graph: '\\x21-\\x7E', - lower: 'a-z', - print: '\\x20-\\x7E ', - punct: '\\-!"#$%&\'()\\*+,./:;<=>?@[\\]^_`{|}~', - space: ' \\t\\r\\n\\v\\f', - upper: 'A-Z', - word: 'A-Za-z0-9_', - xdigit: 'A-Fa-f0-9' -}; - -module.exports = { - MAX_LENGTH: 1024 * 64, - POSIX_REGEX_SOURCE, - - // regular expressions - REGEX_BACKSLASH: /\\(?![*+?^${}(|)[\]])/g, - REGEX_NON_SPECIAL_CHARS: /^[^@![\].,$*+?^{}()|\\/]+/, - REGEX_SPECIAL_CHARS: /[-*+?.^${}(|)[\]]/, - REGEX_SPECIAL_CHARS_BACKREF: /(\\?)((\W)(\3*))/g, - REGEX_SPECIAL_CHARS_GLOBAL: /([-*+?.^${}(|)[\]])/g, - REGEX_REMOVE_BACKSLASH: /(?:\[.*?[^\\]\]|\\(?=.))/g, - - // Replace globs with equivalent patterns to reduce parsing time. - REPLACEMENTS: { - '***': '*', - '**/**': '**', - '**/**/**': '**' - }, - - // Digits - CHAR_0: 48, /* 0 */ - CHAR_9: 57, /* 9 */ - - // Alphabet chars. - CHAR_UPPERCASE_A: 65, /* A */ - CHAR_LOWERCASE_A: 97, /* a */ - CHAR_UPPERCASE_Z: 90, /* Z */ - CHAR_LOWERCASE_Z: 122, /* z */ - - CHAR_LEFT_PARENTHESES: 40, /* ( */ - CHAR_RIGHT_PARENTHESES: 41, /* ) */ - - CHAR_ASTERISK: 42, /* * */ - - // Non-alphabetic chars. - CHAR_AMPERSAND: 38, /* & */ - CHAR_AT: 64, /* @ */ - CHAR_BACKWARD_SLASH: 92, /* \ */ - CHAR_CARRIAGE_RETURN: 13, /* \r */ - CHAR_CIRCUMFLEX_ACCENT: 94, /* ^ */ - CHAR_COLON: 58, /* : */ - CHAR_COMMA: 44, /* , */ - CHAR_DOT: 46, /* . */ - CHAR_DOUBLE_QUOTE: 34, /* " */ - CHAR_EQUAL: 61, /* = */ - CHAR_EXCLAMATION_MARK: 33, /* ! */ - CHAR_FORM_FEED: 12, /* \f */ - CHAR_FORWARD_SLASH: 47, /* / */ - CHAR_GRAVE_ACCENT: 96, /* ` */ - CHAR_HASH: 35, /* # */ - CHAR_HYPHEN_MINUS: 45, /* - */ - CHAR_LEFT_ANGLE_BRACKET: 60, /* < */ - CHAR_LEFT_CURLY_BRACE: 123, /* { */ - CHAR_LEFT_SQUARE_BRACKET: 91, /* [ */ - CHAR_LINE_FEED: 10, /* \n */ - CHAR_NO_BREAK_SPACE: 160, /* \u00A0 */ - CHAR_PERCENT: 37, /* % */ - CHAR_PLUS: 43, /* + */ - CHAR_QUESTION_MARK: 63, /* ? */ - CHAR_RIGHT_ANGLE_BRACKET: 62, /* > */ - CHAR_RIGHT_CURLY_BRACE: 125, /* } */ - CHAR_RIGHT_SQUARE_BRACKET: 93, /* ] */ - CHAR_SEMICOLON: 59, /* ; */ - CHAR_SINGLE_QUOTE: 39, /* ' */ - CHAR_SPACE: 32, /* */ - CHAR_TAB: 9, /* \t */ - CHAR_UNDERSCORE: 95, /* _ */ - CHAR_VERTICAL_LINE: 124, /* | */ - CHAR_ZERO_WIDTH_NOBREAK_SPACE: 65279, /* \uFEFF */ - - SEP: path.sep, - - /** - * Create EXTGLOB_CHARS - */ - - extglobChars(chars) { - return { - '!': { type: 'negate', open: '(?:(?!(?:', close: `))${chars.STAR})` }, - '?': { type: 'qmark', open: '(?:', close: ')?' }, - '+': { type: 'plus', open: '(?:', close: ')+' }, - '*': { type: 'star', open: '(?:', close: ')*' }, - '@': { type: 'at', open: '(?:', close: ')' } - }; - }, - - /** - * Create GLOB_CHARS - */ - - globChars(win32) { - return win32 === true ? WINDOWS_CHARS : POSIX_CHARS; - } -}; - - -/***/ }), - -/***/ "../../node_modules/picomatch/lib/parse.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const constants = __webpack_require__("../../node_modules/picomatch/lib/constants.js"); -const utils = __webpack_require__("../../node_modules/picomatch/lib/utils.js"); - -/** - * Constants - */ - -const { - MAX_LENGTH, - POSIX_REGEX_SOURCE, - REGEX_NON_SPECIAL_CHARS, - REGEX_SPECIAL_CHARS_BACKREF, - REPLACEMENTS -} = constants; - -/** - * Helpers - */ - -const expandRange = (args, options) => { - if (typeof options.expandRange === 'function') { - return options.expandRange(...args, options); - } - - args.sort(); - const value = `[${args.join('-')}]`; - - try { - /* eslint-disable-next-line no-new */ - new RegExp(value); - } catch (ex) { - return args.map(v => utils.escapeRegex(v)).join('..'); - } - - return value; -}; - -/** - * Create the message for a syntax error - */ - -const syntaxError = (type, char) => { - return `Missing ${type}: "${char}" - use "\\\\${char}" to match literal characters`; -}; - -/** - * Parse the given input string. - * @param {String} input - * @param {Object} options - * @return {Object} - */ - -const parse = (input, options) => { - if (typeof input !== 'string') { - throw new TypeError('Expected a string'); - } - - input = REPLACEMENTS[input] || input; - - const opts = { ...options }; - const max = typeof opts.maxLength === 'number' ? Math.min(MAX_LENGTH, opts.maxLength) : MAX_LENGTH; - - let len = input.length; - if (len > max) { - throw new SyntaxError(`Input length: ${len}, exceeds maximum allowed length: ${max}`); - } - - const bos = { type: 'bos', value: '', output: opts.prepend || '' }; - const tokens = [bos]; - - const capture = opts.capture ? '' : '?:'; - const win32 = utils.isWindows(options); - - // create constants based on platform, for windows or posix - const PLATFORM_CHARS = constants.globChars(win32); - const EXTGLOB_CHARS = constants.extglobChars(PLATFORM_CHARS); - - const { - DOT_LITERAL, - PLUS_LITERAL, - SLASH_LITERAL, - ONE_CHAR, - DOTS_SLASH, - NO_DOT, - NO_DOT_SLASH, - NO_DOTS_SLASH, - QMARK, - QMARK_NO_DOT, - STAR, - START_ANCHOR - } = PLATFORM_CHARS; - - const globstar = opts => { - return `(${capture}(?:(?!${START_ANCHOR}${opts.dot ? DOTS_SLASH : DOT_LITERAL}).)*?)`; - }; - - const nodot = opts.dot ? '' : NO_DOT; - const qmarkNoDot = opts.dot ? QMARK : QMARK_NO_DOT; - let star = opts.bash === true ? globstar(opts) : STAR; - - if (opts.capture) { - star = `(${star})`; - } - - // minimatch options support - if (typeof opts.noext === 'boolean') { - opts.noextglob = opts.noext; - } - - const state = { - input, - index: -1, - start: 0, - dot: opts.dot === true, - consumed: '', - output: '', - prefix: '', - backtrack: false, - negated: false, - brackets: 0, - braces: 0, - parens: 0, - quotes: 0, - globstar: false, - tokens - }; - - input = utils.removePrefix(input, state); - len = input.length; - - const extglobs = []; - const braces = []; - const stack = []; - let prev = bos; - let value; - - /** - * Tokenizing helpers - */ - - const eos = () => state.index === len - 1; - const peek = state.peek = (n = 1) => input[state.index + n]; - const advance = state.advance = () => input[++state.index] || ''; - const remaining = () => input.slice(state.index + 1); - const consume = (value = '', num = 0) => { - state.consumed += value; - state.index += num; - }; - - const append = token => { - state.output += token.output != null ? token.output : token.value; - consume(token.value); - }; - - const negate = () => { - let count = 1; - - while (peek() === '!' && (peek(2) !== '(' || peek(3) === '?')) { - advance(); - state.start++; - count++; - } - - if (count % 2 === 0) { - return false; - } - - state.negated = true; - state.start++; - return true; - }; - - const increment = type => { - state[type]++; - stack.push(type); - }; - - const decrement = type => { - state[type]--; - stack.pop(); - }; - - /** - * Push tokens onto the tokens array. This helper speeds up - * tokenizing by 1) helping us avoid backtracking as much as possible, - * and 2) helping us avoid creating extra tokens when consecutive - * characters are plain text. This improves performance and simplifies - * lookbehinds. - */ - - const push = tok => { - if (prev.type === 'globstar') { - const isBrace = state.braces > 0 && (tok.type === 'comma' || tok.type === 'brace'); - const isExtglob = tok.extglob === true || (extglobs.length && (tok.type === 'pipe' || tok.type === 'paren')); - - if (tok.type !== 'slash' && tok.type !== 'paren' && !isBrace && !isExtglob) { - state.output = state.output.slice(0, -prev.output.length); - prev.type = 'star'; - prev.value = '*'; - prev.output = star; - state.output += prev.output; - } - } - - if (extglobs.length && tok.type !== 'paren') { - extglobs[extglobs.length - 1].inner += tok.value; - } - - if (tok.value || tok.output) append(tok); - if (prev && prev.type === 'text' && tok.type === 'text') { - prev.value += tok.value; - prev.output = (prev.output || '') + tok.value; - return; - } - - tok.prev = prev; - tokens.push(tok); - prev = tok; - }; - - const extglobOpen = (type, value) => { - const token = { ...EXTGLOB_CHARS[value], conditions: 1, inner: '' }; - - token.prev = prev; - token.parens = state.parens; - token.output = state.output; - const output = (opts.capture ? '(' : '') + token.open; - - increment('parens'); - push({ type, value, output: state.output ? '' : ONE_CHAR }); - push({ type: 'paren', extglob: true, value: advance(), output }); - extglobs.push(token); - }; - - const extglobClose = token => { - let output = token.close + (opts.capture ? ')' : ''); - let rest; - - if (token.type === 'negate') { - let extglobStar = star; - - if (token.inner && token.inner.length > 1 && token.inner.includes('/')) { - extglobStar = globstar(opts); - } - - if (extglobStar !== star || eos() || /^\)+$/.test(remaining())) { - output = token.close = `)$))${extglobStar}`; - } - - if (token.inner.includes('*') && (rest = remaining()) && /^\.[^\\/.]+$/.test(rest)) { - output = token.close = `)${rest})${extglobStar})`; - } - - if (token.prev.type === 'bos') { - state.negatedExtglob = true; - } - } - - push({ type: 'paren', extglob: true, value, output }); - decrement('parens'); - }; - - /** - * Fast paths - */ - - if (opts.fastpaths !== false && !/(^[*!]|[/()[\]{}"])/.test(input)) { - let backslashes = false; - - let output = input.replace(REGEX_SPECIAL_CHARS_BACKREF, (m, esc, chars, first, rest, index) => { - if (first === '\\') { - backslashes = true; - return m; - } - - if (first === '?') { - if (esc) { - return esc + first + (rest ? QMARK.repeat(rest.length) : ''); - } - if (index === 0) { - return qmarkNoDot + (rest ? QMARK.repeat(rest.length) : ''); - } - return QMARK.repeat(chars.length); - } - - if (first === '.') { - return DOT_LITERAL.repeat(chars.length); - } - - if (first === '*') { - if (esc) { - return esc + first + (rest ? star : ''); - } - return star; - } - return esc ? m : `\\${m}`; - }); - - if (backslashes === true) { - if (opts.unescape === true) { - output = output.replace(/\\/g, ''); - } else { - output = output.replace(/\\+/g, m => { - return m.length % 2 === 0 ? '\\\\' : (m ? '\\' : ''); - }); - } - } - - if (output === input && opts.contains === true) { - state.output = input; - return state; - } - - state.output = utils.wrapOutput(output, state, options); - return state; - } - - /** - * Tokenize input until we reach end-of-string - */ - - while (!eos()) { - value = advance(); - - if (value === '\u0000') { - continue; - } - - /** - * Escaped characters - */ - - if (value === '\\') { - const next = peek(); - - if (next === '/' && opts.bash !== true) { - continue; - } - - if (next === '.' || next === ';') { - continue; - } - - if (!next) { - value += '\\'; - push({ type: 'text', value }); - continue; - } - - // collapse slashes to reduce potential for exploits - const match = /^\\+/.exec(remaining()); - let slashes = 0; - - if (match && match[0].length > 2) { - slashes = match[0].length; - state.index += slashes; - if (slashes % 2 !== 0) { - value += '\\'; - } - } - - if (opts.unescape === true) { - value = advance(); - } else { - value += advance(); - } - - if (state.brackets === 0) { - push({ type: 'text', value }); - continue; - } - } - - /** - * If we're inside a regex character class, continue - * until we reach the closing bracket. - */ - - if (state.brackets > 0 && (value !== ']' || prev.value === '[' || prev.value === '[^')) { - if (opts.posix !== false && value === ':') { - const inner = prev.value.slice(1); - if (inner.includes('[')) { - prev.posix = true; - - if (inner.includes(':')) { - const idx = prev.value.lastIndexOf('['); - const pre = prev.value.slice(0, idx); - const rest = prev.value.slice(idx + 2); - const posix = POSIX_REGEX_SOURCE[rest]; - if (posix) { - prev.value = pre + posix; - state.backtrack = true; - advance(); - - if (!bos.output && tokens.indexOf(prev) === 1) { - bos.output = ONE_CHAR; - } - continue; - } - } - } - } - - if ((value === '[' && peek() !== ':') || (value === '-' && peek() === ']')) { - value = `\\${value}`; - } - - if (value === ']' && (prev.value === '[' || prev.value === '[^')) { - value = `\\${value}`; - } - - if (opts.posix === true && value === '!' && prev.value === '[') { - value = '^'; - } - - prev.value += value; - append({ value }); - continue; - } - - /** - * If we're inside a quoted string, continue - * until we reach the closing double quote. - */ - - if (state.quotes === 1 && value !== '"') { - value = utils.escapeRegex(value); - prev.value += value; - append({ value }); - continue; - } - - /** - * Double quotes - */ - - if (value === '"') { - state.quotes = state.quotes === 1 ? 0 : 1; - if (opts.keepQuotes === true) { - push({ type: 'text', value }); - } - continue; - } - - /** - * Parentheses - */ - - if (value === '(') { - increment('parens'); - push({ type: 'paren', value }); - continue; - } - - if (value === ')') { - if (state.parens === 0 && opts.strictBrackets === true) { - throw new SyntaxError(syntaxError('opening', '(')); - } - - const extglob = extglobs[extglobs.length - 1]; - if (extglob && state.parens === extglob.parens + 1) { - extglobClose(extglobs.pop()); - continue; - } - - push({ type: 'paren', value, output: state.parens ? ')' : '\\)' }); - decrement('parens'); - continue; - } - - /** - * Square brackets - */ - - if (value === '[') { - if (opts.nobracket === true || !remaining().includes(']')) { - if (opts.nobracket !== true && opts.strictBrackets === true) { - throw new SyntaxError(syntaxError('closing', ']')); - } - - value = `\\${value}`; - } else { - increment('brackets'); - } - - push({ type: 'bracket', value }); - continue; - } - - if (value === ']') { - if (opts.nobracket === true || (prev && prev.type === 'bracket' && prev.value.length === 1)) { - push({ type: 'text', value, output: `\\${value}` }); - continue; - } - - if (state.brackets === 0) { - if (opts.strictBrackets === true) { - throw new SyntaxError(syntaxError('opening', '[')); - } - - push({ type: 'text', value, output: `\\${value}` }); - continue; - } - - decrement('brackets'); - - const prevValue = prev.value.slice(1); - if (prev.posix !== true && prevValue[0] === '^' && !prevValue.includes('/')) { - value = `/${value}`; - } - - prev.value += value; - append({ value }); - - // when literal brackets are explicitly disabled - // assume we should match with a regex character class - if (opts.literalBrackets === false || utils.hasRegexChars(prevValue)) { - continue; - } - - const escaped = utils.escapeRegex(prev.value); - state.output = state.output.slice(0, -prev.value.length); - - // when literal brackets are explicitly enabled - // assume we should escape the brackets to match literal characters - if (opts.literalBrackets === true) { - state.output += escaped; - prev.value = escaped; - continue; - } - - // when the user specifies nothing, try to match both - prev.value = `(${capture}${escaped}|${prev.value})`; - state.output += prev.value; - continue; - } - - /** - * Braces - */ - - if (value === '{' && opts.nobrace !== true) { - increment('braces'); - - const open = { - type: 'brace', - value, - output: '(', - outputIndex: state.output.length, - tokensIndex: state.tokens.length - }; - - braces.push(open); - push(open); - continue; - } - - if (value === '}') { - const brace = braces[braces.length - 1]; - - if (opts.nobrace === true || !brace) { - push({ type: 'text', value, output: value }); - continue; - } - - let output = ')'; - - if (brace.dots === true) { - const arr = tokens.slice(); - const range = []; - - for (let i = arr.length - 1; i >= 0; i--) { - tokens.pop(); - if (arr[i].type === 'brace') { - break; - } - if (arr[i].type !== 'dots') { - range.unshift(arr[i].value); - } - } - - output = expandRange(range, opts); - state.backtrack = true; - } - - if (brace.comma !== true && brace.dots !== true) { - const out = state.output.slice(0, brace.outputIndex); - const toks = state.tokens.slice(brace.tokensIndex); - brace.value = brace.output = '\\{'; - value = output = '\\}'; - state.output = out; - for (const t of toks) { - state.output += (t.output || t.value); - } - } - - push({ type: 'brace', value, output }); - decrement('braces'); - braces.pop(); - continue; - } - - /** - * Pipes - */ - - if (value === '|') { - if (extglobs.length > 0) { - extglobs[extglobs.length - 1].conditions++; - } - push({ type: 'text', value }); - continue; - } - - /** - * Commas - */ - - if (value === ',') { - let output = value; - - const brace = braces[braces.length - 1]; - if (brace && stack[stack.length - 1] === 'braces') { - brace.comma = true; - output = '|'; - } - - push({ type: 'comma', value, output }); - continue; - } - - /** - * Slashes - */ - - if (value === '/') { - // if the beginning of the glob is "./", advance the start - // to the current index, and don't add the "./" characters - // to the state. This greatly simplifies lookbehinds when - // checking for BOS characters like "!" and "." (not "./") - if (prev.type === 'dot' && state.index === state.start + 1) { - state.start = state.index + 1; - state.consumed = ''; - state.output = ''; - tokens.pop(); - prev = bos; // reset "prev" to the first token - continue; - } - - push({ type: 'slash', value, output: SLASH_LITERAL }); - continue; - } - - /** - * Dots - */ - - if (value === '.') { - if (state.braces > 0 && prev.type === 'dot') { - if (prev.value === '.') prev.output = DOT_LITERAL; - const brace = braces[braces.length - 1]; - prev.type = 'dots'; - prev.output += value; - prev.value += value; - brace.dots = true; - continue; - } - - if ((state.braces + state.parens) === 0 && prev.type !== 'bos' && prev.type !== 'slash') { - push({ type: 'text', value, output: DOT_LITERAL }); - continue; - } - - push({ type: 'dot', value, output: DOT_LITERAL }); - continue; - } - - /** - * Question marks - */ - - if (value === '?') { - const isGroup = prev && prev.value === '('; - if (!isGroup && opts.noextglob !== true && peek() === '(' && peek(2) !== '?') { - extglobOpen('qmark', value); - continue; - } - - if (prev && prev.type === 'paren') { - const next = peek(); - let output = value; - - if (next === '<' && !utils.supportsLookbehinds()) { - throw new Error('Node.js v10 or higher is required for regex lookbehinds'); - } - - if ((prev.value === '(' && !/[!=<:]/.test(next)) || (next === '<' && !/<([!=]|\w+>)/.test(remaining()))) { - output = `\\${value}`; - } - - push({ type: 'text', value, output }); - continue; - } - - if (opts.dot !== true && (prev.type === 'slash' || prev.type === 'bos')) { - push({ type: 'qmark', value, output: QMARK_NO_DOT }); - continue; - } - - push({ type: 'qmark', value, output: QMARK }); - continue; - } - - /** - * Exclamation - */ - - if (value === '!') { - if (opts.noextglob !== true && peek() === '(') { - if (peek(2) !== '?' || !/[!=<:]/.test(peek(3))) { - extglobOpen('negate', value); - continue; - } - } - - if (opts.nonegate !== true && state.index === 0) { - negate(); - continue; - } - } - - /** - * Plus - */ - - if (value === '+') { - if (opts.noextglob !== true && peek() === '(' && peek(2) !== '?') { - extglobOpen('plus', value); - continue; - } - - if ((prev && prev.value === '(') || opts.regex === false) { - push({ type: 'plus', value, output: PLUS_LITERAL }); - continue; - } - - if ((prev && (prev.type === 'bracket' || prev.type === 'paren' || prev.type === 'brace')) || state.parens > 0) { - push({ type: 'plus', value }); - continue; - } - - push({ type: 'plus', value: PLUS_LITERAL }); - continue; - } - - /** - * Plain text - */ - - if (value === '@') { - if (opts.noextglob !== true && peek() === '(' && peek(2) !== '?') { - push({ type: 'at', extglob: true, value, output: '' }); - continue; - } - - push({ type: 'text', value }); - continue; - } - - /** - * Plain text - */ - - if (value !== '*') { - if (value === '$' || value === '^') { - value = `\\${value}`; - } - - const match = REGEX_NON_SPECIAL_CHARS.exec(remaining()); - if (match) { - value += match[0]; - state.index += match[0].length; - } - - push({ type: 'text', value }); - continue; - } - - /** - * Stars - */ - - if (prev && (prev.type === 'globstar' || prev.star === true)) { - prev.type = 'star'; - prev.star = true; - prev.value += value; - prev.output = star; - state.backtrack = true; - state.globstar = true; - consume(value); - continue; - } - - let rest = remaining(); - if (opts.noextglob !== true && /^\([^?]/.test(rest)) { - extglobOpen('star', value); - continue; - } - - if (prev.type === 'star') { - if (opts.noglobstar === true) { - consume(value); - continue; - } - - const prior = prev.prev; - const before = prior.prev; - const isStart = prior.type === 'slash' || prior.type === 'bos'; - const afterStar = before && (before.type === 'star' || before.type === 'globstar'); - - if (opts.bash === true && (!isStart || (rest[0] && rest[0] !== '/'))) { - push({ type: 'star', value, output: '' }); - continue; - } - - const isBrace = state.braces > 0 && (prior.type === 'comma' || prior.type === 'brace'); - const isExtglob = extglobs.length && (prior.type === 'pipe' || prior.type === 'paren'); - if (!isStart && prior.type !== 'paren' && !isBrace && !isExtglob) { - push({ type: 'star', value, output: '' }); - continue; - } - - // strip consecutive `/**/` - while (rest.slice(0, 3) === '/**') { - const after = input[state.index + 4]; - if (after && after !== '/') { - break; - } - rest = rest.slice(3); - consume('/**', 3); - } - - if (prior.type === 'bos' && eos()) { - prev.type = 'globstar'; - prev.value += value; - prev.output = globstar(opts); - state.output = prev.output; - state.globstar = true; - consume(value); - continue; - } - - if (prior.type === 'slash' && prior.prev.type !== 'bos' && !afterStar && eos()) { - state.output = state.output.slice(0, -(prior.output + prev.output).length); - prior.output = `(?:${prior.output}`; - - prev.type = 'globstar'; - prev.output = globstar(opts) + (opts.strictSlashes ? ')' : '|$)'); - prev.value += value; - state.globstar = true; - state.output += prior.output + prev.output; - consume(value); - continue; - } - - if (prior.type === 'slash' && prior.prev.type !== 'bos' && rest[0] === '/') { - const end = rest[1] !== void 0 ? '|$' : ''; - - state.output = state.output.slice(0, -(prior.output + prev.output).length); - prior.output = `(?:${prior.output}`; - - prev.type = 'globstar'; - prev.output = `${globstar(opts)}${SLASH_LITERAL}|${SLASH_LITERAL}${end})`; - prev.value += value; - - state.output += prior.output + prev.output; - state.globstar = true; - - consume(value + advance()); - - push({ type: 'slash', value: '/', output: '' }); - continue; - } - - if (prior.type === 'bos' && rest[0] === '/') { - prev.type = 'globstar'; - prev.value += value; - prev.output = `(?:^|${SLASH_LITERAL}|${globstar(opts)}${SLASH_LITERAL})`; - state.output = prev.output; - state.globstar = true; - consume(value + advance()); - push({ type: 'slash', value: '/', output: '' }); - continue; - } - - // remove single star from output - state.output = state.output.slice(0, -prev.output.length); - - // reset previous token to globstar - prev.type = 'globstar'; - prev.output = globstar(opts); - prev.value += value; - - // reset output with globstar - state.output += prev.output; - state.globstar = true; - consume(value); - continue; - } - - const token = { type: 'star', value, output: star }; - - if (opts.bash === true) { - token.output = '.*?'; - if (prev.type === 'bos' || prev.type === 'slash') { - token.output = nodot + token.output; - } - push(token); - continue; - } - - if (prev && (prev.type === 'bracket' || prev.type === 'paren') && opts.regex === true) { - token.output = value; - push(token); - continue; - } - - if (state.index === state.start || prev.type === 'slash' || prev.type === 'dot') { - if (prev.type === 'dot') { - state.output += NO_DOT_SLASH; - prev.output += NO_DOT_SLASH; - - } else if (opts.dot === true) { - state.output += NO_DOTS_SLASH; - prev.output += NO_DOTS_SLASH; - - } else { - state.output += nodot; - prev.output += nodot; - } - - if (peek() !== '*') { - state.output += ONE_CHAR; - prev.output += ONE_CHAR; - } - } - - push(token); - } - - while (state.brackets > 0) { - if (opts.strictBrackets === true) throw new SyntaxError(syntaxError('closing', ']')); - state.output = utils.escapeLast(state.output, '['); - decrement('brackets'); - } - - while (state.parens > 0) { - if (opts.strictBrackets === true) throw new SyntaxError(syntaxError('closing', ')')); - state.output = utils.escapeLast(state.output, '('); - decrement('parens'); - } - - while (state.braces > 0) { - if (opts.strictBrackets === true) throw new SyntaxError(syntaxError('closing', '}')); - state.output = utils.escapeLast(state.output, '{'); - decrement('braces'); - } - - if (opts.strictSlashes !== true && (prev.type === 'star' || prev.type === 'bracket')) { - push({ type: 'maybe_slash', value: '', output: `${SLASH_LITERAL}?` }); - } - - // rebuild the output if we had to backtrack at any point - if (state.backtrack === true) { - state.output = ''; - - for (const token of state.tokens) { - state.output += token.output != null ? token.output : token.value; - - if (token.suffix) { - state.output += token.suffix; - } - } - } - - return state; -}; - -/** - * Fast paths for creating regular expressions for common glob patterns. - * This can significantly speed up processing and has very little downside - * impact when none of the fast paths match. - */ - -parse.fastpaths = (input, options) => { - const opts = { ...options }; - const max = typeof opts.maxLength === 'number' ? Math.min(MAX_LENGTH, opts.maxLength) : MAX_LENGTH; - const len = input.length; - if (len > max) { - throw new SyntaxError(`Input length: ${len}, exceeds maximum allowed length: ${max}`); - } - - input = REPLACEMENTS[input] || input; - const win32 = utils.isWindows(options); - - // create constants based on platform, for windows or posix - const { - DOT_LITERAL, - SLASH_LITERAL, - ONE_CHAR, - DOTS_SLASH, - NO_DOT, - NO_DOTS, - NO_DOTS_SLASH, - STAR, - START_ANCHOR - } = constants.globChars(win32); - - const nodot = opts.dot ? NO_DOTS : NO_DOT; - const slashDot = opts.dot ? NO_DOTS_SLASH : NO_DOT; - const capture = opts.capture ? '' : '?:'; - const state = { negated: false, prefix: '' }; - let star = opts.bash === true ? '.*?' : STAR; - - if (opts.capture) { - star = `(${star})`; - } - - const globstar = opts => { - if (opts.noglobstar === true) return star; - return `(${capture}(?:(?!${START_ANCHOR}${opts.dot ? DOTS_SLASH : DOT_LITERAL}).)*?)`; - }; - - const create = str => { - switch (str) { - case '*': - return `${nodot}${ONE_CHAR}${star}`; - - case '.*': - return `${DOT_LITERAL}${ONE_CHAR}${star}`; - - case '*.*': - return `${nodot}${star}${DOT_LITERAL}${ONE_CHAR}${star}`; - - case '*/*': - return `${nodot}${star}${SLASH_LITERAL}${ONE_CHAR}${slashDot}${star}`; - - case '**': - return nodot + globstar(opts); - - case '**/*': - return `(?:${nodot}${globstar(opts)}${SLASH_LITERAL})?${slashDot}${ONE_CHAR}${star}`; - - case '**/*.*': - return `(?:${nodot}${globstar(opts)}${SLASH_LITERAL})?${slashDot}${star}${DOT_LITERAL}${ONE_CHAR}${star}`; - - case '**/.*': - return `(?:${nodot}${globstar(opts)}${SLASH_LITERAL})?${DOT_LITERAL}${ONE_CHAR}${star}`; - - default: { - const match = /^(.*?)\.(\w+)$/.exec(str); - if (!match) return; - - const source = create(match[1]); - if (!source) return; - - return source + DOT_LITERAL + match[2]; - } - } - }; - - const output = utils.removePrefix(input, state); - let source = create(output); - - if (source && opts.strictSlashes !== true) { - source += `${SLASH_LITERAL}?`; - } - - return source; -}; - -module.exports = parse; - - -/***/ }), - -/***/ "../../node_modules/picomatch/lib/picomatch.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const path = __webpack_require__("path"); -const scan = __webpack_require__("../../node_modules/picomatch/lib/scan.js"); -const parse = __webpack_require__("../../node_modules/picomatch/lib/parse.js"); -const utils = __webpack_require__("../../node_modules/picomatch/lib/utils.js"); -const constants = __webpack_require__("../../node_modules/picomatch/lib/constants.js"); -const isObject = val => val && typeof val === 'object' && !Array.isArray(val); - -/** - * Creates a matcher function from one or more glob patterns. The - * returned function takes a string to match as its first argument, - * and returns true if the string is a match. The returned matcher - * function also takes a boolean as the second argument that, when true, - * returns an object with additional information. - * - * ```js - * const picomatch = require('picomatch'); - * // picomatch(glob[, options]); - * - * const isMatch = picomatch('*.!(*a)'); - * console.log(isMatch('a.a')); //=> false - * console.log(isMatch('a.b')); //=> true - * ``` - * @name picomatch - * @param {String|Array} `globs` One or more glob patterns. - * @param {Object=} `options` - * @return {Function=} Returns a matcher function. - * @api public - */ - -const picomatch = (glob, options, returnState = false) => { - if (Array.isArray(glob)) { - const fns = glob.map(input => picomatch(input, options, returnState)); - const arrayMatcher = str => { - for (const isMatch of fns) { - const state = isMatch(str); - if (state) return state; - } - return false; - }; - return arrayMatcher; - } - - const isState = isObject(glob) && glob.tokens && glob.input; - - if (glob === '' || (typeof glob !== 'string' && !isState)) { - throw new TypeError('Expected pattern to be a non-empty string'); - } - - const opts = options || {}; - const posix = utils.isWindows(options); - const regex = isState - ? picomatch.compileRe(glob, options) - : picomatch.makeRe(glob, options, false, true); - - const state = regex.state; - delete regex.state; - - let isIgnored = () => false; - if (opts.ignore) { - const ignoreOpts = { ...options, ignore: null, onMatch: null, onResult: null }; - isIgnored = picomatch(opts.ignore, ignoreOpts, returnState); - } - - const matcher = (input, returnObject = false) => { - const { isMatch, match, output } = picomatch.test(input, regex, options, { glob, posix }); - const result = { glob, state, regex, posix, input, output, match, isMatch }; - - if (typeof opts.onResult === 'function') { - opts.onResult(result); - } - - if (isMatch === false) { - result.isMatch = false; - return returnObject ? result : false; - } - - if (isIgnored(input)) { - if (typeof opts.onIgnore === 'function') { - opts.onIgnore(result); - } - result.isMatch = false; - return returnObject ? result : false; - } - - if (typeof opts.onMatch === 'function') { - opts.onMatch(result); - } - return returnObject ? result : true; - }; - - if (returnState) { - matcher.state = state; - } - - return matcher; -}; - -/** - * Test `input` with the given `regex`. This is used by the main - * `picomatch()` function to test the input string. - * - * ```js - * const picomatch = require('picomatch'); - * // picomatch.test(input, regex[, options]); - * - * console.log(picomatch.test('foo/bar', /^(?:([^/]*?)\/([^/]*?))$/)); - * // { isMatch: true, match: [ 'foo/', 'foo', 'bar' ], output: 'foo/bar' } - * ``` - * @param {String} `input` String to test. - * @param {RegExp} `regex` - * @return {Object} Returns an object with matching info. - * @api public - */ - -picomatch.test = (input, regex, options, { glob, posix } = {}) => { - if (typeof input !== 'string') { - throw new TypeError('Expected input to be a string'); - } - - if (input === '') { - return { isMatch: false, output: '' }; - } - - const opts = options || {}; - const format = opts.format || (posix ? utils.toPosixSlashes : null); - let match = input === glob; - let output = (match && format) ? format(input) : input; - - if (match === false) { - output = format ? format(input) : input; - match = output === glob; - } - - if (match === false || opts.capture === true) { - if (opts.matchBase === true || opts.basename === true) { - match = picomatch.matchBase(input, regex, options, posix); - } else { - match = regex.exec(output); - } - } - - return { isMatch: Boolean(match), match, output }; -}; - -/** - * Match the basename of a filepath. - * - * ```js - * const picomatch = require('picomatch'); - * // picomatch.matchBase(input, glob[, options]); - * console.log(picomatch.matchBase('foo/bar.js', '*.js'); // true - * ``` - * @param {String} `input` String to test. - * @param {RegExp|String} `glob` Glob pattern or regex created by [.makeRe](#makeRe). - * @return {Boolean} - * @api public - */ - -picomatch.matchBase = (input, glob, options, posix = utils.isWindows(options)) => { - const regex = glob instanceof RegExp ? glob : picomatch.makeRe(glob, options); - return regex.test(path.basename(input)); -}; - -/** - * Returns true if **any** of the given glob `patterns` match the specified `string`. - * - * ```js - * const picomatch = require('picomatch'); - * // picomatch.isMatch(string, patterns[, options]); - * - * console.log(picomatch.isMatch('a.a', ['b.*', '*.a'])); //=> true - * console.log(picomatch.isMatch('a.a', 'b.*')); //=> false - * ``` - * @param {String|Array} str The string to test. - * @param {String|Array} patterns One or more glob patterns to use for matching. - * @param {Object} [options] See available [options](#options). - * @return {Boolean} Returns true if any patterns match `str` - * @api public - */ - -picomatch.isMatch = (str, patterns, options) => picomatch(patterns, options)(str); - -/** - * Parse a glob pattern to create the source string for a regular - * expression. - * - * ```js - * const picomatch = require('picomatch'); - * const result = picomatch.parse(pattern[, options]); - * ``` - * @param {String} `pattern` - * @param {Object} `options` - * @return {Object} Returns an object with useful properties and output to be used as a regex source string. - * @api public - */ - -picomatch.parse = (pattern, options) => { - if (Array.isArray(pattern)) return pattern.map(p => picomatch.parse(p, options)); - return parse(pattern, { ...options, fastpaths: false }); -}; - -/** - * Scan a glob pattern to separate the pattern into segments. - * - * ```js - * const picomatch = require('picomatch'); - * // picomatch.scan(input[, options]); - * - * const result = picomatch.scan('!./foo/*.js'); - * console.log(result); - * { prefix: '!./', - * input: '!./foo/*.js', - * start: 3, - * base: 'foo', - * glob: '*.js', - * isBrace: false, - * isBracket: false, - * isGlob: true, - * isExtglob: false, - * isGlobstar: false, - * negated: true } - * ``` - * @param {String} `input` Glob pattern to scan. - * @param {Object} `options` - * @return {Object} Returns an object with - * @api public - */ - -picomatch.scan = (input, options) => scan(input, options); - -/** - * Compile a regular expression from the `state` object returned by the - * [parse()](#parse) method. - * - * @param {Object} `state` - * @param {Object} `options` - * @param {Boolean} `returnOutput` Intended for implementors, this argument allows you to return the raw output from the parser. - * @param {Boolean} `returnState` Adds the state to a `state` property on the returned regex. Useful for implementors and debugging. - * @return {RegExp} - * @api public - */ - -picomatch.compileRe = (state, options, returnOutput = false, returnState = false) => { - if (returnOutput === true) { - return state.output; - } - - const opts = options || {}; - const prepend = opts.contains ? '' : '^'; - const append = opts.contains ? '' : '$'; - - let source = `${prepend}(?:${state.output})${append}`; - if (state && state.negated === true) { - source = `^(?!${source}).*$`; - } - - const regex = picomatch.toRegex(source, options); - if (returnState === true) { - regex.state = state; - } - - return regex; -}; - -/** - * Create a regular expression from a parsed glob pattern. - * - * ```js - * const picomatch = require('picomatch'); - * const state = picomatch.parse('*.js'); - * // picomatch.compileRe(state[, options]); - * - * console.log(picomatch.compileRe(state)); - * //=> /^(?:(?!\.)(?=.)[^/]*?\.js)$/ - * ``` - * @param {String} `state` The object returned from the `.parse` method. - * @param {Object} `options` - * @param {Boolean} `returnOutput` Implementors may use this argument to return the compiled output, instead of a regular expression. This is not exposed on the options to prevent end-users from mutating the result. - * @param {Boolean} `returnState` Implementors may use this argument to return the state from the parsed glob with the returned regular expression. - * @return {RegExp} Returns a regex created from the given pattern. - * @api public - */ - -picomatch.makeRe = (input, options = {}, returnOutput = false, returnState = false) => { - if (!input || typeof input !== 'string') { - throw new TypeError('Expected a non-empty string'); - } - - let parsed = { negated: false, fastpaths: true }; - - if (options.fastpaths !== false && (input[0] === '.' || input[0] === '*')) { - parsed.output = parse.fastpaths(input, options); - } - - if (!parsed.output) { - parsed = parse(input, options); - } - - return picomatch.compileRe(parsed, options, returnOutput, returnState); -}; - -/** - * Create a regular expression from the given regex source string. - * - * ```js - * const picomatch = require('picomatch'); - * // picomatch.toRegex(source[, options]); - * - * const { output } = picomatch.parse('*.js'); - * console.log(picomatch.toRegex(output)); - * //=> /^(?:(?!\.)(?=.)[^/]*?\.js)$/ - * ``` - * @param {String} `source` Regular expression source string. - * @param {Object} `options` - * @return {RegExp} - * @api public - */ - -picomatch.toRegex = (source, options) => { - try { - const opts = options || {}; - return new RegExp(source, opts.flags || (opts.nocase ? 'i' : '')); - } catch (err) { - if (options && options.debug === true) throw err; - return /$^/; - } -}; - -/** - * Picomatch constants. - * @return {Object} - */ - -picomatch.constants = constants; - -/** - * Expose "picomatch" - */ - -module.exports = picomatch; - - -/***/ }), - -/***/ "../../node_modules/picomatch/lib/scan.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const utils = __webpack_require__("../../node_modules/picomatch/lib/utils.js"); -const { - CHAR_ASTERISK, /* * */ - CHAR_AT, /* @ */ - CHAR_BACKWARD_SLASH, /* \ */ - CHAR_COMMA, /* , */ - CHAR_DOT, /* . */ - CHAR_EXCLAMATION_MARK, /* ! */ - CHAR_FORWARD_SLASH, /* / */ - CHAR_LEFT_CURLY_BRACE, /* { */ - CHAR_LEFT_PARENTHESES, /* ( */ - CHAR_LEFT_SQUARE_BRACKET, /* [ */ - CHAR_PLUS, /* + */ - CHAR_QUESTION_MARK, /* ? */ - CHAR_RIGHT_CURLY_BRACE, /* } */ - CHAR_RIGHT_PARENTHESES, /* ) */ - CHAR_RIGHT_SQUARE_BRACKET /* ] */ -} = __webpack_require__("../../node_modules/picomatch/lib/constants.js"); - -const isPathSeparator = code => { - return code === CHAR_FORWARD_SLASH || code === CHAR_BACKWARD_SLASH; -}; - -const depth = token => { - if (token.isPrefix !== true) { - token.depth = token.isGlobstar ? Infinity : 1; - } -}; - -/** - * Quickly scans a glob pattern and returns an object with a handful of - * useful properties, like `isGlob`, `path` (the leading non-glob, if it exists), - * `glob` (the actual pattern), `negated` (true if the path starts with `!` but not - * with `!(`) and `negatedExtglob` (true if the path starts with `!(`). - * - * ```js - * const pm = require('picomatch'); - * console.log(pm.scan('foo/bar/*.js')); - * { isGlob: true, input: 'foo/bar/*.js', base: 'foo/bar', glob: '*.js' } - * ``` - * @param {String} `str` - * @param {Object} `options` - * @return {Object} Returns an object with tokens and regex source string. - * @api public - */ - -const scan = (input, options) => { - const opts = options || {}; - - const length = input.length - 1; - const scanToEnd = opts.parts === true || opts.scanToEnd === true; - const slashes = []; - const tokens = []; - const parts = []; - - let str = input; - let index = -1; - let start = 0; - let lastIndex = 0; - let isBrace = false; - let isBracket = false; - let isGlob = false; - let isExtglob = false; - let isGlobstar = false; - let braceEscaped = false; - let backslashes = false; - let negated = false; - let negatedExtglob = false; - let finished = false; - let braces = 0; - let prev; - let code; - let token = { value: '', depth: 0, isGlob: false }; - - const eos = () => index >= length; - const peek = () => str.charCodeAt(index + 1); - const advance = () => { - prev = code; - return str.charCodeAt(++index); - }; - - while (index < length) { - code = advance(); - let next; - - if (code === CHAR_BACKWARD_SLASH) { - backslashes = token.backslashes = true; - code = advance(); - - if (code === CHAR_LEFT_CURLY_BRACE) { - braceEscaped = true; - } - continue; - } - - if (braceEscaped === true || code === CHAR_LEFT_CURLY_BRACE) { - braces++; - - while (eos() !== true && (code = advance())) { - if (code === CHAR_BACKWARD_SLASH) { - backslashes = token.backslashes = true; - advance(); - continue; - } - - if (code === CHAR_LEFT_CURLY_BRACE) { - braces++; - continue; - } - - if (braceEscaped !== true && code === CHAR_DOT && (code = advance()) === CHAR_DOT) { - isBrace = token.isBrace = true; - isGlob = token.isGlob = true; - finished = true; - - if (scanToEnd === true) { - continue; - } - - break; - } - - if (braceEscaped !== true && code === CHAR_COMMA) { - isBrace = token.isBrace = true; - isGlob = token.isGlob = true; - finished = true; - - if (scanToEnd === true) { - continue; - } - - break; - } - - if (code === CHAR_RIGHT_CURLY_BRACE) { - braces--; - - if (braces === 0) { - braceEscaped = false; - isBrace = token.isBrace = true; - finished = true; - break; - } - } - } - - if (scanToEnd === true) { - continue; - } - - break; - } - - if (code === CHAR_FORWARD_SLASH) { - slashes.push(index); - tokens.push(token); - token = { value: '', depth: 0, isGlob: false }; - - if (finished === true) continue; - if (prev === CHAR_DOT && index === (start + 1)) { - start += 2; - continue; - } - - lastIndex = index + 1; - continue; - } - - if (opts.noext !== true) { - const isExtglobChar = code === CHAR_PLUS - || code === CHAR_AT - || code === CHAR_ASTERISK - || code === CHAR_QUESTION_MARK - || code === CHAR_EXCLAMATION_MARK; - - if (isExtglobChar === true && peek() === CHAR_LEFT_PARENTHESES) { - isGlob = token.isGlob = true; - isExtglob = token.isExtglob = true; - finished = true; - if (code === CHAR_EXCLAMATION_MARK && index === start) { - negatedExtglob = true; - } - - if (scanToEnd === true) { - while (eos() !== true && (code = advance())) { - if (code === CHAR_BACKWARD_SLASH) { - backslashes = token.backslashes = true; - code = advance(); - continue; - } - - if (code === CHAR_RIGHT_PARENTHESES) { - isGlob = token.isGlob = true; - finished = true; - break; - } - } - continue; - } - break; - } - } - - if (code === CHAR_ASTERISK) { - if (prev === CHAR_ASTERISK) isGlobstar = token.isGlobstar = true; - isGlob = token.isGlob = true; - finished = true; - - if (scanToEnd === true) { - continue; - } - break; - } - - if (code === CHAR_QUESTION_MARK) { - isGlob = token.isGlob = true; - finished = true; - - if (scanToEnd === true) { - continue; - } - break; - } - - if (code === CHAR_LEFT_SQUARE_BRACKET) { - while (eos() !== true && (next = advance())) { - if (next === CHAR_BACKWARD_SLASH) { - backslashes = token.backslashes = true; - advance(); - continue; - } - - if (next === CHAR_RIGHT_SQUARE_BRACKET) { - isBracket = token.isBracket = true; - isGlob = token.isGlob = true; - finished = true; - break; - } - } - - if (scanToEnd === true) { - continue; - } - - break; - } - - if (opts.nonegate !== true && code === CHAR_EXCLAMATION_MARK && index === start) { - negated = token.negated = true; - start++; - continue; - } - - if (opts.noparen !== true && code === CHAR_LEFT_PARENTHESES) { - isGlob = token.isGlob = true; - - if (scanToEnd === true) { - while (eos() !== true && (code = advance())) { - if (code === CHAR_LEFT_PARENTHESES) { - backslashes = token.backslashes = true; - code = advance(); - continue; - } - - if (code === CHAR_RIGHT_PARENTHESES) { - finished = true; - break; - } - } - continue; - } - break; - } - - if (isGlob === true) { - finished = true; - - if (scanToEnd === true) { - continue; - } - - break; - } - } - - if (opts.noext === true) { - isExtglob = false; - isGlob = false; - } - - let base = str; - let prefix = ''; - let glob = ''; - - if (start > 0) { - prefix = str.slice(0, start); - str = str.slice(start); - lastIndex -= start; - } - - if (base && isGlob === true && lastIndex > 0) { - base = str.slice(0, lastIndex); - glob = str.slice(lastIndex); - } else if (isGlob === true) { - base = ''; - glob = str; - } else { - base = str; - } - - if (base && base !== '' && base !== '/' && base !== str) { - if (isPathSeparator(base.charCodeAt(base.length - 1))) { - base = base.slice(0, -1); - } - } - - if (opts.unescape === true) { - if (glob) glob = utils.removeBackslashes(glob); - - if (base && backslashes === true) { - base = utils.removeBackslashes(base); - } - } - - const state = { - prefix, - input, - start, - base, - glob, - isBrace, - isBracket, - isGlob, - isExtglob, - isGlobstar, - negated, - negatedExtglob - }; - - if (opts.tokens === true) { - state.maxDepth = 0; - if (!isPathSeparator(code)) { - tokens.push(token); - } - state.tokens = tokens; - } - - if (opts.parts === true || opts.tokens === true) { - let prevIndex; - - for (let idx = 0; idx < slashes.length; idx++) { - const n = prevIndex ? prevIndex + 1 : start; - const i = slashes[idx]; - const value = input.slice(n, i); - if (opts.tokens) { - if (idx === 0 && start !== 0) { - tokens[idx].isPrefix = true; - tokens[idx].value = prefix; - } else { - tokens[idx].value = value; - } - depth(tokens[idx]); - state.maxDepth += tokens[idx].depth; - } - if (idx !== 0 || value !== '') { - parts.push(value); - } - prevIndex = i; - } - - if (prevIndex && prevIndex + 1 < input.length) { - const value = input.slice(prevIndex + 1); - parts.push(value); - - if (opts.tokens) { - tokens[tokens.length - 1].value = value; - depth(tokens[tokens.length - 1]); - state.maxDepth += tokens[tokens.length - 1].depth; - } - } - - state.slashes = slashes; - state.parts = parts; - } - - return state; -}; - -module.exports = scan; - - -/***/ }), - -/***/ "../../node_modules/picomatch/lib/utils.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const path = __webpack_require__("path"); -const win32 = process.platform === 'win32'; -const { - REGEX_BACKSLASH, - REGEX_REMOVE_BACKSLASH, - REGEX_SPECIAL_CHARS, - REGEX_SPECIAL_CHARS_GLOBAL -} = __webpack_require__("../../node_modules/picomatch/lib/constants.js"); - -exports.isObject = val => val !== null && typeof val === 'object' && !Array.isArray(val); -exports.hasRegexChars = str => REGEX_SPECIAL_CHARS.test(str); -exports.isRegexChar = str => str.length === 1 && exports.hasRegexChars(str); -exports.escapeRegex = str => str.replace(REGEX_SPECIAL_CHARS_GLOBAL, '\\$1'); -exports.toPosixSlashes = str => str.replace(REGEX_BACKSLASH, '/'); - -exports.removeBackslashes = str => { - return str.replace(REGEX_REMOVE_BACKSLASH, match => { - return match === '\\' ? '' : match; - }); -}; - -exports.supportsLookbehinds = () => { - const segs = process.version.slice(1).split('.').map(Number); - if (segs.length === 3 && segs[0] >= 9 || (segs[0] === 8 && segs[1] >= 10)) { - return true; - } - return false; -}; - -exports.isWindows = options => { - if (options && typeof options.windows === 'boolean') { - return options.windows; - } - return win32 === true || path.sep === '\\'; -}; - -exports.escapeLast = (input, char, lastIdx) => { - const idx = input.lastIndexOf(char, lastIdx); - if (idx === -1) return input; - if (input[idx - 1] === '\\') return exports.escapeLast(input, char, idx - 1); - return `${input.slice(0, idx)}\\${input.slice(idx)}`; -}; - -exports.removePrefix = (input, state = {}) => { - let output = input; - if (output.startsWith('./')) { - output = output.slice(2); - state.prefix = './'; - } - return output; -}; - -exports.wrapOutput = (input, state = {}, options = {}) => { - const prepend = options.contains ? '' : '^'; - const append = options.contains ? '' : '$'; - - let output = `${prepend}(?:${input})${append}`; - if (state.negated === true) { - output = `(?:^(?!${output}).*$)`; - } - return output; -}; - - -/***/ }), - -/***/ "../../node_modules/pump/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var once = __webpack_require__("../../node_modules/once/once.js") -var eos = __webpack_require__("../../node_modules/end-of-stream/index.js") -var fs = __webpack_require__("fs") // we only need fs to get the ReadStream and WriteStream prototypes - -var noop = function () {} -var ancient = /^v?\.0/.test(process.version) - -var isFn = function (fn) { - return typeof fn === 'function' -} - -var isFS = function (stream) { - if (!ancient) return false // newer node version do not need to care about fs is a special way - if (!fs) return false // browser - return (stream instanceof (fs.ReadStream || noop) || stream instanceof (fs.WriteStream || noop)) && isFn(stream.close) -} - -var isRequest = function (stream) { - return stream.setHeader && isFn(stream.abort) -} - -var destroyer = function (stream, reading, writing, callback) { - callback = once(callback) - - var closed = false - stream.on('close', function () { - closed = true - }) - - eos(stream, {readable: reading, writable: writing}, function (err) { - if (err) return callback(err) - closed = true - callback() - }) - - var destroyed = false - return function (err) { - if (closed) return - if (destroyed) return - destroyed = true - - if (isFS(stream)) return stream.close(noop) // use close for fs streams to avoid fd leaks - if (isRequest(stream)) return stream.abort() // request.destroy just do .end - .abort is what we want - - if (isFn(stream.destroy)) return stream.destroy() - - callback(err || new Error('stream was destroyed')) - } -} - -var call = function (fn) { - fn() -} - -var pipe = function (from, to) { - return from.pipe(to) -} - -var pump = function () { - var streams = Array.prototype.slice.call(arguments) - var callback = isFn(streams[streams.length - 1] || noop) && streams.pop() || noop - - if (Array.isArray(streams[0])) streams = streams[0] - if (streams.length < 2) throw new Error('pump requires two streams per minimum') - - var error - var destroys = streams.map(function (stream, i) { - var reading = i < streams.length - 1 - var writing = i > 0 - return destroyer(stream, reading, writing, function (err) { - if (!error) error = err - if (err) destroys.forEach(call) - if (reading) return - destroys.forEach(call) - callback(error) - }) - }) - - return streams.reduce(pipe) -} - -module.exports = pump - - -/***/ }), - -/***/ "../../node_modules/read-pkg/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const {promisify} = __webpack_require__("util"); -const fs = __webpack_require__("fs"); -const path = __webpack_require__("path"); -const parseJson = __webpack_require__("../../node_modules/parse-json/index.js"); - -const readFileAsync = promisify(fs.readFile); - -module.exports = async options => { - options = { - cwd: process.cwd(), - normalize: true, - ...options - }; - - const filePath = path.resolve(options.cwd, 'package.json'); - const json = parseJson(await readFileAsync(filePath, 'utf8')); - - if (options.normalize) { - __webpack_require__("../../node_modules/normalize-package-data/lib/normalize.js")(json); - } - - return json; -}; - -module.exports.sync = options => { - options = { - cwd: process.cwd(), - normalize: true, - ...options - }; - - const filePath = path.resolve(options.cwd, 'package.json'); - const json = parseJson(fs.readFileSync(filePath, 'utf8')); - - if (options.normalize) { - __webpack_require__("../../node_modules/normalize-package-data/lib/normalize.js")(json); - } - - return json; -}; - - -/***/ }), - -/***/ "../../node_modules/resolve/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var async = __webpack_require__("../../node_modules/resolve/lib/async.js"); -async.core = __webpack_require__("../../node_modules/resolve/lib/core.js"); -async.isCore = __webpack_require__("../../node_modules/resolve/lib/is-core.js"); -async.sync = __webpack_require__("../../node_modules/resolve/lib/sync.js"); - -module.exports = async; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/async.js": -/***/ (function(module, exports, __webpack_require__) { - -var fs = __webpack_require__("fs"); -var getHomedir = __webpack_require__("../../node_modules/resolve/lib/homedir.js"); -var path = __webpack_require__("path"); -var caller = __webpack_require__("../../node_modules/resolve/lib/caller.js"); -var nodeModulesPaths = __webpack_require__("../../node_modules/resolve/lib/node-modules-paths.js"); -var normalizeOptions = __webpack_require__("../../node_modules/resolve/lib/normalize-options.js"); -var isCore = __webpack_require__("../../node_modules/is-core-module/index.js"); - -var realpathFS = fs.realpath && typeof fs.realpath.native === 'function' ? fs.realpath.native : fs.realpath; - -var homedir = getHomedir(); -var defaultPaths = function () { - return [ - path.join(homedir, '.node_modules'), - path.join(homedir, '.node_libraries') - ]; -}; - -var defaultIsFile = function isFile(file, cb) { - fs.stat(file, function (err, stat) { - if (!err) { - return cb(null, stat.isFile() || stat.isFIFO()); - } - if (err.code === 'ENOENT' || err.code === 'ENOTDIR') return cb(null, false); - return cb(err); - }); -}; - -var defaultIsDir = function isDirectory(dir, cb) { - fs.stat(dir, function (err, stat) { - if (!err) { - return cb(null, stat.isDirectory()); - } - if (err.code === 'ENOENT' || err.code === 'ENOTDIR') return cb(null, false); - return cb(err); - }); -}; - -var defaultRealpath = function realpath(x, cb) { - realpathFS(x, function (realpathErr, realPath) { - if (realpathErr && realpathErr.code !== 'ENOENT') cb(realpathErr); - else cb(null, realpathErr ? x : realPath); - }); -}; - -var maybeRealpath = function maybeRealpath(realpath, x, opts, cb) { - if (opts && opts.preserveSymlinks === false) { - realpath(x, cb); - } else { - cb(null, x); - } -}; - -var defaultReadPackage = function defaultReadPackage(readFile, pkgfile, cb) { - readFile(pkgfile, function (readFileErr, body) { - if (readFileErr) cb(readFileErr); - else { - try { - var pkg = JSON.parse(body); - cb(null, pkg); - } catch (jsonErr) { - cb(null); - } - } - }); -}; - -var getPackageCandidates = function getPackageCandidates(x, start, opts) { - var dirs = nodeModulesPaths(start, opts, x); - for (var i = 0; i < dirs.length; i++) { - dirs[i] = path.join(dirs[i], x); - } - return dirs; -}; - -module.exports = function resolve(x, options, callback) { - var cb = callback; - var opts = options; - if (typeof options === 'function') { - cb = opts; - opts = {}; - } - if (typeof x !== 'string') { - var err = new TypeError('Path must be a string.'); - return process.nextTick(function () { - cb(err); - }); - } - - opts = normalizeOptions(x, opts); - - var isFile = opts.isFile || defaultIsFile; - var isDirectory = opts.isDirectory || defaultIsDir; - var readFile = opts.readFile || fs.readFile; - var realpath = opts.realpath || defaultRealpath; - var readPackage = opts.readPackage || defaultReadPackage; - if (opts.readFile && opts.readPackage) { - var conflictErr = new TypeError('`readFile` and `readPackage` are mutually exclusive.'); - return process.nextTick(function () { - cb(conflictErr); - }); - } - var packageIterator = opts.packageIterator; - - var extensions = opts.extensions || ['.js']; - var includeCoreModules = opts.includeCoreModules !== false; - var basedir = opts.basedir || path.dirname(caller()); - var parent = opts.filename || basedir; - - opts.paths = opts.paths || defaultPaths(); - - // ensure that `basedir` is an absolute path at this point, resolving against the process' current working directory - var absoluteStart = path.resolve(basedir); - - maybeRealpath( - realpath, - absoluteStart, - opts, - function (err, realStart) { - if (err) cb(err); - else init(realStart); - } - ); - - var res; - function init(basedir) { - if ((/^(?:\.\.?(?:\/|$)|\/|([A-Za-z]:)?[/\\])/).test(x)) { - res = path.resolve(basedir, x); - if (x === '.' || x === '..' || x.slice(-1) === '/') res += '/'; - if ((/\/$/).test(x) && res === basedir) { - loadAsDirectory(res, opts.package, onfile); - } else loadAsFile(res, opts.package, onfile); - } else if (includeCoreModules && isCore(x)) { - return cb(null, x); - } else loadNodeModules(x, basedir, function (err, n, pkg) { - if (err) cb(err); - else if (n) { - return maybeRealpath(realpath, n, opts, function (err, realN) { - if (err) { - cb(err); - } else { - cb(null, realN, pkg); - } - }); - } else { - var moduleError = new Error("Cannot find module '" + x + "' from '" + parent + "'"); - moduleError.code = 'MODULE_NOT_FOUND'; - cb(moduleError); - } - }); - } - - function onfile(err, m, pkg) { - if (err) cb(err); - else if (m) cb(null, m, pkg); - else loadAsDirectory(res, function (err, d, pkg) { - if (err) cb(err); - else if (d) { - maybeRealpath(realpath, d, opts, function (err, realD) { - if (err) { - cb(err); - } else { - cb(null, realD, pkg); - } - }); - } else { - var moduleError = new Error("Cannot find module '" + x + "' from '" + parent + "'"); - moduleError.code = 'MODULE_NOT_FOUND'; - cb(moduleError); - } - }); - } - - function loadAsFile(x, thePackage, callback) { - var loadAsFilePackage = thePackage; - var cb = callback; - if (typeof loadAsFilePackage === 'function') { - cb = loadAsFilePackage; - loadAsFilePackage = undefined; - } - - var exts = [''].concat(extensions); - load(exts, x, loadAsFilePackage); - - function load(exts, x, loadPackage) { - if (exts.length === 0) return cb(null, undefined, loadPackage); - var file = x + exts[0]; - - var pkg = loadPackage; - if (pkg) onpkg(null, pkg); - else loadpkg(path.dirname(file), onpkg); - - function onpkg(err, pkg_, dir) { - pkg = pkg_; - if (err) return cb(err); - if (dir && pkg && opts.pathFilter) { - var rfile = path.relative(dir, file); - var rel = rfile.slice(0, rfile.length - exts[0].length); - var r = opts.pathFilter(pkg, x, rel); - if (r) return load( - [''].concat(extensions.slice()), - path.resolve(dir, r), - pkg - ); - } - isFile(file, onex); - } - function onex(err, ex) { - if (err) return cb(err); - if (ex) return cb(null, file, pkg); - load(exts.slice(1), x, pkg); - } - } - } - - function loadpkg(dir, cb) { - if (dir === '' || dir === '/') return cb(null); - if (process.platform === 'win32' && (/^\w:[/\\]*$/).test(dir)) { - return cb(null); - } - if ((/[/\\]node_modules[/\\]*$/).test(dir)) return cb(null); - - maybeRealpath(realpath, dir, opts, function (unwrapErr, pkgdir) { - if (unwrapErr) return loadpkg(path.dirname(dir), cb); - var pkgfile = path.join(pkgdir, 'package.json'); - isFile(pkgfile, function (err, ex) { - // on err, ex is false - if (!ex) return loadpkg(path.dirname(dir), cb); - - readPackage(readFile, pkgfile, function (err, pkgParam) { - if (err) cb(err); - - var pkg = pkgParam; - - if (pkg && opts.packageFilter) { - pkg = opts.packageFilter(pkg, pkgfile); - } - cb(null, pkg, dir); - }); - }); - }); - } - - function loadAsDirectory(x, loadAsDirectoryPackage, callback) { - var cb = callback; - var fpkg = loadAsDirectoryPackage; - if (typeof fpkg === 'function') { - cb = fpkg; - fpkg = opts.package; - } - - maybeRealpath(realpath, x, opts, function (unwrapErr, pkgdir) { - if (unwrapErr) return cb(unwrapErr); - var pkgfile = path.join(pkgdir, 'package.json'); - isFile(pkgfile, function (err, ex) { - if (err) return cb(err); - if (!ex) return loadAsFile(path.join(x, 'index'), fpkg, cb); - - readPackage(readFile, pkgfile, function (err, pkgParam) { - if (err) return cb(err); - - var pkg = pkgParam; - - if (pkg && opts.packageFilter) { - pkg = opts.packageFilter(pkg, pkgfile); - } - - if (pkg && pkg.main) { - if (typeof pkg.main !== 'string') { - var mainError = new TypeError('package “' + pkg.name + '” `main` must be a string'); - mainError.code = 'INVALID_PACKAGE_MAIN'; - return cb(mainError); - } - if (pkg.main === '.' || pkg.main === './') { - pkg.main = 'index'; - } - loadAsFile(path.resolve(x, pkg.main), pkg, function (err, m, pkg) { - if (err) return cb(err); - if (m) return cb(null, m, pkg); - if (!pkg) return loadAsFile(path.join(x, 'index'), pkg, cb); - - var dir = path.resolve(x, pkg.main); - loadAsDirectory(dir, pkg, function (err, n, pkg) { - if (err) return cb(err); - if (n) return cb(null, n, pkg); - loadAsFile(path.join(x, 'index'), pkg, cb); - }); - }); - return; - } - - loadAsFile(path.join(x, '/index'), pkg, cb); - }); - }); - }); - } - - function processDirs(cb, dirs) { - if (dirs.length === 0) return cb(null, undefined); - var dir = dirs[0]; - - isDirectory(path.dirname(dir), isdir); - - function isdir(err, isdir) { - if (err) return cb(err); - if (!isdir) return processDirs(cb, dirs.slice(1)); - loadAsFile(dir, opts.package, onfile); - } - - function onfile(err, m, pkg) { - if (err) return cb(err); - if (m) return cb(null, m, pkg); - loadAsDirectory(dir, opts.package, ondir); - } - - function ondir(err, n, pkg) { - if (err) return cb(err); - if (n) return cb(null, n, pkg); - processDirs(cb, dirs.slice(1)); - } - } - function loadNodeModules(x, start, cb) { - var thunk = function () { return getPackageCandidates(x, start, opts); }; - processDirs( - cb, - packageIterator ? packageIterator(x, start, thunk, opts) : thunk() - ); - } -}; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/caller.js": -/***/ (function(module, exports) { - -module.exports = function () { - // see https://code.google.com/p/v8/wiki/JavaScriptStackTraceApi - var origPrepareStackTrace = Error.prepareStackTrace; - Error.prepareStackTrace = function (_, stack) { return stack; }; - var stack = (new Error()).stack; - Error.prepareStackTrace = origPrepareStackTrace; - return stack[2].getFileName(); -}; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/core.js": -/***/ (function(module, exports, __webpack_require__) { - -var current = (process.versions && process.versions.node && process.versions.node.split('.')) || []; - -function specifierIncluded(specifier) { - var parts = specifier.split(' '); - var op = parts.length > 1 ? parts[0] : '='; - var versionParts = (parts.length > 1 ? parts[1] : parts[0]).split('.'); - - for (var i = 0; i < 3; ++i) { - var cur = parseInt(current[i] || 0, 10); - var ver = parseInt(versionParts[i] || 0, 10); - if (cur === ver) { - continue; // eslint-disable-line no-restricted-syntax, no-continue - } - if (op === '<') { - return cur < ver; - } else if (op === '>=') { - return cur >= ver; - } - return false; - } - return op === '>='; -} - -function matchesRange(range) { - var specifiers = range.split(/ ?&& ?/); - if (specifiers.length === 0) { return false; } - for (var i = 0; i < specifiers.length; ++i) { - if (!specifierIncluded(specifiers[i])) { return false; } - } - return true; -} - -function versionIncluded(specifierValue) { - if (typeof specifierValue === 'boolean') { return specifierValue; } - if (specifierValue && typeof specifierValue === 'object') { - for (var i = 0; i < specifierValue.length; ++i) { - if (matchesRange(specifierValue[i])) { return true; } - } - return false; - } - return matchesRange(specifierValue); -} - -var data = __webpack_require__("../../node_modules/resolve/lib/core.json"); - -var core = {}; -for (var mod in data) { // eslint-disable-line no-restricted-syntax - if (Object.prototype.hasOwnProperty.call(data, mod)) { - core[mod] = versionIncluded(data[mod]); - } -} -module.exports = core; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/core.json": -/***/ (function(module) { - -module.exports = JSON.parse("{\"assert\":true,\"node:assert\":[\">= 14.18 && < 15\",\">= 16\"],\"assert/strict\":\">= 15\",\"node:assert/strict\":\">= 16\",\"async_hooks\":\">= 8\",\"node:async_hooks\":[\">= 14.18 && < 15\",\">= 16\"],\"buffer_ieee754\":\">= 0.5 && < 0.9.7\",\"buffer\":true,\"node:buffer\":[\">= 14.18 && < 15\",\">= 16\"],\"child_process\":true,\"node:child_process\":[\">= 14.18 && < 15\",\">= 16\"],\"cluster\":\">= 0.5\",\"node:cluster\":[\">= 14.18 && < 15\",\">= 16\"],\"console\":true,\"node:console\":[\">= 14.18 && < 15\",\">= 16\"],\"constants\":true,\"node:constants\":[\">= 14.18 && < 15\",\">= 16\"],\"crypto\":true,\"node:crypto\":[\">= 14.18 && < 15\",\">= 16\"],\"_debug_agent\":\">= 1 && < 8\",\"_debugger\":\"< 8\",\"dgram\":true,\"node:dgram\":[\">= 14.18 && < 15\",\">= 16\"],\"diagnostics_channel\":[\">= 14.17 && < 15\",\">= 15.1\"],\"node:diagnostics_channel\":[\">= 14.18 && < 15\",\">= 16\"],\"dns\":true,\"node:dns\":[\">= 14.18 && < 15\",\">= 16\"],\"dns/promises\":\">= 15\",\"node:dns/promises\":\">= 16\",\"domain\":\">= 0.7.12\",\"node:domain\":[\">= 14.18 && < 15\",\">= 16\"],\"events\":true,\"node:events\":[\">= 14.18 && < 15\",\">= 16\"],\"freelist\":\"< 6\",\"fs\":true,\"node:fs\":[\">= 14.18 && < 15\",\">= 16\"],\"fs/promises\":[\">= 10 && < 10.1\",\">= 14\"],\"node:fs/promises\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_agent\":\">= 0.11.1\",\"node:_http_agent\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_client\":\">= 0.11.1\",\"node:_http_client\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_common\":\">= 0.11.1\",\"node:_http_common\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_incoming\":\">= 0.11.1\",\"node:_http_incoming\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_outgoing\":\">= 0.11.1\",\"node:_http_outgoing\":[\">= 14.18 && < 15\",\">= 16\"],\"_http_server\":\">= 0.11.1\",\"node:_http_server\":[\">= 14.18 && < 15\",\">= 16\"],\"http\":true,\"node:http\":[\">= 14.18 && < 15\",\">= 16\"],\"http2\":\">= 8.8\",\"node:http2\":[\">= 14.18 && < 15\",\">= 16\"],\"https\":true,\"node:https\":[\">= 14.18 && < 15\",\">= 16\"],\"inspector\":\">= 8\",\"node:inspector\":[\">= 14.18 && < 15\",\">= 16\"],\"_linklist\":\"< 8\",\"module\":true,\"node:module\":[\">= 14.18 && < 15\",\">= 16\"],\"net\":true,\"node:net\":[\">= 14.18 && < 15\",\">= 16\"],\"node-inspect/lib/_inspect\":\">= 7.6 && < 12\",\"node-inspect/lib/internal/inspect_client\":\">= 7.6 && < 12\",\"node-inspect/lib/internal/inspect_repl\":\">= 7.6 && < 12\",\"os\":true,\"node:os\":[\">= 14.18 && < 15\",\">= 16\"],\"path\":true,\"node:path\":[\">= 14.18 && < 15\",\">= 16\"],\"path/posix\":\">= 15.3\",\"node:path/posix\":\">= 16\",\"path/win32\":\">= 15.3\",\"node:path/win32\":\">= 16\",\"perf_hooks\":\">= 8.5\",\"node:perf_hooks\":[\">= 14.18 && < 15\",\">= 16\"],\"process\":\">= 1\",\"node:process\":[\">= 14.18 && < 15\",\">= 16\"],\"punycode\":\">= 0.5\",\"node:punycode\":[\">= 14.18 && < 15\",\">= 16\"],\"querystring\":true,\"node:querystring\":[\">= 14.18 && < 15\",\">= 16\"],\"readline\":true,\"node:readline\":[\">= 14.18 && < 15\",\">= 16\"],\"readline/promises\":\">= 17\",\"node:readline/promises\":\">= 17\",\"repl\":true,\"node:repl\":[\">= 14.18 && < 15\",\">= 16\"],\"smalloc\":\">= 0.11.5 && < 3\",\"_stream_duplex\":\">= 0.9.4\",\"node:_stream_duplex\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_transform\":\">= 0.9.4\",\"node:_stream_transform\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_wrap\":\">= 1.4.1\",\"node:_stream_wrap\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_passthrough\":\">= 0.9.4\",\"node:_stream_passthrough\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_readable\":\">= 0.9.4\",\"node:_stream_readable\":[\">= 14.18 && < 15\",\">= 16\"],\"_stream_writable\":\">= 0.9.4\",\"node:_stream_writable\":[\">= 14.18 && < 15\",\">= 16\"],\"stream\":true,\"node:stream\":[\">= 14.18 && < 15\",\">= 16\"],\"stream/consumers\":\">= 16.7\",\"node:stream/consumers\":\">= 16.7\",\"stream/promises\":\">= 15\",\"node:stream/promises\":\">= 16\",\"stream/web\":\">= 16.5\",\"node:stream/web\":\">= 16.5\",\"string_decoder\":true,\"node:string_decoder\":[\">= 14.18 && < 15\",\">= 16\"],\"sys\":[\">= 0.4 && < 0.7\",\">= 0.8\"],\"node:sys\":[\">= 14.18 && < 15\",\">= 16\"],\"timers\":true,\"node:timers\":[\">= 14.18 && < 15\",\">= 16\"],\"timers/promises\":\">= 15\",\"node:timers/promises\":\">= 16\",\"_tls_common\":\">= 0.11.13\",\"node:_tls_common\":[\">= 14.18 && < 15\",\">= 16\"],\"_tls_legacy\":\">= 0.11.3 && < 10\",\"_tls_wrap\":\">= 0.11.3\",\"node:_tls_wrap\":[\">= 14.18 && < 15\",\">= 16\"],\"tls\":true,\"node:tls\":[\">= 14.18 && < 15\",\">= 16\"],\"trace_events\":\">= 10\",\"node:trace_events\":[\">= 14.18 && < 15\",\">= 16\"],\"tty\":true,\"node:tty\":[\">= 14.18 && < 15\",\">= 16\"],\"url\":true,\"node:url\":[\">= 14.18 && < 15\",\">= 16\"],\"util\":true,\"node:util\":[\">= 14.18 && < 15\",\">= 16\"],\"util/types\":\">= 15.3\",\"node:util/types\":\">= 16\",\"v8/tools/arguments\":\">= 10 && < 12\",\"v8/tools/codemap\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/consarray\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/csvparser\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/logreader\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/profile_view\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8/tools/splaytree\":[\">= 4.4 && < 5\",\">= 5.2 && < 12\"],\"v8\":\">= 1\",\"node:v8\":[\">= 14.18 && < 15\",\">= 16\"],\"vm\":true,\"node:vm\":[\">= 14.18 && < 15\",\">= 16\"],\"wasi\":\">= 13.4 && < 13.5\",\"worker_threads\":\">= 11.7\",\"node:worker_threads\":[\">= 14.18 && < 15\",\">= 16\"],\"zlib\":\">= 0.5\",\"node:zlib\":[\">= 14.18 && < 15\",\">= 16\"]}"); - -/***/ }), - -/***/ "../../node_modules/resolve/lib/homedir.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var os = __webpack_require__("os"); - -// adapted from https://github.com/sindresorhus/os-homedir/blob/11e089f4754db38bb535e5a8416320c4446e8cfd/index.js - -module.exports = os.homedir || function homedir() { - var home = process.env.HOME; - var user = process.env.LOGNAME || process.env.USER || process.env.LNAME || process.env.USERNAME; - - if (process.platform === 'win32') { - return process.env.USERPROFILE || process.env.HOMEDRIVE + process.env.HOMEPATH || home || null; - } - - if (process.platform === 'darwin') { - return home || (user ? '/Users/' + user : null); - } - - if (process.platform === 'linux') { - return home || (process.getuid() === 0 ? '/root' : (user ? '/home/' + user : null)); // eslint-disable-line no-extra-parens - } - - return home || null; -}; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/is-core.js": -/***/ (function(module, exports, __webpack_require__) { - -var isCoreModule = __webpack_require__("../../node_modules/is-core-module/index.js"); - -module.exports = function isCore(x) { - return isCoreModule(x); -}; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/node-modules-paths.js": -/***/ (function(module, exports, __webpack_require__) { - -var path = __webpack_require__("path"); -var parse = path.parse || __webpack_require__("../../node_modules/path-parse/index.js"); // eslint-disable-line global-require - -var getNodeModulesDirs = function getNodeModulesDirs(absoluteStart, modules) { - var prefix = '/'; - if ((/^([A-Za-z]:)/).test(absoluteStart)) { - prefix = ''; - } else if ((/^\\\\/).test(absoluteStart)) { - prefix = '\\\\'; - } - - var paths = [absoluteStart]; - var parsed = parse(absoluteStart); - while (parsed.dir !== paths[paths.length - 1]) { - paths.push(parsed.dir); - parsed = parse(parsed.dir); - } - - return paths.reduce(function (dirs, aPath) { - return dirs.concat(modules.map(function (moduleDir) { - return path.resolve(prefix, aPath, moduleDir); - })); - }, []); -}; - -module.exports = function nodeModulesPaths(start, opts, request) { - var modules = opts && opts.moduleDirectory - ? [].concat(opts.moduleDirectory) - : ['node_modules']; - - if (opts && typeof opts.paths === 'function') { - return opts.paths( - request, - start, - function () { return getNodeModulesDirs(start, modules); }, - opts - ); - } - - var dirs = getNodeModulesDirs(start, modules); - return opts && opts.paths ? dirs.concat(opts.paths) : dirs; -}; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/normalize-options.js": -/***/ (function(module, exports) { - -module.exports = function (x, opts) { - /** - * This file is purposefully a passthrough. It's expected that third-party - * environments will override it at runtime in order to inject special logic - * into `resolve` (by manipulating the options). One such example is the PnP - * code path in Yarn. - */ - - return opts || {}; -}; - - -/***/ }), - -/***/ "../../node_modules/resolve/lib/sync.js": -/***/ (function(module, exports, __webpack_require__) { - -var isCore = __webpack_require__("../../node_modules/is-core-module/index.js"); -var fs = __webpack_require__("fs"); -var path = __webpack_require__("path"); -var getHomedir = __webpack_require__("../../node_modules/resolve/lib/homedir.js"); -var caller = __webpack_require__("../../node_modules/resolve/lib/caller.js"); -var nodeModulesPaths = __webpack_require__("../../node_modules/resolve/lib/node-modules-paths.js"); -var normalizeOptions = __webpack_require__("../../node_modules/resolve/lib/normalize-options.js"); - -var realpathFS = fs.realpathSync && typeof fs.realpathSync.native === 'function' ? fs.realpathSync.native : fs.realpathSync; - -var homedir = getHomedir(); -var defaultPaths = function () { - return [ - path.join(homedir, '.node_modules'), - path.join(homedir, '.node_libraries') - ]; -}; - -var defaultIsFile = function isFile(file) { - try { - var stat = fs.statSync(file, { throwIfNoEntry: false }); - } catch (e) { - if (e && (e.code === 'ENOENT' || e.code === 'ENOTDIR')) return false; - throw e; - } - return !!stat && (stat.isFile() || stat.isFIFO()); -}; - -var defaultIsDir = function isDirectory(dir) { - try { - var stat = fs.statSync(dir, { throwIfNoEntry: false }); - } catch (e) { - if (e && (e.code === 'ENOENT' || e.code === 'ENOTDIR')) return false; - throw e; - } - return !!stat && stat.isDirectory(); -}; - -var defaultRealpathSync = function realpathSync(x) { - try { - return realpathFS(x); - } catch (realpathErr) { - if (realpathErr.code !== 'ENOENT') { - throw realpathErr; - } - } - return x; -}; - -var maybeRealpathSync = function maybeRealpathSync(realpathSync, x, opts) { - if (opts && opts.preserveSymlinks === false) { - return realpathSync(x); - } - return x; -}; - -var defaultReadPackageSync = function defaultReadPackageSync(readFileSync, pkgfile) { - var body = readFileSync(pkgfile); - try { - var pkg = JSON.parse(body); - return pkg; - } catch (jsonErr) {} -}; - -var getPackageCandidates = function getPackageCandidates(x, start, opts) { - var dirs = nodeModulesPaths(start, opts, x); - for (var i = 0; i < dirs.length; i++) { - dirs[i] = path.join(dirs[i], x); - } - return dirs; -}; - -module.exports = function resolveSync(x, options) { - if (typeof x !== 'string') { - throw new TypeError('Path must be a string.'); - } - var opts = normalizeOptions(x, options); - - var isFile = opts.isFile || defaultIsFile; - var readFileSync = opts.readFileSync || fs.readFileSync; - var isDirectory = opts.isDirectory || defaultIsDir; - var realpathSync = opts.realpathSync || defaultRealpathSync; - var readPackageSync = opts.readPackageSync || defaultReadPackageSync; - if (opts.readFileSync && opts.readPackageSync) { - throw new TypeError('`readFileSync` and `readPackageSync` are mutually exclusive.'); - } - var packageIterator = opts.packageIterator; - - var extensions = opts.extensions || ['.js']; - var includeCoreModules = opts.includeCoreModules !== false; - var basedir = opts.basedir || path.dirname(caller()); - var parent = opts.filename || basedir; - - opts.paths = opts.paths || defaultPaths(); - - // ensure that `basedir` is an absolute path at this point, resolving against the process' current working directory - var absoluteStart = maybeRealpathSync(realpathSync, path.resolve(basedir), opts); - - if ((/^(?:\.\.?(?:\/|$)|\/|([A-Za-z]:)?[/\\])/).test(x)) { - var res = path.resolve(absoluteStart, x); - if (x === '.' || x === '..' || x.slice(-1) === '/') res += '/'; - var m = loadAsFileSync(res) || loadAsDirectorySync(res); - if (m) return maybeRealpathSync(realpathSync, m, opts); - } else if (includeCoreModules && isCore(x)) { - return x; - } else { - var n = loadNodeModulesSync(x, absoluteStart); - if (n) return maybeRealpathSync(realpathSync, n, opts); - } - - var err = new Error("Cannot find module '" + x + "' from '" + parent + "'"); - err.code = 'MODULE_NOT_FOUND'; - throw err; - - function loadAsFileSync(x) { - var pkg = loadpkg(path.dirname(x)); - - if (pkg && pkg.dir && pkg.pkg && opts.pathFilter) { - var rfile = path.relative(pkg.dir, x); - var r = opts.pathFilter(pkg.pkg, x, rfile); - if (r) { - x = path.resolve(pkg.dir, r); // eslint-disable-line no-param-reassign - } - } - - if (isFile(x)) { - return x; - } - - for (var i = 0; i < extensions.length; i++) { - var file = x + extensions[i]; - if (isFile(file)) { - return file; - } - } - } - - function loadpkg(dir) { - if (dir === '' || dir === '/') return; - if (process.platform === 'win32' && (/^\w:[/\\]*$/).test(dir)) { - return; - } - if ((/[/\\]node_modules[/\\]*$/).test(dir)) return; - - var pkgfile = path.join(maybeRealpathSync(realpathSync, dir, opts), 'package.json'); - - if (!isFile(pkgfile)) { - return loadpkg(path.dirname(dir)); - } - - var pkg = readPackageSync(readFileSync, pkgfile); - - if (pkg && opts.packageFilter) { - // v2 will pass pkgfile - pkg = opts.packageFilter(pkg, /*pkgfile,*/ dir); // eslint-disable-line spaced-comment - } - - return { pkg: pkg, dir: dir }; - } - - function loadAsDirectorySync(x) { - var pkgfile = path.join(maybeRealpathSync(realpathSync, x, opts), '/package.json'); - if (isFile(pkgfile)) { - try { - var pkg = readPackageSync(readFileSync, pkgfile); - } catch (e) {} - - if (pkg && opts.packageFilter) { - // v2 will pass pkgfile - pkg = opts.packageFilter(pkg, /*pkgfile,*/ x); // eslint-disable-line spaced-comment - } - - if (pkg && pkg.main) { - if (typeof pkg.main !== 'string') { - var mainError = new TypeError('package “' + pkg.name + '” `main` must be a string'); - mainError.code = 'INVALID_PACKAGE_MAIN'; - throw mainError; - } - if (pkg.main === '.' || pkg.main === './') { - pkg.main = 'index'; - } - try { - var m = loadAsFileSync(path.resolve(x, pkg.main)); - if (m) return m; - var n = loadAsDirectorySync(path.resolve(x, pkg.main)); - if (n) return n; - } catch (e) {} - } - } - - return loadAsFileSync(path.join(x, '/index')); - } - - function loadNodeModulesSync(x, start) { - var thunk = function () { return getPackageCandidates(x, start, opts); }; - var dirs = packageIterator ? packageIterator(x, start, thunk, opts) : thunk(); - - for (var i = 0; i < dirs.length; i++) { - var dir = dirs[i]; - if (isDirectory(path.dirname(dir))) { - var m = loadAsFileSync(dir); - if (m) return m; - var n = loadAsDirectorySync(dir); - if (n) return n; - } - } - } -}; - - -/***/ }), - -/***/ "../../node_modules/restore-cursor/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const onetime = __webpack_require__("../../node_modules/onetime/index.js"); -const signalExit = __webpack_require__("../../node_modules/signal-exit/index.js"); - -module.exports = onetime(() => { - signalExit(() => { - process.stderr.write('\u001B[?25h'); - }, {alwaysLast: true}); -}); - - -/***/ }), - -/***/ "../../node_modules/reusify/reusify.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -function reusify (Constructor) { - var head = new Constructor() - var tail = head - - function get () { - var current = head - - if (current.next) { - head = current.next - } else { - head = new Constructor() - tail = head - } - - current.next = null - - return current - } - - function release (obj) { - tail.next = obj - tail = obj - } - - return { - get: get, - release: release - } -} - -module.exports = reusify - - -/***/ }), - -/***/ "../../node_modules/rimraf/rimraf.js": -/***/ (function(module, exports, __webpack_require__) { - -const assert = __webpack_require__("assert") -const path = __webpack_require__("path") -const fs = __webpack_require__("fs") -let glob = undefined -try { - glob = __webpack_require__("../../node_modules/glob/glob.js") -} catch (_err) { - // treat glob as optional. -} - -const defaultGlobOpts = { - nosort: true, - silent: true -} - -// for EMFILE handling -let timeout = 0 - -const isWindows = (process.platform === "win32") - -const defaults = options => { - const methods = [ - 'unlink', - 'chmod', - 'stat', - 'lstat', - 'rmdir', - 'readdir' - ] - methods.forEach(m => { - options[m] = options[m] || fs[m] - m = m + 'Sync' - options[m] = options[m] || fs[m] - }) - - options.maxBusyTries = options.maxBusyTries || 3 - options.emfileWait = options.emfileWait || 1000 - if (options.glob === false) { - options.disableGlob = true - } - if (options.disableGlob !== true && glob === undefined) { - throw Error('glob dependency not found, set `options.disableGlob = true` if intentional') - } - options.disableGlob = options.disableGlob || false - options.glob = options.glob || defaultGlobOpts -} - -const rimraf = (p, options, cb) => { - if (typeof options === 'function') { - cb = options - options = {} - } - - assert(p, 'rimraf: missing path') - assert.equal(typeof p, 'string', 'rimraf: path should be a string') - assert.equal(typeof cb, 'function', 'rimraf: callback function required') - assert(options, 'rimraf: invalid options argument provided') - assert.equal(typeof options, 'object', 'rimraf: options should be object') - - defaults(options) - - let busyTries = 0 - let errState = null - let n = 0 - - const next = (er) => { - errState = errState || er - if (--n === 0) - cb(errState) - } - - const afterGlob = (er, results) => { - if (er) - return cb(er) - - n = results.length - if (n === 0) - return cb() - - results.forEach(p => { - const CB = (er) => { - if (er) { - if ((er.code === "EBUSY" || er.code === "ENOTEMPTY" || er.code === "EPERM") && - busyTries < options.maxBusyTries) { - busyTries ++ - // try again, with the same exact callback as this one. - return setTimeout(() => rimraf_(p, options, CB), busyTries * 100) - } - - // this one won't happen if graceful-fs is used. - if (er.code === "EMFILE" && timeout < options.emfileWait) { - return setTimeout(() => rimraf_(p, options, CB), timeout ++) - } - - // already gone - if (er.code === "ENOENT") er = null - } - - timeout = 0 - next(er) - } - rimraf_(p, options, CB) - }) - } - - if (options.disableGlob || !glob.hasMagic(p)) - return afterGlob(null, [p]) - - options.lstat(p, (er, stat) => { - if (!er) - return afterGlob(null, [p]) - - glob(p, options.glob, afterGlob) - }) - -} - -// Two possible strategies. -// 1. Assume it's a file. unlink it, then do the dir stuff on EPERM or EISDIR -// 2. Assume it's a directory. readdir, then do the file stuff on ENOTDIR -// -// Both result in an extra syscall when you guess wrong. However, there -// are likely far more normal files in the world than directories. This -// is based on the assumption that a the average number of files per -// directory is >= 1. -// -// If anyone ever complains about this, then I guess the strategy could -// be made configurable somehow. But until then, YAGNI. -const rimraf_ = (p, options, cb) => { - assert(p) - assert(options) - assert(typeof cb === 'function') - - // sunos lets the root user unlink directories, which is... weird. - // so we have to lstat here and make sure it's not a dir. - options.lstat(p, (er, st) => { - if (er && er.code === "ENOENT") - return cb(null) - - // Windows can EPERM on stat. Life is suffering. - if (er && er.code === "EPERM" && isWindows) - fixWinEPERM(p, options, er, cb) - - if (st && st.isDirectory()) - return rmdir(p, options, er, cb) - - options.unlink(p, er => { - if (er) { - if (er.code === "ENOENT") - return cb(null) - if (er.code === "EPERM") - return (isWindows) - ? fixWinEPERM(p, options, er, cb) - : rmdir(p, options, er, cb) - if (er.code === "EISDIR") - return rmdir(p, options, er, cb) - } - return cb(er) - }) - }) -} - -const fixWinEPERM = (p, options, er, cb) => { - assert(p) - assert(options) - assert(typeof cb === 'function') - - options.chmod(p, 0o666, er2 => { - if (er2) - cb(er2.code === "ENOENT" ? null : er) - else - options.stat(p, (er3, stats) => { - if (er3) - cb(er3.code === "ENOENT" ? null : er) - else if (stats.isDirectory()) - rmdir(p, options, er, cb) - else - options.unlink(p, cb) - }) - }) -} - -const fixWinEPERMSync = (p, options, er) => { - assert(p) - assert(options) - - try { - options.chmodSync(p, 0o666) - } catch (er2) { - if (er2.code === "ENOENT") - return - else - throw er - } - - let stats - try { - stats = options.statSync(p) - } catch (er3) { - if (er3.code === "ENOENT") - return - else - throw er - } - - if (stats.isDirectory()) - rmdirSync(p, options, er) - else - options.unlinkSync(p) -} - -const rmdir = (p, options, originalEr, cb) => { - assert(p) - assert(options) - assert(typeof cb === 'function') - - // try to rmdir first, and only readdir on ENOTEMPTY or EEXIST (SunOS) - // if we guessed wrong, and it's not a directory, then - // raise the original error. - options.rmdir(p, er => { - if (er && (er.code === "ENOTEMPTY" || er.code === "EEXIST" || er.code === "EPERM")) - rmkids(p, options, cb) - else if (er && er.code === "ENOTDIR") - cb(originalEr) - else - cb(er) - }) -} - -const rmkids = (p, options, cb) => { - assert(p) - assert(options) - assert(typeof cb === 'function') - - options.readdir(p, (er, files) => { - if (er) - return cb(er) - let n = files.length - if (n === 0) - return options.rmdir(p, cb) - let errState - files.forEach(f => { - rimraf(path.join(p, f), options, er => { - if (errState) - return - if (er) - return cb(errState = er) - if (--n === 0) - options.rmdir(p, cb) - }) - }) - }) -} - -// this looks simpler, and is strictly *faster*, but will -// tie up the JavaScript thread and fail on excessively -// deep directory trees. -const rimrafSync = (p, options) => { - options = options || {} - defaults(options) - - assert(p, 'rimraf: missing path') - assert.equal(typeof p, 'string', 'rimraf: path should be a string') - assert(options, 'rimraf: missing options') - assert.equal(typeof options, 'object', 'rimraf: options should be object') - - let results - - if (options.disableGlob || !glob.hasMagic(p)) { - results = [p] - } else { - try { - options.lstatSync(p) - results = [p] - } catch (er) { - results = glob.sync(p, options.glob) - } - } - - if (!results.length) - return - - for (let i = 0; i < results.length; i++) { - const p = results[i] - - let st - try { - st = options.lstatSync(p) - } catch (er) { - if (er.code === "ENOENT") - return - - // Windows can EPERM on stat. Life is suffering. - if (er.code === "EPERM" && isWindows) - fixWinEPERMSync(p, options, er) - } - - try { - // sunos lets the root user unlink directories, which is... weird. - if (st && st.isDirectory()) - rmdirSync(p, options, null) - else - options.unlinkSync(p) - } catch (er) { - if (er.code === "ENOENT") - return - if (er.code === "EPERM") - return isWindows ? fixWinEPERMSync(p, options, er) : rmdirSync(p, options, er) - if (er.code !== "EISDIR") - throw er - - rmdirSync(p, options, er) - } - } -} - -const rmdirSync = (p, options, originalEr) => { - assert(p) - assert(options) - - try { - options.rmdirSync(p) - } catch (er) { - if (er.code === "ENOENT") - return - if (er.code === "ENOTDIR") - throw originalEr - if (er.code === "ENOTEMPTY" || er.code === "EEXIST" || er.code === "EPERM") - rmkidsSync(p, options) - } -} - -const rmkidsSync = (p, options) => { - assert(p) - assert(options) - options.readdirSync(p).forEach(f => rimrafSync(path.join(p, f), options)) - - // We only end up here once we got ENOTEMPTY at least once, and - // at this point, we are guaranteed to have removed all the kids. - // So, we know that it won't be ENOENT or ENOTDIR or anything else. - // try really hard to delete stuff on windows, because it has a - // PROFOUNDLY annoying habit of not closing handles promptly when - // files are deleted, resulting in spurious ENOTEMPTY errors. - const retries = isWindows ? 100 : 1 - let i = 0 - do { - let threw = true - try { - const ret = options.rmdirSync(p, options) - threw = false - return ret - } finally { - if (++i < retries && threw) - continue - } - } while (true) -} - -module.exports = rimraf -rimraf.sync = rimrafSync - - -/***/ }), - -/***/ "../../node_modules/run-parallel/index.js": -/***/ (function(module, exports) { - -module.exports = runParallel - -function runParallel (tasks, cb) { - var results, pending, keys - var isSync = true - - if (Array.isArray(tasks)) { - results = [] - pending = tasks.length - } else { - keys = Object.keys(tasks) - results = {} - pending = keys.length - } - - function done (err) { - function end () { - if (cb) cb(err, results) - cb = null - } - if (isSync) process.nextTick(end) - else end() - } - - function each (i, err, result) { - results[i] = result - if (--pending === 0 || err) { - done(err) - } - } - - if (!pending) { - // empty - done(null) - } else if (keys) { - // object - keys.forEach(function (key) { - tasks[key](function (err, result) { each(key, err, result) }) - }) - } else { - // array - tasks.forEach(function (task, i) { - task(function (err, result) { each(i, err, result) }) - }) - } - - isSync = false -} - - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/index.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -__webpack_require__.r(__webpack_exports__); -/* harmony import */ var _internal_Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "Observable", function() { return _internal_Observable__WEBPACK_IMPORTED_MODULE_0__["a"]; }); - -/* harmony import */ var _internal_observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/ConnectableObservable.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "ConnectableObservable", function() { return _internal_observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_1__["a"]; }); - -/* harmony import */ var _internal_symbol_observable__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/symbol/observable.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "observable", function() { return _internal_symbol_observable__WEBPACK_IMPORTED_MODULE_2__["a"]; }); - -/* harmony import */ var _internal_observable_dom_animationFrames__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/dom/animationFrames.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "animationFrames", function() { return _internal_observable_dom_animationFrames__WEBPACK_IMPORTED_MODULE_3__["a"]; }); - -/* harmony import */ var _internal_Subject__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "Subject", function() { return _internal_Subject__WEBPACK_IMPORTED_MODULE_4__["a"]; }); - -/* harmony import */ var _internal_BehaviorSubject__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/BehaviorSubject.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "BehaviorSubject", function() { return _internal_BehaviorSubject__WEBPACK_IMPORTED_MODULE_5__["a"]; }); - -/* harmony import */ var _internal_ReplaySubject__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/ReplaySubject.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "ReplaySubject", function() { return _internal_ReplaySubject__WEBPACK_IMPORTED_MODULE_6__["a"]; }); - -/* harmony import */ var _internal_AsyncSubject__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/AsyncSubject.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "AsyncSubject", function() { return _internal_AsyncSubject__WEBPACK_IMPORTED_MODULE_7__["a"]; }); - -/* harmony import */ var _internal_scheduler_asap__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/asap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "asap", function() { return _internal_scheduler_asap__WEBPACK_IMPORTED_MODULE_8__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "asapScheduler", function() { return _internal_scheduler_asap__WEBPACK_IMPORTED_MODULE_8__["b"]; }); - -/* harmony import */ var _internal_scheduler_async__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "async", function() { return _internal_scheduler_async__WEBPACK_IMPORTED_MODULE_9__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "asyncScheduler", function() { return _internal_scheduler_async__WEBPACK_IMPORTED_MODULE_9__["b"]; }); - -/* harmony import */ var _internal_scheduler_queue__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/queue.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "queue", function() { return _internal_scheduler_queue__WEBPACK_IMPORTED_MODULE_10__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "queueScheduler", function() { return _internal_scheduler_queue__WEBPACK_IMPORTED_MODULE_10__["b"]; }); - -/* harmony import */ var _internal_scheduler_animationFrame__WEBPACK_IMPORTED_MODULE_11__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/animationFrame.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "animationFrame", function() { return _internal_scheduler_animationFrame__WEBPACK_IMPORTED_MODULE_11__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "animationFrameScheduler", function() { return _internal_scheduler_animationFrame__WEBPACK_IMPORTED_MODULE_11__["b"]; }); - -/* harmony import */ var _internal_scheduler_VirtualTimeScheduler__WEBPACK_IMPORTED_MODULE_12__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/VirtualTimeScheduler.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "VirtualTimeScheduler", function() { return _internal_scheduler_VirtualTimeScheduler__WEBPACK_IMPORTED_MODULE_12__["b"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "VirtualAction", function() { return _internal_scheduler_VirtualTimeScheduler__WEBPACK_IMPORTED_MODULE_12__["a"]; }); - -/* harmony import */ var _internal_Scheduler__WEBPACK_IMPORTED_MODULE_13__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Scheduler.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "Scheduler", function() { return _internal_Scheduler__WEBPACK_IMPORTED_MODULE_13__["a"]; }); - -/* harmony import */ var _internal_Subscription__WEBPACK_IMPORTED_MODULE_14__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "Subscription", function() { return _internal_Subscription__WEBPACK_IMPORTED_MODULE_14__["b"]; }); - -/* harmony import */ var _internal_Subscriber__WEBPACK_IMPORTED_MODULE_15__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscriber.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "Subscriber", function() { return _internal_Subscriber__WEBPACK_IMPORTED_MODULE_15__["b"]; }); - -/* harmony import */ var _internal_Notification__WEBPACK_IMPORTED_MODULE_16__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Notification.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "Notification", function() { return _internal_Notification__WEBPACK_IMPORTED_MODULE_16__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "NotificationKind", function() { return _internal_Notification__WEBPACK_IMPORTED_MODULE_16__["b"]; }); - -/* harmony import */ var _internal_util_pipe__WEBPACK_IMPORTED_MODULE_17__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/pipe.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "pipe", function() { return _internal_util_pipe__WEBPACK_IMPORTED_MODULE_17__["a"]; }); - -/* harmony import */ var _internal_util_noop__WEBPACK_IMPORTED_MODULE_18__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "noop", function() { return _internal_util_noop__WEBPACK_IMPORTED_MODULE_18__["a"]; }); - -/* harmony import */ var _internal_util_identity__WEBPACK_IMPORTED_MODULE_19__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "identity", function() { return _internal_util_identity__WEBPACK_IMPORTED_MODULE_19__["a"]; }); - -/* harmony import */ var _internal_util_isObservable__WEBPACK_IMPORTED_MODULE_20__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isObservable.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "isObservable", function() { return _internal_util_isObservable__WEBPACK_IMPORTED_MODULE_20__["a"]; }); - -/* harmony import */ var _internal_lastValueFrom__WEBPACK_IMPORTED_MODULE_21__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/lastValueFrom.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "lastValueFrom", function() { return _internal_lastValueFrom__WEBPACK_IMPORTED_MODULE_21__["a"]; }); - -/* harmony import */ var _internal_firstValueFrom__WEBPACK_IMPORTED_MODULE_22__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/firstValueFrom.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "firstValueFrom", function() { return _internal_firstValueFrom__WEBPACK_IMPORTED_MODULE_22__["a"]; }); - -/* harmony import */ var _internal_util_ArgumentOutOfRangeError__WEBPACK_IMPORTED_MODULE_23__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/ArgumentOutOfRangeError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "ArgumentOutOfRangeError", function() { return _internal_util_ArgumentOutOfRangeError__WEBPACK_IMPORTED_MODULE_23__["a"]; }); - -/* harmony import */ var _internal_util_EmptyError__WEBPACK_IMPORTED_MODULE_24__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "EmptyError", function() { return _internal_util_EmptyError__WEBPACK_IMPORTED_MODULE_24__["a"]; }); - -/* harmony import */ var _internal_util_NotFoundError__WEBPACK_IMPORTED_MODULE_25__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/NotFoundError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "NotFoundError", function() { return _internal_util_NotFoundError__WEBPACK_IMPORTED_MODULE_25__["a"]; }); - -/* harmony import */ var _internal_util_ObjectUnsubscribedError__WEBPACK_IMPORTED_MODULE_26__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/ObjectUnsubscribedError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "ObjectUnsubscribedError", function() { return _internal_util_ObjectUnsubscribedError__WEBPACK_IMPORTED_MODULE_26__["a"]; }); - -/* harmony import */ var _internal_util_SequenceError__WEBPACK_IMPORTED_MODULE_27__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/SequenceError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "SequenceError", function() { return _internal_util_SequenceError__WEBPACK_IMPORTED_MODULE_27__["a"]; }); - -/* harmony import */ var _internal_operators_timeout__WEBPACK_IMPORTED_MODULE_28__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timeout.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "TimeoutError", function() { return _internal_operators_timeout__WEBPACK_IMPORTED_MODULE_28__["a"]; }); - -/* harmony import */ var _internal_util_UnsubscriptionError__WEBPACK_IMPORTED_MODULE_29__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/UnsubscriptionError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "UnsubscriptionError", function() { return _internal_util_UnsubscriptionError__WEBPACK_IMPORTED_MODULE_29__["a"]; }); - -/* harmony import */ var _internal_observable_bindCallback__WEBPACK_IMPORTED_MODULE_30__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/bindCallback.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bindCallback", function() { return _internal_observable_bindCallback__WEBPACK_IMPORTED_MODULE_30__["a"]; }); - -/* harmony import */ var _internal_observable_bindNodeCallback__WEBPACK_IMPORTED_MODULE_31__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/bindNodeCallback.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bindNodeCallback", function() { return _internal_observable_bindNodeCallback__WEBPACK_IMPORTED_MODULE_31__["a"]; }); - -/* harmony import */ var _internal_observable_combineLatest__WEBPACK_IMPORTED_MODULE_32__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/combineLatest.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineLatest", function() { return _internal_observable_combineLatest__WEBPACK_IMPORTED_MODULE_32__["a"]; }); - -/* harmony import */ var _internal_observable_concat__WEBPACK_IMPORTED_MODULE_33__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/concat.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concat", function() { return _internal_observable_concat__WEBPACK_IMPORTED_MODULE_33__["a"]; }); - -/* harmony import */ var _internal_observable_connectable__WEBPACK_IMPORTED_MODULE_34__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/connectable.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "connectable", function() { return _internal_observable_connectable__WEBPACK_IMPORTED_MODULE_34__["a"]; }); - -/* harmony import */ var _internal_observable_defer__WEBPACK_IMPORTED_MODULE_35__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/defer.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "defer", function() { return _internal_observable_defer__WEBPACK_IMPORTED_MODULE_35__["a"]; }); - -/* harmony import */ var _internal_observable_empty__WEBPACK_IMPORTED_MODULE_36__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "empty", function() { return _internal_observable_empty__WEBPACK_IMPORTED_MODULE_36__["b"]; }); - -/* harmony import */ var _internal_observable_forkJoin__WEBPACK_IMPORTED_MODULE_37__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/forkJoin.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "forkJoin", function() { return _internal_observable_forkJoin__WEBPACK_IMPORTED_MODULE_37__["a"]; }); - -/* harmony import */ var _internal_observable_from__WEBPACK_IMPORTED_MODULE_38__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "from", function() { return _internal_observable_from__WEBPACK_IMPORTED_MODULE_38__["a"]; }); - -/* harmony import */ var _internal_observable_fromEvent__WEBPACK_IMPORTED_MODULE_39__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/fromEvent.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "fromEvent", function() { return _internal_observable_fromEvent__WEBPACK_IMPORTED_MODULE_39__["a"]; }); - -/* harmony import */ var _internal_observable_fromEventPattern__WEBPACK_IMPORTED_MODULE_40__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/fromEventPattern.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "fromEventPattern", function() { return _internal_observable_fromEventPattern__WEBPACK_IMPORTED_MODULE_40__["a"]; }); - -/* harmony import */ var _internal_observable_generate__WEBPACK_IMPORTED_MODULE_41__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/generate.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "generate", function() { return _internal_observable_generate__WEBPACK_IMPORTED_MODULE_41__["a"]; }); - -/* harmony import */ var _internal_observable_iif__WEBPACK_IMPORTED_MODULE_42__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/iif.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "iif", function() { return _internal_observable_iif__WEBPACK_IMPORTED_MODULE_42__["a"]; }); - -/* harmony import */ var _internal_observable_interval__WEBPACK_IMPORTED_MODULE_43__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/interval.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "interval", function() { return _internal_observable_interval__WEBPACK_IMPORTED_MODULE_43__["a"]; }); - -/* harmony import */ var _internal_observable_merge__WEBPACK_IMPORTED_MODULE_44__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/merge.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "merge", function() { return _internal_observable_merge__WEBPACK_IMPORTED_MODULE_44__["a"]; }); - -/* harmony import */ var _internal_observable_never__WEBPACK_IMPORTED_MODULE_45__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/never.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "never", function() { return _internal_observable_never__WEBPACK_IMPORTED_MODULE_45__["b"]; }); - -/* harmony import */ var _internal_observable_of__WEBPACK_IMPORTED_MODULE_46__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/of.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "of", function() { return _internal_observable_of__WEBPACK_IMPORTED_MODULE_46__["a"]; }); - -/* harmony import */ var _internal_observable_onErrorResumeNext__WEBPACK_IMPORTED_MODULE_47__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/onErrorResumeNext.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "onErrorResumeNext", function() { return _internal_observable_onErrorResumeNext__WEBPACK_IMPORTED_MODULE_47__["a"]; }); - -/* harmony import */ var _internal_observable_pairs__WEBPACK_IMPORTED_MODULE_48__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/pairs.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "pairs", function() { return _internal_observable_pairs__WEBPACK_IMPORTED_MODULE_48__["a"]; }); - -/* harmony import */ var _internal_observable_partition__WEBPACK_IMPORTED_MODULE_49__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/partition.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "partition", function() { return _internal_observable_partition__WEBPACK_IMPORTED_MODULE_49__["a"]; }); - -/* harmony import */ var _internal_observable_race__WEBPACK_IMPORTED_MODULE_50__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/race.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "race", function() { return _internal_observable_race__WEBPACK_IMPORTED_MODULE_50__["a"]; }); - -/* harmony import */ var _internal_observable_range__WEBPACK_IMPORTED_MODULE_51__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/range.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "range", function() { return _internal_observable_range__WEBPACK_IMPORTED_MODULE_51__["a"]; }); - -/* harmony import */ var _internal_observable_throwError__WEBPACK_IMPORTED_MODULE_52__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/throwError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "throwError", function() { return _internal_observable_throwError__WEBPACK_IMPORTED_MODULE_52__["a"]; }); - -/* harmony import */ var _internal_observable_timer__WEBPACK_IMPORTED_MODULE_53__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/timer.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timer", function() { return _internal_observable_timer__WEBPACK_IMPORTED_MODULE_53__["a"]; }); - -/* harmony import */ var _internal_observable_using__WEBPACK_IMPORTED_MODULE_54__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/using.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "using", function() { return _internal_observable_using__WEBPACK_IMPORTED_MODULE_54__["a"]; }); - -/* harmony import */ var _internal_observable_zip__WEBPACK_IMPORTED_MODULE_55__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/zip.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "zip", function() { return _internal_observable_zip__WEBPACK_IMPORTED_MODULE_55__["a"]; }); - -/* harmony import */ var _internal_scheduled_scheduled__WEBPACK_IMPORTED_MODULE_56__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduled.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "scheduled", function() { return _internal_scheduled_scheduled__WEBPACK_IMPORTED_MODULE_56__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "EMPTY", function() { return _internal_observable_empty__WEBPACK_IMPORTED_MODULE_36__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "NEVER", function() { return _internal_observable_never__WEBPACK_IMPORTED_MODULE_45__["a"]; }); - -/* harmony import */ var _internal_config__WEBPACK_IMPORTED_MODULE_57__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/config.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "config", function() { return _internal_config__WEBPACK_IMPORTED_MODULE_57__["a"]; }); - -/* harmony import */ var _internal_operators_audit__WEBPACK_IMPORTED_MODULE_58__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/audit.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "audit", function() { return _internal_operators_audit__WEBPACK_IMPORTED_MODULE_58__["a"]; }); - -/* harmony import */ var _internal_operators_auditTime__WEBPACK_IMPORTED_MODULE_59__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/auditTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "auditTime", function() { return _internal_operators_auditTime__WEBPACK_IMPORTED_MODULE_59__["a"]; }); - -/* harmony import */ var _internal_operators_buffer__WEBPACK_IMPORTED_MODULE_60__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/buffer.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "buffer", function() { return _internal_operators_buffer__WEBPACK_IMPORTED_MODULE_60__["a"]; }); - -/* harmony import */ var _internal_operators_bufferCount__WEBPACK_IMPORTED_MODULE_61__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferCount.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferCount", function() { return _internal_operators_bufferCount__WEBPACK_IMPORTED_MODULE_61__["a"]; }); - -/* harmony import */ var _internal_operators_bufferTime__WEBPACK_IMPORTED_MODULE_62__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferTime", function() { return _internal_operators_bufferTime__WEBPACK_IMPORTED_MODULE_62__["a"]; }); - -/* harmony import */ var _internal_operators_bufferToggle__WEBPACK_IMPORTED_MODULE_63__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferToggle.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferToggle", function() { return _internal_operators_bufferToggle__WEBPACK_IMPORTED_MODULE_63__["a"]; }); - -/* harmony import */ var _internal_operators_bufferWhen__WEBPACK_IMPORTED_MODULE_64__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferWhen", function() { return _internal_operators_bufferWhen__WEBPACK_IMPORTED_MODULE_64__["a"]; }); - -/* harmony import */ var _internal_operators_catchError__WEBPACK_IMPORTED_MODULE_65__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/catchError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "catchError", function() { return _internal_operators_catchError__WEBPACK_IMPORTED_MODULE_65__["a"]; }); - -/* harmony import */ var _internal_operators_combineAll__WEBPACK_IMPORTED_MODULE_66__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineAll", function() { return _internal_operators_combineAll__WEBPACK_IMPORTED_MODULE_66__["a"]; }); - -/* harmony import */ var _internal_operators_combineLatestAll__WEBPACK_IMPORTED_MODULE_67__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineLatestAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineLatestAll", function() { return _internal_operators_combineLatestAll__WEBPACK_IMPORTED_MODULE_67__["a"]; }); - -/* harmony import */ var _internal_operators_combineLatestWith__WEBPACK_IMPORTED_MODULE_68__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineLatestWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineLatestWith", function() { return _internal_operators_combineLatestWith__WEBPACK_IMPORTED_MODULE_68__["a"]; }); - -/* harmony import */ var _internal_operators_concatAll__WEBPACK_IMPORTED_MODULE_69__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatAll", function() { return _internal_operators_concatAll__WEBPACK_IMPORTED_MODULE_69__["a"]; }); - -/* harmony import */ var _internal_operators_concatMap__WEBPACK_IMPORTED_MODULE_70__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatMap", function() { return _internal_operators_concatMap__WEBPACK_IMPORTED_MODULE_70__["a"]; }); - -/* harmony import */ var _internal_operators_concatMapTo__WEBPACK_IMPORTED_MODULE_71__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatMapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatMapTo", function() { return _internal_operators_concatMapTo__WEBPACK_IMPORTED_MODULE_71__["a"]; }); - -/* harmony import */ var _internal_operators_concatWith__WEBPACK_IMPORTED_MODULE_72__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatWith", function() { return _internal_operators_concatWith__WEBPACK_IMPORTED_MODULE_72__["a"]; }); - -/* harmony import */ var _internal_operators_connect__WEBPACK_IMPORTED_MODULE_73__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/connect.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "connect", function() { return _internal_operators_connect__WEBPACK_IMPORTED_MODULE_73__["a"]; }); - -/* harmony import */ var _internal_operators_count__WEBPACK_IMPORTED_MODULE_74__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/count.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "count", function() { return _internal_operators_count__WEBPACK_IMPORTED_MODULE_74__["a"]; }); - -/* harmony import */ var _internal_operators_debounce__WEBPACK_IMPORTED_MODULE_75__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/debounce.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "debounce", function() { return _internal_operators_debounce__WEBPACK_IMPORTED_MODULE_75__["a"]; }); - -/* harmony import */ var _internal_operators_debounceTime__WEBPACK_IMPORTED_MODULE_76__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/debounceTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "debounceTime", function() { return _internal_operators_debounceTime__WEBPACK_IMPORTED_MODULE_76__["a"]; }); - -/* harmony import */ var _internal_operators_defaultIfEmpty__WEBPACK_IMPORTED_MODULE_77__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/defaultIfEmpty.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "defaultIfEmpty", function() { return _internal_operators_defaultIfEmpty__WEBPACK_IMPORTED_MODULE_77__["a"]; }); - -/* harmony import */ var _internal_operators_delay__WEBPACK_IMPORTED_MODULE_78__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/delay.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "delay", function() { return _internal_operators_delay__WEBPACK_IMPORTED_MODULE_78__["a"]; }); - -/* harmony import */ var _internal_operators_delayWhen__WEBPACK_IMPORTED_MODULE_79__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/delayWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "delayWhen", function() { return _internal_operators_delayWhen__WEBPACK_IMPORTED_MODULE_79__["a"]; }); - -/* harmony import */ var _internal_operators_dematerialize__WEBPACK_IMPORTED_MODULE_80__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/dematerialize.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "dematerialize", function() { return _internal_operators_dematerialize__WEBPACK_IMPORTED_MODULE_80__["a"]; }); - -/* harmony import */ var _internal_operators_distinct__WEBPACK_IMPORTED_MODULE_81__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/distinct.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "distinct", function() { return _internal_operators_distinct__WEBPACK_IMPORTED_MODULE_81__["a"]; }); - -/* harmony import */ var _internal_operators_distinctUntilChanged__WEBPACK_IMPORTED_MODULE_82__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/distinctUntilChanged.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "distinctUntilChanged", function() { return _internal_operators_distinctUntilChanged__WEBPACK_IMPORTED_MODULE_82__["a"]; }); - -/* harmony import */ var _internal_operators_distinctUntilKeyChanged__WEBPACK_IMPORTED_MODULE_83__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/distinctUntilKeyChanged.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "distinctUntilKeyChanged", function() { return _internal_operators_distinctUntilKeyChanged__WEBPACK_IMPORTED_MODULE_83__["a"]; }); - -/* harmony import */ var _internal_operators_elementAt__WEBPACK_IMPORTED_MODULE_84__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/elementAt.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "elementAt", function() { return _internal_operators_elementAt__WEBPACK_IMPORTED_MODULE_84__["a"]; }); - -/* harmony import */ var _internal_operators_endWith__WEBPACK_IMPORTED_MODULE_85__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/endWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "endWith", function() { return _internal_operators_endWith__WEBPACK_IMPORTED_MODULE_85__["a"]; }); - -/* harmony import */ var _internal_operators_every__WEBPACK_IMPORTED_MODULE_86__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/every.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "every", function() { return _internal_operators_every__WEBPACK_IMPORTED_MODULE_86__["a"]; }); - -/* harmony import */ var _internal_operators_exhaust__WEBPACK_IMPORTED_MODULE_87__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/exhaust.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "exhaust", function() { return _internal_operators_exhaust__WEBPACK_IMPORTED_MODULE_87__["a"]; }); - -/* harmony import */ var _internal_operators_exhaustAll__WEBPACK_IMPORTED_MODULE_88__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/exhaustAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "exhaustAll", function() { return _internal_operators_exhaustAll__WEBPACK_IMPORTED_MODULE_88__["a"]; }); - -/* harmony import */ var _internal_operators_exhaustMap__WEBPACK_IMPORTED_MODULE_89__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/exhaustMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "exhaustMap", function() { return _internal_operators_exhaustMap__WEBPACK_IMPORTED_MODULE_89__["a"]; }); - -/* harmony import */ var _internal_operators_expand__WEBPACK_IMPORTED_MODULE_90__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/expand.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "expand", function() { return _internal_operators_expand__WEBPACK_IMPORTED_MODULE_90__["a"]; }); - -/* harmony import */ var _internal_operators_filter__WEBPACK_IMPORTED_MODULE_91__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "filter", function() { return _internal_operators_filter__WEBPACK_IMPORTED_MODULE_91__["a"]; }); - -/* harmony import */ var _internal_operators_finalize__WEBPACK_IMPORTED_MODULE_92__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/finalize.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "finalize", function() { return _internal_operators_finalize__WEBPACK_IMPORTED_MODULE_92__["a"]; }); - -/* harmony import */ var _internal_operators_find__WEBPACK_IMPORTED_MODULE_93__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/find.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "find", function() { return _internal_operators_find__WEBPACK_IMPORTED_MODULE_93__["b"]; }); - -/* harmony import */ var _internal_operators_findIndex__WEBPACK_IMPORTED_MODULE_94__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/findIndex.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "findIndex", function() { return _internal_operators_findIndex__WEBPACK_IMPORTED_MODULE_94__["a"]; }); - -/* harmony import */ var _internal_operators_first__WEBPACK_IMPORTED_MODULE_95__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/first.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "first", function() { return _internal_operators_first__WEBPACK_IMPORTED_MODULE_95__["a"]; }); - -/* harmony import */ var _internal_operators_groupBy__WEBPACK_IMPORTED_MODULE_96__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/groupBy.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "groupBy", function() { return _internal_operators_groupBy__WEBPACK_IMPORTED_MODULE_96__["a"]; }); - -/* harmony import */ var _internal_operators_ignoreElements__WEBPACK_IMPORTED_MODULE_97__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/ignoreElements.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "ignoreElements", function() { return _internal_operators_ignoreElements__WEBPACK_IMPORTED_MODULE_97__["a"]; }); - -/* harmony import */ var _internal_operators_isEmpty__WEBPACK_IMPORTED_MODULE_98__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/isEmpty.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "isEmpty", function() { return _internal_operators_isEmpty__WEBPACK_IMPORTED_MODULE_98__["a"]; }); - -/* harmony import */ var _internal_operators_last__WEBPACK_IMPORTED_MODULE_99__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/last.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "last", function() { return _internal_operators_last__WEBPACK_IMPORTED_MODULE_99__["a"]; }); - -/* harmony import */ var _internal_operators_map__WEBPACK_IMPORTED_MODULE_100__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "map", function() { return _internal_operators_map__WEBPACK_IMPORTED_MODULE_100__["a"]; }); - -/* harmony import */ var _internal_operators_mapTo__WEBPACK_IMPORTED_MODULE_101__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mapTo", function() { return _internal_operators_mapTo__WEBPACK_IMPORTED_MODULE_101__["a"]; }); - -/* harmony import */ var _internal_operators_materialize__WEBPACK_IMPORTED_MODULE_102__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/materialize.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "materialize", function() { return _internal_operators_materialize__WEBPACK_IMPORTED_MODULE_102__["a"]; }); - -/* harmony import */ var _internal_operators_max__WEBPACK_IMPORTED_MODULE_103__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/max.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "max", function() { return _internal_operators_max__WEBPACK_IMPORTED_MODULE_103__["a"]; }); - -/* harmony import */ var _internal_operators_mergeAll__WEBPACK_IMPORTED_MODULE_104__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeAll", function() { return _internal_operators_mergeAll__WEBPACK_IMPORTED_MODULE_104__["a"]; }); - -/* harmony import */ var _internal_operators_flatMap__WEBPACK_IMPORTED_MODULE_105__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/flatMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "flatMap", function() { return _internal_operators_flatMap__WEBPACK_IMPORTED_MODULE_105__["a"]; }); - -/* harmony import */ var _internal_operators_mergeMap__WEBPACK_IMPORTED_MODULE_106__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeMap", function() { return _internal_operators_mergeMap__WEBPACK_IMPORTED_MODULE_106__["a"]; }); - -/* harmony import */ var _internal_operators_mergeMapTo__WEBPACK_IMPORTED_MODULE_107__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeMapTo", function() { return _internal_operators_mergeMapTo__WEBPACK_IMPORTED_MODULE_107__["a"]; }); - -/* harmony import */ var _internal_operators_mergeScan__WEBPACK_IMPORTED_MODULE_108__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeScan.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeScan", function() { return _internal_operators_mergeScan__WEBPACK_IMPORTED_MODULE_108__["a"]; }); - -/* harmony import */ var _internal_operators_mergeWith__WEBPACK_IMPORTED_MODULE_109__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeWith", function() { return _internal_operators_mergeWith__WEBPACK_IMPORTED_MODULE_109__["a"]; }); - -/* harmony import */ var _internal_operators_min__WEBPACK_IMPORTED_MODULE_110__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/min.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "min", function() { return _internal_operators_min__WEBPACK_IMPORTED_MODULE_110__["a"]; }); - -/* harmony import */ var _internal_operators_multicast__WEBPACK_IMPORTED_MODULE_111__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/multicast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "multicast", function() { return _internal_operators_multicast__WEBPACK_IMPORTED_MODULE_111__["a"]; }); - -/* harmony import */ var _internal_operators_observeOn__WEBPACK_IMPORTED_MODULE_112__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/observeOn.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "observeOn", function() { return _internal_operators_observeOn__WEBPACK_IMPORTED_MODULE_112__["a"]; }); - -/* harmony import */ var _internal_operators_pairwise__WEBPACK_IMPORTED_MODULE_113__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/pairwise.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "pairwise", function() { return _internal_operators_pairwise__WEBPACK_IMPORTED_MODULE_113__["a"]; }); - -/* harmony import */ var _internal_operators_pluck__WEBPACK_IMPORTED_MODULE_114__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/pluck.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "pluck", function() { return _internal_operators_pluck__WEBPACK_IMPORTED_MODULE_114__["a"]; }); - -/* harmony import */ var _internal_operators_publish__WEBPACK_IMPORTED_MODULE_115__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publish.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publish", function() { return _internal_operators_publish__WEBPACK_IMPORTED_MODULE_115__["a"]; }); - -/* harmony import */ var _internal_operators_publishBehavior__WEBPACK_IMPORTED_MODULE_116__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publishBehavior.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publishBehavior", function() { return _internal_operators_publishBehavior__WEBPACK_IMPORTED_MODULE_116__["a"]; }); - -/* harmony import */ var _internal_operators_publishLast__WEBPACK_IMPORTED_MODULE_117__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publishLast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publishLast", function() { return _internal_operators_publishLast__WEBPACK_IMPORTED_MODULE_117__["a"]; }); - -/* harmony import */ var _internal_operators_publishReplay__WEBPACK_IMPORTED_MODULE_118__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publishReplay.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publishReplay", function() { return _internal_operators_publishReplay__WEBPACK_IMPORTED_MODULE_118__["a"]; }); - -/* harmony import */ var _internal_operators_raceWith__WEBPACK_IMPORTED_MODULE_119__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/raceWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "raceWith", function() { return _internal_operators_raceWith__WEBPACK_IMPORTED_MODULE_119__["a"]; }); - -/* harmony import */ var _internal_operators_reduce__WEBPACK_IMPORTED_MODULE_120__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/reduce.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "reduce", function() { return _internal_operators_reduce__WEBPACK_IMPORTED_MODULE_120__["a"]; }); - -/* harmony import */ var _internal_operators_repeat__WEBPACK_IMPORTED_MODULE_121__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/repeat.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "repeat", function() { return _internal_operators_repeat__WEBPACK_IMPORTED_MODULE_121__["a"]; }); - -/* harmony import */ var _internal_operators_repeatWhen__WEBPACK_IMPORTED_MODULE_122__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/repeatWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "repeatWhen", function() { return _internal_operators_repeatWhen__WEBPACK_IMPORTED_MODULE_122__["a"]; }); - -/* harmony import */ var _internal_operators_retry__WEBPACK_IMPORTED_MODULE_123__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/retry.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "retry", function() { return _internal_operators_retry__WEBPACK_IMPORTED_MODULE_123__["a"]; }); - -/* harmony import */ var _internal_operators_retryWhen__WEBPACK_IMPORTED_MODULE_124__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/retryWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "retryWhen", function() { return _internal_operators_retryWhen__WEBPACK_IMPORTED_MODULE_124__["a"]; }); - -/* harmony import */ var _internal_operators_refCount__WEBPACK_IMPORTED_MODULE_125__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/refCount.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "refCount", function() { return _internal_operators_refCount__WEBPACK_IMPORTED_MODULE_125__["a"]; }); - -/* harmony import */ var _internal_operators_sample__WEBPACK_IMPORTED_MODULE_126__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/sample.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "sample", function() { return _internal_operators_sample__WEBPACK_IMPORTED_MODULE_126__["a"]; }); - -/* harmony import */ var _internal_operators_sampleTime__WEBPACK_IMPORTED_MODULE_127__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/sampleTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "sampleTime", function() { return _internal_operators_sampleTime__WEBPACK_IMPORTED_MODULE_127__["a"]; }); - -/* harmony import */ var _internal_operators_scan__WEBPACK_IMPORTED_MODULE_128__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/scan.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "scan", function() { return _internal_operators_scan__WEBPACK_IMPORTED_MODULE_128__["a"]; }); - -/* harmony import */ var _internal_operators_sequenceEqual__WEBPACK_IMPORTED_MODULE_129__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/sequenceEqual.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "sequenceEqual", function() { return _internal_operators_sequenceEqual__WEBPACK_IMPORTED_MODULE_129__["a"]; }); - -/* harmony import */ var _internal_operators_share__WEBPACK_IMPORTED_MODULE_130__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/share.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "share", function() { return _internal_operators_share__WEBPACK_IMPORTED_MODULE_130__["a"]; }); - -/* harmony import */ var _internal_operators_shareReplay__WEBPACK_IMPORTED_MODULE_131__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/shareReplay.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "shareReplay", function() { return _internal_operators_shareReplay__WEBPACK_IMPORTED_MODULE_131__["a"]; }); - -/* harmony import */ var _internal_operators_single__WEBPACK_IMPORTED_MODULE_132__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/single.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "single", function() { return _internal_operators_single__WEBPACK_IMPORTED_MODULE_132__["a"]; }); - -/* harmony import */ var _internal_operators_skip__WEBPACK_IMPORTED_MODULE_133__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skip.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skip", function() { return _internal_operators_skip__WEBPACK_IMPORTED_MODULE_133__["a"]; }); - -/* harmony import */ var _internal_operators_skipLast__WEBPACK_IMPORTED_MODULE_134__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skipLast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skipLast", function() { return _internal_operators_skipLast__WEBPACK_IMPORTED_MODULE_134__["a"]; }); - -/* harmony import */ var _internal_operators_skipUntil__WEBPACK_IMPORTED_MODULE_135__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skipUntil.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skipUntil", function() { return _internal_operators_skipUntil__WEBPACK_IMPORTED_MODULE_135__["a"]; }); - -/* harmony import */ var _internal_operators_skipWhile__WEBPACK_IMPORTED_MODULE_136__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skipWhile.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skipWhile", function() { return _internal_operators_skipWhile__WEBPACK_IMPORTED_MODULE_136__["a"]; }); - -/* harmony import */ var _internal_operators_startWith__WEBPACK_IMPORTED_MODULE_137__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/startWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "startWith", function() { return _internal_operators_startWith__WEBPACK_IMPORTED_MODULE_137__["a"]; }); - -/* harmony import */ var _internal_operators_subscribeOn__WEBPACK_IMPORTED_MODULE_138__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/subscribeOn.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "subscribeOn", function() { return _internal_operators_subscribeOn__WEBPACK_IMPORTED_MODULE_138__["a"]; }); - -/* harmony import */ var _internal_operators_switchAll__WEBPACK_IMPORTED_MODULE_139__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchAll", function() { return _internal_operators_switchAll__WEBPACK_IMPORTED_MODULE_139__["a"]; }); - -/* harmony import */ var _internal_operators_switchMap__WEBPACK_IMPORTED_MODULE_140__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchMap", function() { return _internal_operators_switchMap__WEBPACK_IMPORTED_MODULE_140__["a"]; }); - -/* harmony import */ var _internal_operators_switchMapTo__WEBPACK_IMPORTED_MODULE_141__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchMapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchMapTo", function() { return _internal_operators_switchMapTo__WEBPACK_IMPORTED_MODULE_141__["a"]; }); - -/* harmony import */ var _internal_operators_switchScan__WEBPACK_IMPORTED_MODULE_142__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchScan.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchScan", function() { return _internal_operators_switchScan__WEBPACK_IMPORTED_MODULE_142__["a"]; }); - -/* harmony import */ var _internal_operators_take__WEBPACK_IMPORTED_MODULE_143__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/take.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "take", function() { return _internal_operators_take__WEBPACK_IMPORTED_MODULE_143__["a"]; }); - -/* harmony import */ var _internal_operators_takeLast__WEBPACK_IMPORTED_MODULE_144__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/takeLast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "takeLast", function() { return _internal_operators_takeLast__WEBPACK_IMPORTED_MODULE_144__["a"]; }); - -/* harmony import */ var _internal_operators_takeUntil__WEBPACK_IMPORTED_MODULE_145__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/takeUntil.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "takeUntil", function() { return _internal_operators_takeUntil__WEBPACK_IMPORTED_MODULE_145__["a"]; }); - -/* harmony import */ var _internal_operators_takeWhile__WEBPACK_IMPORTED_MODULE_146__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/takeWhile.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "takeWhile", function() { return _internal_operators_takeWhile__WEBPACK_IMPORTED_MODULE_146__["a"]; }); - -/* harmony import */ var _internal_operators_tap__WEBPACK_IMPORTED_MODULE_147__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/tap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "tap", function() { return _internal_operators_tap__WEBPACK_IMPORTED_MODULE_147__["a"]; }); - -/* harmony import */ var _internal_operators_throttle__WEBPACK_IMPORTED_MODULE_148__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throttle.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "throttle", function() { return _internal_operators_throttle__WEBPACK_IMPORTED_MODULE_148__["b"]; }); - -/* harmony import */ var _internal_operators_throttleTime__WEBPACK_IMPORTED_MODULE_149__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throttleTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "throttleTime", function() { return _internal_operators_throttleTime__WEBPACK_IMPORTED_MODULE_149__["a"]; }); - -/* harmony import */ var _internal_operators_throwIfEmpty__WEBPACK_IMPORTED_MODULE_150__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throwIfEmpty.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "throwIfEmpty", function() { return _internal_operators_throwIfEmpty__WEBPACK_IMPORTED_MODULE_150__["a"]; }); - -/* harmony import */ var _internal_operators_timeInterval__WEBPACK_IMPORTED_MODULE_151__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timeInterval.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timeInterval", function() { return _internal_operators_timeInterval__WEBPACK_IMPORTED_MODULE_151__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timeout", function() { return _internal_operators_timeout__WEBPACK_IMPORTED_MODULE_28__["b"]; }); - -/* harmony import */ var _internal_operators_timeoutWith__WEBPACK_IMPORTED_MODULE_152__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timeoutWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timeoutWith", function() { return _internal_operators_timeoutWith__WEBPACK_IMPORTED_MODULE_152__["a"]; }); - -/* harmony import */ var _internal_operators_timestamp__WEBPACK_IMPORTED_MODULE_153__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timestamp.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timestamp", function() { return _internal_operators_timestamp__WEBPACK_IMPORTED_MODULE_153__["a"]; }); - -/* harmony import */ var _internal_operators_toArray__WEBPACK_IMPORTED_MODULE_154__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/toArray.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "toArray", function() { return _internal_operators_toArray__WEBPACK_IMPORTED_MODULE_154__["a"]; }); - -/* harmony import */ var _internal_operators_window__WEBPACK_IMPORTED_MODULE_155__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/window.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "window", function() { return _internal_operators_window__WEBPACK_IMPORTED_MODULE_155__["a"]; }); - -/* harmony import */ var _internal_operators_windowCount__WEBPACK_IMPORTED_MODULE_156__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowCount.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowCount", function() { return _internal_operators_windowCount__WEBPACK_IMPORTED_MODULE_156__["a"]; }); - -/* harmony import */ var _internal_operators_windowTime__WEBPACK_IMPORTED_MODULE_157__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowTime", function() { return _internal_operators_windowTime__WEBPACK_IMPORTED_MODULE_157__["a"]; }); - -/* harmony import */ var _internal_operators_windowToggle__WEBPACK_IMPORTED_MODULE_158__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowToggle.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowToggle", function() { return _internal_operators_windowToggle__WEBPACK_IMPORTED_MODULE_158__["a"]; }); - -/* harmony import */ var _internal_operators_windowWhen__WEBPACK_IMPORTED_MODULE_159__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowWhen", function() { return _internal_operators_windowWhen__WEBPACK_IMPORTED_MODULE_159__["a"]; }); - -/* harmony import */ var _internal_operators_withLatestFrom__WEBPACK_IMPORTED_MODULE_160__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/withLatestFrom.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "withLatestFrom", function() { return _internal_operators_withLatestFrom__WEBPACK_IMPORTED_MODULE_160__["a"]; }); - -/* harmony import */ var _internal_operators_zipAll__WEBPACK_IMPORTED_MODULE_161__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/zipAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "zipAll", function() { return _internal_operators_zipAll__WEBPACK_IMPORTED_MODULE_161__["a"]; }); - -/* harmony import */ var _internal_operators_zipWith__WEBPACK_IMPORTED_MODULE_162__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/zipWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "zipWith", function() { return _internal_operators_zipWith__WEBPACK_IMPORTED_MODULE_162__["a"]; }); - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -//# sourceMappingURL=index.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/AsyncSubject.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return AsyncSubject; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); - - -var AsyncSubject = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AsyncSubject, _super); - function AsyncSubject() { - var _this = _super !== null && _super.apply(this, arguments) || this; - _this._value = null; - _this._hasValue = false; - _this._isComplete = false; - return _this; - } - AsyncSubject.prototype._checkFinalizedStatuses = function (subscriber) { - var _a = this, hasError = _a.hasError, _hasValue = _a._hasValue, _value = _a._value, thrownError = _a.thrownError, isStopped = _a.isStopped, _isComplete = _a._isComplete; - if (hasError) { - subscriber.error(thrownError); - } - else if (isStopped || _isComplete) { - _hasValue && subscriber.next(_value); - subscriber.complete(); - } - }; - AsyncSubject.prototype.next = function (value) { - if (!this.isStopped) { - this._value = value; - this._hasValue = true; - } - }; - AsyncSubject.prototype.complete = function () { - var _a = this, _hasValue = _a._hasValue, _value = _a._value, _isComplete = _a._isComplete; - if (!_isComplete) { - this._isComplete = true; - _hasValue && _super.prototype.next.call(this, _value); - _super.prototype.complete.call(this); - } - }; - return AsyncSubject; -}(_Subject__WEBPACK_IMPORTED_MODULE_1__[/* Subject */ "a"])); - -//# sourceMappingURL=AsyncSubject.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/BehaviorSubject.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return BehaviorSubject; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); - - -var BehaviorSubject = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(BehaviorSubject, _super); - function BehaviorSubject(_value) { - var _this = _super.call(this) || this; - _this._value = _value; - return _this; - } - Object.defineProperty(BehaviorSubject.prototype, "value", { - get: function () { - return this.getValue(); - }, - enumerable: false, - configurable: true - }); - BehaviorSubject.prototype._subscribe = function (subscriber) { - var subscription = _super.prototype._subscribe.call(this, subscriber); - !subscription.closed && subscriber.next(this._value); - return subscription; - }; - BehaviorSubject.prototype.getValue = function () { - var _a = this, hasError = _a.hasError, thrownError = _a.thrownError, _value = _a._value; - if (hasError) { - throw thrownError; - } - this._throwIfClosed(); - return _value; - }; - BehaviorSubject.prototype.next = function (value) { - _super.prototype.next.call(this, (this._value = value)); - }; - return BehaviorSubject; -}(_Subject__WEBPACK_IMPORTED_MODULE_1__[/* Subject */ "a"])); - -//# sourceMappingURL=BehaviorSubject.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/Notification.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return NotificationKind; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Notification; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return observeNotification; }); -/* harmony import */ var _observable_empty__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony import */ var _observable_of__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/of.js"); -/* harmony import */ var _observable_throwError__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/throwError.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - - - -var NotificationKind; -(function (NotificationKind) { - NotificationKind["NEXT"] = "N"; - NotificationKind["ERROR"] = "E"; - NotificationKind["COMPLETE"] = "C"; -})(NotificationKind || (NotificationKind = {})); -var Notification = (function () { - function Notification(kind, value, error) { - this.kind = kind; - this.value = value; - this.error = error; - this.hasValue = kind === 'N'; - } - Notification.prototype.observe = function (observer) { - return observeNotification(this, observer); - }; - Notification.prototype.do = function (nextHandler, errorHandler, completeHandler) { - var _a = this, kind = _a.kind, value = _a.value, error = _a.error; - return kind === 'N' ? nextHandler === null || nextHandler === void 0 ? void 0 : nextHandler(value) : kind === 'E' ? errorHandler === null || errorHandler === void 0 ? void 0 : errorHandler(error) : completeHandler === null || completeHandler === void 0 ? void 0 : completeHandler(); - }; - Notification.prototype.accept = function (nextOrObserver, error, complete) { - var _a; - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_3__[/* isFunction */ "a"])((_a = nextOrObserver) === null || _a === void 0 ? void 0 : _a.next) - ? this.observe(nextOrObserver) - : this.do(nextOrObserver, error, complete); - }; - Notification.prototype.toObservable = function () { - var _a = this, kind = _a.kind, value = _a.value, error = _a.error; - var result = kind === 'N' - ? - Object(_observable_of__WEBPACK_IMPORTED_MODULE_1__[/* of */ "a"])(value) - : - kind === 'E' - ? - Object(_observable_throwError__WEBPACK_IMPORTED_MODULE_2__[/* throwError */ "a"])(function () { return error; }) - : - kind === 'C' - ? - _observable_empty__WEBPACK_IMPORTED_MODULE_0__[/* EMPTY */ "a"] - : - 0; - if (!result) { - throw new TypeError("Unexpected notification kind " + kind); - } - return result; - }; - Notification.createNext = function (value) { - return new Notification('N', value); - }; - Notification.createError = function (err) { - return new Notification('E', undefined, err); - }; - Notification.createComplete = function () { - return Notification.completeNotification; - }; - Notification.completeNotification = new Notification('C'); - return Notification; -}()); - -function observeNotification(notification, observer) { - var _a, _b, _c; - var _d = notification, kind = _d.kind, value = _d.value, error = _d.error; - if (typeof kind !== 'string') { - throw new TypeError('Invalid notification, missing "kind"'); - } - kind === 'N' ? (_a = observer.next) === null || _a === void 0 ? void 0 : _a.call(observer, value) : kind === 'E' ? (_b = observer.error) === null || _b === void 0 ? void 0 : _b.call(observer, error) : (_c = observer.complete) === null || _c === void 0 ? void 0 : _c.call(observer); -} -//# sourceMappingURL=Notification.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/NotificationFactories.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return COMPLETE_NOTIFICATION; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return errorNotification; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return nextNotification; }); -/* unused harmony export createNotification */ -var COMPLETE_NOTIFICATION = (function () { return createNotification('C', undefined, undefined); })(); -function errorNotification(error) { - return createNotification('E', undefined, error); -} -function nextNotification(value) { - return createNotification('N', value, undefined); -} -function createNotification(kind, value, error) { - return { - kind: kind, - value: value, - error: error, - }; -} -//# sourceMappingURL=NotificationFactories.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/Observable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Observable; }); -/* harmony import */ var _Subscriber__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscriber.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _symbol_observable__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/symbol/observable.js"); -/* harmony import */ var _util_pipe__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/pipe.js"); -/* harmony import */ var _config__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/config.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _util_errorContext__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/errorContext.js"); - - - - - - - -var Observable = (function () { - function Observable(subscribe) { - if (subscribe) { - this._subscribe = subscribe; - } - } - Observable.prototype.lift = function (operator) { - var observable = new Observable(); - observable.source = this; - observable.operator = operator; - return observable; - }; - Observable.prototype.subscribe = function (observerOrNext, error, complete) { - var _this = this; - var subscriber = isSubscriber(observerOrNext) ? observerOrNext : new _Subscriber__WEBPACK_IMPORTED_MODULE_0__[/* SafeSubscriber */ "a"](observerOrNext, error, complete); - Object(_util_errorContext__WEBPACK_IMPORTED_MODULE_6__[/* errorContext */ "b"])(function () { - var _a = _this, operator = _a.operator, source = _a.source; - subscriber.add(operator - ? - operator.call(subscriber, source) - : source - ? - _this._subscribe(subscriber) - : - _this._trySubscribe(subscriber)); - }); - return subscriber; - }; - Observable.prototype._trySubscribe = function (sink) { - try { - return this._subscribe(sink); - } - catch (err) { - sink.error(err); - } - }; - Observable.prototype.forEach = function (next, promiseCtor) { - var _this = this; - promiseCtor = getPromiseCtor(promiseCtor); - return new promiseCtor(function (resolve, reject) { - var subscriber = new _Subscriber__WEBPACK_IMPORTED_MODULE_0__[/* SafeSubscriber */ "a"]({ - next: function (value) { - try { - next(value); - } - catch (err) { - reject(err); - subscriber.unsubscribe(); - } - }, - error: reject, - complete: resolve, - }); - _this.subscribe(subscriber); - }); - }; - Observable.prototype._subscribe = function (subscriber) { - var _a; - return (_a = this.source) === null || _a === void 0 ? void 0 : _a.subscribe(subscriber); - }; - Observable.prototype[_symbol_observable__WEBPACK_IMPORTED_MODULE_2__[/* observable */ "a"]] = function () { - return this; - }; - Observable.prototype.pipe = function () { - var operations = []; - for (var _i = 0; _i < arguments.length; _i++) { - operations[_i] = arguments[_i]; - } - return Object(_util_pipe__WEBPACK_IMPORTED_MODULE_3__[/* pipeFromArray */ "b"])(operations)(this); - }; - Observable.prototype.toPromise = function (promiseCtor) { - var _this = this; - promiseCtor = getPromiseCtor(promiseCtor); - return new promiseCtor(function (resolve, reject) { - var value; - _this.subscribe(function (x) { return (value = x); }, function (err) { return reject(err); }, function () { return resolve(value); }); - }); - }; - Observable.create = function (subscribe) { - return new Observable(subscribe); - }; - return Observable; -}()); - -function getPromiseCtor(promiseCtor) { - var _a; - return (_a = promiseCtor !== null && promiseCtor !== void 0 ? promiseCtor : _config__WEBPACK_IMPORTED_MODULE_4__[/* config */ "a"].Promise) !== null && _a !== void 0 ? _a : Promise; -} -function isObserver(value) { - return value && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(value.next) && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(value.error) && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(value.complete); -} -function isSubscriber(value) { - return (value && value instanceof _Subscriber__WEBPACK_IMPORTED_MODULE_0__[/* Subscriber */ "b"]) || (isObserver(value) && Object(_Subscription__WEBPACK_IMPORTED_MODULE_1__[/* isSubscription */ "c"])(value)); -} -//# sourceMappingURL=Observable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/ReplaySubject.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return ReplaySubject; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _scheduler_dateTimestampProvider__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/dateTimestampProvider.js"); - - - -var ReplaySubject = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(ReplaySubject, _super); - function ReplaySubject(_bufferSize, _windowTime, _timestampProvider) { - if (_bufferSize === void 0) { _bufferSize = Infinity; } - if (_windowTime === void 0) { _windowTime = Infinity; } - if (_timestampProvider === void 0) { _timestampProvider = _scheduler_dateTimestampProvider__WEBPACK_IMPORTED_MODULE_2__[/* dateTimestampProvider */ "a"]; } - var _this = _super.call(this) || this; - _this._bufferSize = _bufferSize; - _this._windowTime = _windowTime; - _this._timestampProvider = _timestampProvider; - _this._buffer = []; - _this._infiniteTimeWindow = true; - _this._infiniteTimeWindow = _windowTime === Infinity; - _this._bufferSize = Math.max(1, _bufferSize); - _this._windowTime = Math.max(1, _windowTime); - return _this; - } - ReplaySubject.prototype.next = function (value) { - var _a = this, isStopped = _a.isStopped, _buffer = _a._buffer, _infiniteTimeWindow = _a._infiniteTimeWindow, _timestampProvider = _a._timestampProvider, _windowTime = _a._windowTime; - if (!isStopped) { - _buffer.push(value); - !_infiniteTimeWindow && _buffer.push(_timestampProvider.now() + _windowTime); - } - this._trimBuffer(); - _super.prototype.next.call(this, value); - }; - ReplaySubject.prototype._subscribe = function (subscriber) { - this._throwIfClosed(); - this._trimBuffer(); - var subscription = this._innerSubscribe(subscriber); - var _a = this, _infiniteTimeWindow = _a._infiniteTimeWindow, _buffer = _a._buffer; - var copy = _buffer.slice(); - for (var i = 0; i < copy.length && !subscriber.closed; i += _infiniteTimeWindow ? 1 : 2) { - subscriber.next(copy[i]); - } - this._checkFinalizedStatuses(subscriber); - return subscription; - }; - ReplaySubject.prototype._trimBuffer = function () { - var _a = this, _bufferSize = _a._bufferSize, _timestampProvider = _a._timestampProvider, _buffer = _a._buffer, _infiniteTimeWindow = _a._infiniteTimeWindow; - var adjustedBufferSize = (_infiniteTimeWindow ? 1 : 2) * _bufferSize; - _bufferSize < Infinity && adjustedBufferSize < _buffer.length && _buffer.splice(0, _buffer.length - adjustedBufferSize); - if (!_infiniteTimeWindow) { - var now = _timestampProvider.now(); - var last = 0; - for (var i = 1; i < _buffer.length && _buffer[i] <= now; i += 2) { - last = i; - } - last && _buffer.splice(0, last + 1); - } - }; - return ReplaySubject; -}(_Subject__WEBPACK_IMPORTED_MODULE_1__[/* Subject */ "a"])); - -//# sourceMappingURL=ReplaySubject.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/Scheduler.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Scheduler; }); -/* harmony import */ var _scheduler_dateTimestampProvider__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/dateTimestampProvider.js"); - -var Scheduler = (function () { - function Scheduler(schedulerActionCtor, now) { - if (now === void 0) { now = Scheduler.now; } - this.schedulerActionCtor = schedulerActionCtor; - this.now = now; - } - Scheduler.prototype.schedule = function (work, delay, state) { - if (delay === void 0) { delay = 0; } - return new this.schedulerActionCtor(this, work).schedule(state, delay); - }; - Scheduler.now = _scheduler_dateTimestampProvider__WEBPACK_IMPORTED_MODULE_0__[/* dateTimestampProvider */ "a"].now; - return Scheduler; -}()); - -//# sourceMappingURL=Scheduler.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/Subject.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Subject; }); -/* unused harmony export AnonymousSubject */ -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _util_ObjectUnsubscribedError__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/ObjectUnsubscribedError.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); -/* harmony import */ var _util_errorContext__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/errorContext.js"); - - - - - - -var Subject = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(Subject, _super); - function Subject() { - var _this = _super.call(this) || this; - _this.closed = false; - _this.currentObservers = null; - _this.observers = []; - _this.isStopped = false; - _this.hasError = false; - _this.thrownError = null; - return _this; - } - Subject.prototype.lift = function (operator) { - var subject = new AnonymousSubject(this, this); - subject.operator = operator; - return subject; - }; - Subject.prototype._throwIfClosed = function () { - if (this.closed) { - throw new _util_ObjectUnsubscribedError__WEBPACK_IMPORTED_MODULE_3__[/* ObjectUnsubscribedError */ "a"](); - } - }; - Subject.prototype.next = function (value) { - var _this = this; - Object(_util_errorContext__WEBPACK_IMPORTED_MODULE_5__[/* errorContext */ "b"])(function () { - var e_1, _a; - _this._throwIfClosed(); - if (!_this.isStopped) { - if (!_this.currentObservers) { - _this.currentObservers = Array.from(_this.observers); - } - try { - for (var _b = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(_this.currentObservers), _c = _b.next(); !_c.done; _c = _b.next()) { - var observer = _c.value; - observer.next(value); - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (_c && !_c.done && (_a = _b.return)) _a.call(_b); - } - finally { if (e_1) throw e_1.error; } - } - } - }); - }; - Subject.prototype.error = function (err) { - var _this = this; - Object(_util_errorContext__WEBPACK_IMPORTED_MODULE_5__[/* errorContext */ "b"])(function () { - _this._throwIfClosed(); - if (!_this.isStopped) { - _this.hasError = _this.isStopped = true; - _this.thrownError = err; - var observers = _this.observers; - while (observers.length) { - observers.shift().error(err); - } - } - }); - }; - Subject.prototype.complete = function () { - var _this = this; - Object(_util_errorContext__WEBPACK_IMPORTED_MODULE_5__[/* errorContext */ "b"])(function () { - _this._throwIfClosed(); - if (!_this.isStopped) { - _this.isStopped = true; - var observers = _this.observers; - while (observers.length) { - observers.shift().complete(); - } - } - }); - }; - Subject.prototype.unsubscribe = function () { - this.isStopped = this.closed = true; - this.observers = this.currentObservers = null; - }; - Object.defineProperty(Subject.prototype, "observed", { - get: function () { - var _a; - return ((_a = this.observers) === null || _a === void 0 ? void 0 : _a.length) > 0; - }, - enumerable: false, - configurable: true - }); - Subject.prototype._trySubscribe = function (subscriber) { - this._throwIfClosed(); - return _super.prototype._trySubscribe.call(this, subscriber); - }; - Subject.prototype._subscribe = function (subscriber) { - this._throwIfClosed(); - this._checkFinalizedStatuses(subscriber); - return this._innerSubscribe(subscriber); - }; - Subject.prototype._innerSubscribe = function (subscriber) { - var _this = this; - var _a = this, hasError = _a.hasError, isStopped = _a.isStopped, observers = _a.observers; - if (hasError || isStopped) { - return _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* EMPTY_SUBSCRIPTION */ "a"]; - } - this.currentObservers = null; - observers.push(subscriber); - return new _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* Subscription */ "b"](function () { - _this.currentObservers = null; - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_4__[/* arrRemove */ "a"])(observers, subscriber); - }); - }; - Subject.prototype._checkFinalizedStatuses = function (subscriber) { - var _a = this, hasError = _a.hasError, thrownError = _a.thrownError, isStopped = _a.isStopped; - if (hasError) { - subscriber.error(thrownError); - } - else if (isStopped) { - subscriber.complete(); - } - }; - Subject.prototype.asObservable = function () { - var observable = new _Observable__WEBPACK_IMPORTED_MODULE_1__[/* Observable */ "a"](); - observable.source = this; - return observable; - }; - Subject.create = function (destination, source) { - return new AnonymousSubject(destination, source); - }; - return Subject; -}(_Observable__WEBPACK_IMPORTED_MODULE_1__[/* Observable */ "a"])); - -var AnonymousSubject = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AnonymousSubject, _super); - function AnonymousSubject(destination, source) { - var _this = _super.call(this) || this; - _this.destination = destination; - _this.source = source; - return _this; - } - AnonymousSubject.prototype.next = function (value) { - var _a, _b; - (_b = (_a = this.destination) === null || _a === void 0 ? void 0 : _a.next) === null || _b === void 0 ? void 0 : _b.call(_a, value); - }; - AnonymousSubject.prototype.error = function (err) { - var _a, _b; - (_b = (_a = this.destination) === null || _a === void 0 ? void 0 : _a.error) === null || _b === void 0 ? void 0 : _b.call(_a, err); - }; - AnonymousSubject.prototype.complete = function () { - var _a, _b; - (_b = (_a = this.destination) === null || _a === void 0 ? void 0 : _a.complete) === null || _b === void 0 ? void 0 : _b.call(_a); - }; - AnonymousSubject.prototype._subscribe = function (subscriber) { - var _a, _b; - return (_b = (_a = this.source) === null || _a === void 0 ? void 0 : _a.subscribe(subscriber)) !== null && _b !== void 0 ? _b : _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* EMPTY_SUBSCRIPTION */ "a"]; - }; - return AnonymousSubject; -}(Subject)); - -//# sourceMappingURL=Subject.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/Subscriber.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return Subscriber; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return SafeSubscriber; }); -/* unused harmony export EMPTY_OBSERVER */ -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _config__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/config.js"); -/* harmony import */ var _util_reportUnhandledError__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/reportUnhandledError.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _NotificationFactories__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/NotificationFactories.js"); -/* harmony import */ var _scheduler_timeoutProvider__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/timeoutProvider.js"); -/* harmony import */ var _util_errorContext__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/errorContext.js"); - - - - - - - - - -var Subscriber = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(Subscriber, _super); - function Subscriber(destination) { - var _this = _super.call(this) || this; - _this.isStopped = false; - if (destination) { - _this.destination = destination; - if (Object(_Subscription__WEBPACK_IMPORTED_MODULE_2__[/* isSubscription */ "c"])(destination)) { - destination.add(_this); - } - } - else { - _this.destination = EMPTY_OBSERVER; - } - return _this; - } - Subscriber.create = function (next, error, complete) { - return new SafeSubscriber(next, error, complete); - }; - Subscriber.prototype.next = function (value) { - if (this.isStopped) { - handleStoppedNotification(Object(_NotificationFactories__WEBPACK_IMPORTED_MODULE_6__[/* nextNotification */ "c"])(value), this); - } - else { - this._next(value); - } - }; - Subscriber.prototype.error = function (err) { - if (this.isStopped) { - handleStoppedNotification(Object(_NotificationFactories__WEBPACK_IMPORTED_MODULE_6__[/* errorNotification */ "b"])(err), this); - } - else { - this.isStopped = true; - this._error(err); - } - }; - Subscriber.prototype.complete = function () { - if (this.isStopped) { - handleStoppedNotification(_NotificationFactories__WEBPACK_IMPORTED_MODULE_6__[/* COMPLETE_NOTIFICATION */ "a"], this); - } - else { - this.isStopped = true; - this._complete(); - } - }; - Subscriber.prototype.unsubscribe = function () { - if (!this.closed) { - this.isStopped = true; - _super.prototype.unsubscribe.call(this); - this.destination = null; - } - }; - Subscriber.prototype._next = function (value) { - this.destination.next(value); - }; - Subscriber.prototype._error = function (err) { - try { - this.destination.error(err); - } - finally { - this.unsubscribe(); - } - }; - Subscriber.prototype._complete = function () { - try { - this.destination.complete(); - } - finally { - this.unsubscribe(); - } - }; - return Subscriber; -}(_Subscription__WEBPACK_IMPORTED_MODULE_2__[/* Subscription */ "b"])); - -var _bind = Function.prototype.bind; -function bind(fn, thisArg) { - return _bind.call(fn, thisArg); -} -var ConsumerObserver = (function () { - function ConsumerObserver(partialObserver) { - this.partialObserver = partialObserver; - } - ConsumerObserver.prototype.next = function (value) { - var partialObserver = this.partialObserver; - if (partialObserver.next) { - try { - partialObserver.next(value); - } - catch (error) { - handleUnhandledError(error); - } - } - }; - ConsumerObserver.prototype.error = function (err) { - var partialObserver = this.partialObserver; - if (partialObserver.error) { - try { - partialObserver.error(err); - } - catch (error) { - handleUnhandledError(error); - } - } - else { - handleUnhandledError(err); - } - }; - ConsumerObserver.prototype.complete = function () { - var partialObserver = this.partialObserver; - if (partialObserver.complete) { - try { - partialObserver.complete(); - } - catch (error) { - handleUnhandledError(error); - } - } - }; - return ConsumerObserver; -}()); -var SafeSubscriber = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(SafeSubscriber, _super); - function SafeSubscriber(observerOrNext, error, complete) { - var _this = _super.call(this) || this; - var partialObserver; - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(observerOrNext) || !observerOrNext) { - partialObserver = { - next: observerOrNext !== null && observerOrNext !== void 0 ? observerOrNext : undefined, - error: error !== null && error !== void 0 ? error : undefined, - complete: complete !== null && complete !== void 0 ? complete : undefined, - }; - } - else { - var context_1; - if (_this && _config__WEBPACK_IMPORTED_MODULE_3__[/* config */ "a"].useDeprecatedNextContext) { - context_1 = Object.create(observerOrNext); - context_1.unsubscribe = function () { return _this.unsubscribe(); }; - partialObserver = { - next: observerOrNext.next && bind(observerOrNext.next, context_1), - error: observerOrNext.error && bind(observerOrNext.error, context_1), - complete: observerOrNext.complete && bind(observerOrNext.complete, context_1), - }; - } - else { - partialObserver = observerOrNext; - } - } - _this.destination = new ConsumerObserver(partialObserver); - return _this; - } - return SafeSubscriber; -}(Subscriber)); - -function handleUnhandledError(error) { - if (_config__WEBPACK_IMPORTED_MODULE_3__[/* config */ "a"].useDeprecatedSynchronousErrorHandling) { - Object(_util_errorContext__WEBPACK_IMPORTED_MODULE_8__[/* captureError */ "a"])(error); - } - else { - Object(_util_reportUnhandledError__WEBPACK_IMPORTED_MODULE_4__[/* reportUnhandledError */ "a"])(error); - } -} -function defaultErrorHandler(err) { - throw err; -} -function handleStoppedNotification(notification, subscriber) { - var onStoppedNotification = _config__WEBPACK_IMPORTED_MODULE_3__[/* config */ "a"].onStoppedNotification; - onStoppedNotification && _scheduler_timeoutProvider__WEBPACK_IMPORTED_MODULE_7__[/* timeoutProvider */ "a"].setTimeout(function () { return onStoppedNotification(notification, subscriber); }); -} -var EMPTY_OBSERVER = { - closed: true, - next: _util_noop__WEBPACK_IMPORTED_MODULE_5__[/* noop */ "a"], - error: defaultErrorHandler, - complete: _util_noop__WEBPACK_IMPORTED_MODULE_5__[/* noop */ "a"], -}; -//# sourceMappingURL=Subscriber.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/Subscription.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return Subscription; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return EMPTY_SUBSCRIPTION; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return isSubscription; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _util_UnsubscriptionError__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/UnsubscriptionError.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); - - - - -var Subscription = (function () { - function Subscription(initialTeardown) { - this.initialTeardown = initialTeardown; - this.closed = false; - this._parentage = null; - this._finalizers = null; - } - Subscription.prototype.unsubscribe = function () { - var e_1, _a, e_2, _b; - var errors; - if (!this.closed) { - this.closed = true; - var _parentage = this._parentage; - if (_parentage) { - this._parentage = null; - if (Array.isArray(_parentage)) { - try { - for (var _parentage_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(_parentage), _parentage_1_1 = _parentage_1.next(); !_parentage_1_1.done; _parentage_1_1 = _parentage_1.next()) { - var parent_1 = _parentage_1_1.value; - parent_1.remove(this); - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (_parentage_1_1 && !_parentage_1_1.done && (_a = _parentage_1.return)) _a.call(_parentage_1); - } - finally { if (e_1) throw e_1.error; } - } - } - else { - _parentage.remove(this); - } - } - var initialFinalizer = this.initialTeardown; - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(initialFinalizer)) { - try { - initialFinalizer(); - } - catch (e) { - errors = e instanceof _util_UnsubscriptionError__WEBPACK_IMPORTED_MODULE_2__[/* UnsubscriptionError */ "a"] ? e.errors : [e]; - } - } - var _finalizers = this._finalizers; - if (_finalizers) { - this._finalizers = null; - try { - for (var _finalizers_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(_finalizers), _finalizers_1_1 = _finalizers_1.next(); !_finalizers_1_1.done; _finalizers_1_1 = _finalizers_1.next()) { - var finalizer = _finalizers_1_1.value; - try { - execFinalizer(finalizer); - } - catch (err) { - errors = errors !== null && errors !== void 0 ? errors : []; - if (err instanceof _util_UnsubscriptionError__WEBPACK_IMPORTED_MODULE_2__[/* UnsubscriptionError */ "a"]) { - errors = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])(Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(errors)), Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(err.errors)); - } - else { - errors.push(err); - } - } - } - } - catch (e_2_1) { e_2 = { error: e_2_1 }; } - finally { - try { - if (_finalizers_1_1 && !_finalizers_1_1.done && (_b = _finalizers_1.return)) _b.call(_finalizers_1); - } - finally { if (e_2) throw e_2.error; } - } - } - if (errors) { - throw new _util_UnsubscriptionError__WEBPACK_IMPORTED_MODULE_2__[/* UnsubscriptionError */ "a"](errors); - } - } - }; - Subscription.prototype.add = function (teardown) { - var _a; - if (teardown && teardown !== this) { - if (this.closed) { - execFinalizer(teardown); - } - else { - if (teardown instanceof Subscription) { - if (teardown.closed || teardown._hasParent(this)) { - return; - } - teardown._addParent(this); - } - (this._finalizers = (_a = this._finalizers) !== null && _a !== void 0 ? _a : []).push(teardown); - } - } - }; - Subscription.prototype._hasParent = function (parent) { - var _parentage = this._parentage; - return _parentage === parent || (Array.isArray(_parentage) && _parentage.includes(parent)); - }; - Subscription.prototype._addParent = function (parent) { - var _parentage = this._parentage; - this._parentage = Array.isArray(_parentage) ? (_parentage.push(parent), _parentage) : _parentage ? [_parentage, parent] : parent; - }; - Subscription.prototype._removeParent = function (parent) { - var _parentage = this._parentage; - if (_parentage === parent) { - this._parentage = null; - } - else if (Array.isArray(_parentage)) { - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_3__[/* arrRemove */ "a"])(_parentage, parent); - } - }; - Subscription.prototype.remove = function (teardown) { - var _finalizers = this._finalizers; - _finalizers && Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_3__[/* arrRemove */ "a"])(_finalizers, teardown); - if (teardown instanceof Subscription) { - teardown._removeParent(this); - } - }; - Subscription.EMPTY = (function () { - var empty = new Subscription(); - empty.closed = true; - return empty; - })(); - return Subscription; -}()); - -var EMPTY_SUBSCRIPTION = Subscription.EMPTY; -function isSubscription(value) { - return (value instanceof Subscription || - (value && 'closed' in value && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(value.remove) && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(value.add) && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(value.unsubscribe))); -} -function execFinalizer(finalizer) { - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(finalizer)) { - finalizer(); - } - else { - finalizer.unsubscribe(); - } -} -//# sourceMappingURL=Subscription.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/config.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return config; }); -var config = { - onUnhandledError: null, - onStoppedNotification: null, - Promise: undefined, - useDeprecatedSynchronousErrorHandling: false, - useDeprecatedNextContext: false, -}; -//# sourceMappingURL=config.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/firstValueFrom.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return firstValueFrom; }); -/* harmony import */ var _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js"); -/* harmony import */ var _Subscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscriber.js"); - - -function firstValueFrom(source, config) { - var hasConfig = typeof config === 'object'; - return new Promise(function (resolve, reject) { - var subscriber = new _Subscriber__WEBPACK_IMPORTED_MODULE_1__[/* SafeSubscriber */ "a"]({ - next: function (value) { - resolve(value); - subscriber.unsubscribe(); - }, - error: reject, - complete: function () { - if (hasConfig) { - resolve(config.defaultValue); - } - else { - reject(new _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__[/* EmptyError */ "a"]()); - } - }, - }); - source.subscribe(subscriber); - }); -} -//# sourceMappingURL=firstValueFrom.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/lastValueFrom.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return lastValueFrom; }); -/* harmony import */ var _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js"); - -function lastValueFrom(source, config) { - var hasConfig = typeof config === 'object'; - return new Promise(function (resolve, reject) { - var _hasValue = false; - var _value; - source.subscribe({ - next: function (value) { - _value = value; - _hasValue = true; - }, - error: reject, - complete: function () { - if (_hasValue) { - resolve(_value); - } - else if (hasConfig) { - resolve(config.defaultValue); - } - else { - reject(new _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__[/* EmptyError */ "a"]()); - } - }, - }); - }); -} -//# sourceMappingURL=lastValueFrom.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/ConnectableObservable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return ConnectableObservable; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _operators_refCount__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/refCount.js"); -/* harmony import */ var _operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - - - - - -var ConnectableObservable = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(ConnectableObservable, _super); - function ConnectableObservable(source, subjectFactory) { - var _this = _super.call(this) || this; - _this.source = source; - _this.subjectFactory = subjectFactory; - _this._subject = null; - _this._refCount = 0; - _this._connection = null; - if (Object(_util_lift__WEBPACK_IMPORTED_MODULE_5__[/* hasLift */ "a"])(source)) { - _this.lift = source.lift; - } - return _this; - } - ConnectableObservable.prototype._subscribe = function (subscriber) { - return this.getSubject().subscribe(subscriber); - }; - ConnectableObservable.prototype.getSubject = function () { - var subject = this._subject; - if (!subject || subject.isStopped) { - this._subject = this.subjectFactory(); - } - return this._subject; - }; - ConnectableObservable.prototype._teardown = function () { - this._refCount = 0; - var _connection = this._connection; - this._subject = this._connection = null; - _connection === null || _connection === void 0 ? void 0 : _connection.unsubscribe(); - }; - ConnectableObservable.prototype.connect = function () { - var _this = this; - var connection = this._connection; - if (!connection) { - connection = this._connection = new _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* Subscription */ "b"](); - var subject_1 = this.getSubject(); - connection.add(this.source.subscribe(Object(_operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subject_1, undefined, function () { - _this._teardown(); - subject_1.complete(); - }, function (err) { - _this._teardown(); - subject_1.error(err); - }, function () { return _this._teardown(); }))); - if (connection.closed) { - this._connection = null; - connection = _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* Subscription */ "b"].EMPTY; - } - } - return connection; - }; - ConnectableObservable.prototype.refCount = function () { - return Object(_operators_refCount__WEBPACK_IMPORTED_MODULE_3__[/* refCount */ "a"])()(this); - }; - return ConnectableObservable; -}(_Observable__WEBPACK_IMPORTED_MODULE_1__[/* Observable */ "a"])); - -//# sourceMappingURL=ConnectableObservable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/bindCallback.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return bindCallback; }); -/* harmony import */ var _bindCallbackInternals__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/bindCallbackInternals.js"); - -function bindCallback(callbackFunc, resultSelector, scheduler) { - return Object(_bindCallbackInternals__WEBPACK_IMPORTED_MODULE_0__[/* bindCallbackInternals */ "a"])(false, callbackFunc, resultSelector, scheduler); -} -//# sourceMappingURL=bindCallback.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/bindCallbackInternals.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return bindCallbackInternals; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_isScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isScheduler.js"); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _operators_subscribeOn__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/subscribeOn.js"); -/* harmony import */ var _util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js"); -/* harmony import */ var _operators_observeOn__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/observeOn.js"); -/* harmony import */ var _AsyncSubject__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/AsyncSubject.js"); - - - - - - - -function bindCallbackInternals(isNodeStyle, callbackFunc, resultSelector, scheduler) { - if (resultSelector) { - if (Object(_util_isScheduler__WEBPACK_IMPORTED_MODULE_1__[/* isScheduler */ "a"])(resultSelector)) { - scheduler = resultSelector; - } - else { - return function () { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - return bindCallbackInternals(isNodeStyle, callbackFunc, scheduler) - .apply(this, args) - .pipe(Object(_util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_4__[/* mapOneOrManyArgs */ "a"])(resultSelector)); - }; - } - } - if (scheduler) { - return function () { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - return bindCallbackInternals(isNodeStyle, callbackFunc) - .apply(this, args) - .pipe(Object(_operators_subscribeOn__WEBPACK_IMPORTED_MODULE_3__[/* subscribeOn */ "a"])(scheduler), Object(_operators_observeOn__WEBPACK_IMPORTED_MODULE_5__[/* observeOn */ "a"])(scheduler)); - }; - } - return function () { - var _this = this; - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var subject = new _AsyncSubject__WEBPACK_IMPORTED_MODULE_6__[/* AsyncSubject */ "a"](); - var uninitialized = true; - return new _Observable__WEBPACK_IMPORTED_MODULE_2__[/* Observable */ "a"](function (subscriber) { - var subs = subject.subscribe(subscriber); - if (uninitialized) { - uninitialized = false; - var isAsync_1 = false; - var isComplete_1 = false; - callbackFunc.apply(_this, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])(Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args)), [ - function () { - var results = []; - for (var _i = 0; _i < arguments.length; _i++) { - results[_i] = arguments[_i]; - } - if (isNodeStyle) { - var err = results.shift(); - if (err != null) { - subject.error(err); - return; - } - } - subject.next(1 < results.length ? results : results[0]); - isComplete_1 = true; - if (isAsync_1) { - subject.complete(); - } - }, - ])); - if (isComplete_1) { - subject.complete(); - } - isAsync_1 = true; - } - return subs; - }); - }; -} -//# sourceMappingURL=bindCallbackInternals.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/bindNodeCallback.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return bindNodeCallback; }); -/* harmony import */ var _bindCallbackInternals__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/bindCallbackInternals.js"); - -function bindNodeCallback(callbackFunc, resultSelector, scheduler) { - return Object(_bindCallbackInternals__WEBPACK_IMPORTED_MODULE_0__[/* bindCallbackInternals */ "a"])(true, callbackFunc, resultSelector, scheduler); -} -//# sourceMappingURL=bindNodeCallback.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/combineLatest.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return combineLatest; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return combineLatestInit; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _util_argsArgArrayOrObject__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsArgArrayOrObject.js"); -/* harmony import */ var _from__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony import */ var _util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _util_createObject__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createObject.js"); -/* harmony import */ var _operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); - - - - - - - - - -function combineLatest() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var scheduler = Object(_util_args__WEBPACK_IMPORTED_MODULE_5__[/* popScheduler */ "c"])(args); - var resultSelector = Object(_util_args__WEBPACK_IMPORTED_MODULE_5__[/* popResultSelector */ "b"])(args); - var _a = Object(_util_argsArgArrayOrObject__WEBPACK_IMPORTED_MODULE_1__[/* argsArgArrayOrObject */ "a"])(args), observables = _a.args, keys = _a.keys; - if (observables.length === 0) { - return Object(_from__WEBPACK_IMPORTED_MODULE_2__[/* from */ "a"])([], scheduler); - } - var result = new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](combineLatestInit(observables, scheduler, keys - ? - function (values) { return Object(_util_createObject__WEBPACK_IMPORTED_MODULE_6__[/* createObject */ "a"])(keys, values); } - : - _util_identity__WEBPACK_IMPORTED_MODULE_3__[/* identity */ "a"])); - return resultSelector ? result.pipe(Object(_util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_4__[/* mapOneOrManyArgs */ "a"])(resultSelector)) : result; -} -function combineLatestInit(observables, scheduler, valueTransform) { - if (valueTransform === void 0) { valueTransform = _util_identity__WEBPACK_IMPORTED_MODULE_3__[/* identity */ "a"]; } - return function (subscriber) { - maybeSchedule(scheduler, function () { - var length = observables.length; - var values = new Array(length); - var active = length; - var remainingFirstValues = length; - var _loop_1 = function (i) { - maybeSchedule(scheduler, function () { - var source = Object(_from__WEBPACK_IMPORTED_MODULE_2__[/* from */ "a"])(observables[i], scheduler); - var hasFirstValue = false; - source.subscribe(Object(_operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_7__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - values[i] = value; - if (!hasFirstValue) { - hasFirstValue = true; - remainingFirstValues--; - } - if (!remainingFirstValues) { - subscriber.next(valueTransform(values.slice())); - } - }, function () { - if (!--active) { - subscriber.complete(); - } - })); - }, subscriber); - }; - for (var i = 0; i < length; i++) { - _loop_1(i); - } - }, subscriber); - }; -} -function maybeSchedule(scheduler, execute, subscription) { - if (scheduler) { - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_8__[/* executeSchedule */ "a"])(subscription, scheduler, execute); - } - else { - execute(); - } -} -//# sourceMappingURL=combineLatest.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/concat.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return concat; }); -/* harmony import */ var _operators_concatAll__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatAll.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _from__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); - - - -function concat() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - return Object(_operators_concatAll__WEBPACK_IMPORTED_MODULE_0__[/* concatAll */ "a"])()(Object(_from__WEBPACK_IMPORTED_MODULE_2__[/* from */ "a"])(args, Object(_util_args__WEBPACK_IMPORTED_MODULE_1__[/* popScheduler */ "c"])(args))); -} -//# sourceMappingURL=concat.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/connectable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return connectable; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _defer__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/defer.js"); - - - -var DEFAULT_CONFIG = { - connector: function () { return new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"](); }, - resetOnDisconnect: true, -}; -function connectable(source, config) { - if (config === void 0) { config = DEFAULT_CONFIG; } - var connection = null; - var connector = config.connector, _a = config.resetOnDisconnect, resetOnDisconnect = _a === void 0 ? true : _a; - var subject = connector(); - var result = new _Observable__WEBPACK_IMPORTED_MODULE_1__[/* Observable */ "a"](function (subscriber) { - return subject.subscribe(subscriber); - }); - result.connect = function () { - if (!connection || connection.closed) { - connection = Object(_defer__WEBPACK_IMPORTED_MODULE_2__[/* defer */ "a"])(function () { return source; }).subscribe(subject); - if (resetOnDisconnect) { - connection.add(function () { return (subject = connector()); }); - } - } - return connection; - }; - return result; -} -//# sourceMappingURL=connectable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/defer.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return defer; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - -function defer(observableFactory) { - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - Object(_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(observableFactory()).subscribe(subscriber); - }); -} -//# sourceMappingURL=defer.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/dom/animationFrames.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return animationFrames; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _scheduler_performanceTimestampProvider__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/performanceTimestampProvider.js"); -/* harmony import */ var _scheduler_animationFrameProvider__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/animationFrameProvider.js"); - - - - -function animationFrames(timestampProvider) { - return timestampProvider ? animationFramesFactory(timestampProvider) : DEFAULT_ANIMATION_FRAMES; -} -function animationFramesFactory(timestampProvider) { - var schedule = _scheduler_animationFrameProvider__WEBPACK_IMPORTED_MODULE_3__[/* animationFrameProvider */ "a"].schedule; - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - var subscription = new _Subscription__WEBPACK_IMPORTED_MODULE_1__[/* Subscription */ "b"](); - var provider = timestampProvider || _scheduler_performanceTimestampProvider__WEBPACK_IMPORTED_MODULE_2__[/* performanceTimestampProvider */ "a"]; - var start = provider.now(); - var run = function (timestamp) { - var now = provider.now(); - subscriber.next({ - timestamp: timestampProvider ? now : timestamp, - elapsed: now - start, - }); - if (!subscriber.closed) { - subscription.add(schedule(run)); - } - }; - subscription.add(schedule(run)); - return subscription; - }); -} -var DEFAULT_ANIMATION_FRAMES = animationFramesFactory(); -//# sourceMappingURL=animationFrames.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/empty.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return EMPTY; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return empty; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); - -var EMPTY = new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { return subscriber.complete(); }); -function empty(scheduler) { - return scheduler ? emptyScheduled(scheduler) : EMPTY; -} -function emptyScheduled(scheduler) { - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { return scheduler.schedule(function () { return subscriber.complete(); }); }); -} -//# sourceMappingURL=empty.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/forkJoin.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return forkJoin; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _util_argsArgArrayOrObject__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsArgArrayOrObject.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js"); -/* harmony import */ var _util_createObject__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createObject.js"); - - - - - - - -function forkJoin() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var resultSelector = Object(_util_args__WEBPACK_IMPORTED_MODULE_3__[/* popResultSelector */ "b"])(args); - var _a = Object(_util_argsArgArrayOrObject__WEBPACK_IMPORTED_MODULE_1__[/* argsArgArrayOrObject */ "a"])(args), sources = _a.args, keys = _a.keys; - var result = new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - var length = sources.length; - if (!length) { - subscriber.complete(); - return; - } - var values = new Array(length); - var remainingCompletions = length; - var remainingEmissions = length; - var _loop_1 = function (sourceIndex) { - var hasValue = false; - Object(_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(sources[sourceIndex]).subscribe(Object(_operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - if (!hasValue) { - hasValue = true; - remainingEmissions--; - } - values[sourceIndex] = value; - }, function () { return remainingCompletions--; }, undefined, function () { - if (!remainingCompletions || !hasValue) { - if (!remainingEmissions) { - subscriber.next(keys ? Object(_util_createObject__WEBPACK_IMPORTED_MODULE_6__[/* createObject */ "a"])(keys, values) : values); - } - subscriber.complete(); - } - })); - }; - for (var sourceIndex = 0; sourceIndex < length; sourceIndex++) { - _loop_1(sourceIndex); - } - }); - return resultSelector ? result.pipe(Object(_util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_5__[/* mapOneOrManyArgs */ "a"])(resultSelector)) : result; -} -//# sourceMappingURL=forkJoin.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/from.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return from; }); -/* harmony import */ var _scheduled_scheduled__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduled.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - -function from(input, scheduler) { - return scheduler ? Object(_scheduled_scheduled__WEBPACK_IMPORTED_MODULE_0__[/* scheduled */ "a"])(input, scheduler) : Object(_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(input); -} -//# sourceMappingURL=from.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/fromEvent.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return fromEvent; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _operators_mergeMap__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); -/* harmony import */ var _util_isArrayLike__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isArrayLike.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js"); - - - - - - - -var nodeEventEmitterMethods = ['addListener', 'removeListener']; -var eventTargetMethods = ['addEventListener', 'removeEventListener']; -var jqueryMethods = ['on', 'off']; -function fromEvent(target, eventName, options, resultSelector) { - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(options)) { - resultSelector = options; - options = undefined; - } - if (resultSelector) { - return fromEvent(target, eventName, options).pipe(Object(_util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_6__[/* mapOneOrManyArgs */ "a"])(resultSelector)); - } - var _a = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(isEventTarget(target) - ? eventTargetMethods.map(function (methodName) { return function (handler) { return target[methodName](eventName, handler, options); }; }) - : - isNodeStyleEventEmitter(target) - ? nodeEventEmitterMethods.map(toCommonHandlerRegistry(target, eventName)) - : isJQueryStyleEventEmitter(target) - ? jqueryMethods.map(toCommonHandlerRegistry(target, eventName)) - : [], 2), add = _a[0], remove = _a[1]; - if (!add) { - if (Object(_util_isArrayLike__WEBPACK_IMPORTED_MODULE_4__[/* isArrayLike */ "a"])(target)) { - return Object(_operators_mergeMap__WEBPACK_IMPORTED_MODULE_3__[/* mergeMap */ "a"])(function (subTarget) { return fromEvent(subTarget, eventName, options); })(Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(target)); - } - } - if (!add) { - throw new TypeError('Invalid event target'); - } - return new _Observable__WEBPACK_IMPORTED_MODULE_2__[/* Observable */ "a"](function (subscriber) { - var handler = function () { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - return subscriber.next(1 < args.length ? args : args[0]); - }; - add(handler); - return function () { return remove(handler); }; - }); -} -function toCommonHandlerRegistry(target, eventName) { - return function (methodName) { return function (handler) { return target[methodName](eventName, handler); }; }; -} -function isNodeStyleEventEmitter(target) { - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(target.addListener) && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(target.removeListener); -} -function isJQueryStyleEventEmitter(target) { - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(target.on) && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(target.off); -} -function isEventTarget(target) { - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(target.addEventListener) && Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_5__[/* isFunction */ "a"])(target.removeEventListener); -} -//# sourceMappingURL=fromEvent.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/fromEventPattern.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return fromEventPattern; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js"); - - - -function fromEventPattern(addHandler, removeHandler, resultSelector) { - if (resultSelector) { - return fromEventPattern(addHandler, removeHandler).pipe(Object(_util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_2__[/* mapOneOrManyArgs */ "a"])(resultSelector)); - } - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - var handler = function () { - var e = []; - for (var _i = 0; _i < arguments.length; _i++) { - e[_i] = arguments[_i]; - } - return subscriber.next(e.length === 1 ? e[0] : e); - }; - var retValue = addHandler(handler); - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(removeHandler) ? function () { return removeHandler(handler, retValue); } : undefined; - }); -} -//# sourceMappingURL=fromEventPattern.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/fromSubscribable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return fromSubscribable; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); - -function fromSubscribable(subscribable) { - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { return subscribable.subscribe(subscriber); }); -} -//# sourceMappingURL=fromSubscribable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/generate.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return generate; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony import */ var _util_isScheduler__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isScheduler.js"); -/* harmony import */ var _defer__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/defer.js"); -/* harmony import */ var _scheduled_scheduleIterable__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleIterable.js"); - - - - - -function generate(initialStateOrOptions, condition, iterate, resultSelectorOrScheduler, scheduler) { - var _a, _b; - var resultSelector; - var initialState; - if (arguments.length === 1) { - (_a = initialStateOrOptions, initialState = _a.initialState, condition = _a.condition, iterate = _a.iterate, _b = _a.resultSelector, resultSelector = _b === void 0 ? _util_identity__WEBPACK_IMPORTED_MODULE_1__[/* identity */ "a"] : _b, scheduler = _a.scheduler); - } - else { - initialState = initialStateOrOptions; - if (!resultSelectorOrScheduler || Object(_util_isScheduler__WEBPACK_IMPORTED_MODULE_2__[/* isScheduler */ "a"])(resultSelectorOrScheduler)) { - resultSelector = _util_identity__WEBPACK_IMPORTED_MODULE_1__[/* identity */ "a"]; - scheduler = resultSelectorOrScheduler; - } - else { - resultSelector = resultSelectorOrScheduler; - } - } - function gen() { - var state; - return Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __generator */ "f"])(this, function (_a) { - switch (_a.label) { - case 0: - state = initialState; - _a.label = 1; - case 1: - if (!(!condition || condition(state))) return [3, 4]; - return [4, resultSelector(state)]; - case 2: - _a.sent(); - _a.label = 3; - case 3: - state = iterate(state); - return [3, 1]; - case 4: return [2]; - } - }); - } - return Object(_defer__WEBPACK_IMPORTED_MODULE_3__[/* defer */ "a"])((scheduler - ? - function () { return Object(_scheduled_scheduleIterable__WEBPACK_IMPORTED_MODULE_4__[/* scheduleIterable */ "a"])(gen(), scheduler); } - : - gen)); -} -//# sourceMappingURL=generate.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/iif.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return iif; }); -/* harmony import */ var _defer__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/defer.js"); - -function iif(condition, trueResult, falseResult) { - return Object(_defer__WEBPACK_IMPORTED_MODULE_0__[/* defer */ "a"])(function () { return (condition() ? trueResult : falseResult); }); -} -//# sourceMappingURL=iif.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return innerFrom; }); -/* unused harmony export fromInteropObservable */ -/* unused harmony export fromArrayLike */ -/* unused harmony export fromPromise */ -/* unused harmony export fromIterable */ -/* unused harmony export fromAsyncIterable */ -/* unused harmony export fromReadableStreamLike */ -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_isArrayLike__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isArrayLike.js"); -/* harmony import */ var _util_isPromise__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isPromise.js"); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _util_isInteropObservable__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isInteropObservable.js"); -/* harmony import */ var _util_isAsyncIterable__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isAsyncIterable.js"); -/* harmony import */ var _util_throwUnobservableError__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/throwUnobservableError.js"); -/* harmony import */ var _util_isIterable__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isIterable.js"); -/* harmony import */ var _util_isReadableStreamLike__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isReadableStreamLike.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _util_reportUnhandledError__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/reportUnhandledError.js"); -/* harmony import */ var _symbol_observable__WEBPACK_IMPORTED_MODULE_11__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/symbol/observable.js"); - - - - - - - - - - - - -function innerFrom(input) { - if (input instanceof _Observable__WEBPACK_IMPORTED_MODULE_3__[/* Observable */ "a"]) { - return input; - } - if (input != null) { - if (Object(_util_isInteropObservable__WEBPACK_IMPORTED_MODULE_4__[/* isInteropObservable */ "a"])(input)) { - return fromInteropObservable(input); - } - if (Object(_util_isArrayLike__WEBPACK_IMPORTED_MODULE_1__[/* isArrayLike */ "a"])(input)) { - return fromArrayLike(input); - } - if (Object(_util_isPromise__WEBPACK_IMPORTED_MODULE_2__[/* isPromise */ "a"])(input)) { - return fromPromise(input); - } - if (Object(_util_isAsyncIterable__WEBPACK_IMPORTED_MODULE_5__[/* isAsyncIterable */ "a"])(input)) { - return fromAsyncIterable(input); - } - if (Object(_util_isIterable__WEBPACK_IMPORTED_MODULE_7__[/* isIterable */ "a"])(input)) { - return fromIterable(input); - } - if (Object(_util_isReadableStreamLike__WEBPACK_IMPORTED_MODULE_8__[/* isReadableStreamLike */ "a"])(input)) { - return fromReadableStreamLike(input); - } - } - throw Object(_util_throwUnobservableError__WEBPACK_IMPORTED_MODULE_6__[/* createInvalidObservableTypeError */ "a"])(input); -} -function fromInteropObservable(obj) { - return new _Observable__WEBPACK_IMPORTED_MODULE_3__[/* Observable */ "a"](function (subscriber) { - var obs = obj[_symbol_observable__WEBPACK_IMPORTED_MODULE_11__[/* observable */ "a"]](); - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_9__[/* isFunction */ "a"])(obs.subscribe)) { - return obs.subscribe(subscriber); - } - throw new TypeError('Provided object does not correctly implement Symbol.observable'); - }); -} -function fromArrayLike(array) { - return new _Observable__WEBPACK_IMPORTED_MODULE_3__[/* Observable */ "a"](function (subscriber) { - for (var i = 0; i < array.length && !subscriber.closed; i++) { - subscriber.next(array[i]); - } - subscriber.complete(); - }); -} -function fromPromise(promise) { - return new _Observable__WEBPACK_IMPORTED_MODULE_3__[/* Observable */ "a"](function (subscriber) { - promise - .then(function (value) { - if (!subscriber.closed) { - subscriber.next(value); - subscriber.complete(); - } - }, function (err) { return subscriber.error(err); }) - .then(null, _util_reportUnhandledError__WEBPACK_IMPORTED_MODULE_10__[/* reportUnhandledError */ "a"]); - }); -} -function fromIterable(iterable) { - return new _Observable__WEBPACK_IMPORTED_MODULE_3__[/* Observable */ "a"](function (subscriber) { - var e_1, _a; - try { - for (var iterable_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(iterable), iterable_1_1 = iterable_1.next(); !iterable_1_1.done; iterable_1_1 = iterable_1.next()) { - var value = iterable_1_1.value; - subscriber.next(value); - if (subscriber.closed) { - return; - } - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (iterable_1_1 && !iterable_1_1.done && (_a = iterable_1.return)) _a.call(iterable_1); - } - finally { if (e_1) throw e_1.error; } - } - subscriber.complete(); - }); -} -function fromAsyncIterable(asyncIterable) { - return new _Observable__WEBPACK_IMPORTED_MODULE_3__[/* Observable */ "a"](function (subscriber) { - process(asyncIterable, subscriber).catch(function (err) { return subscriber.error(err); }); - }); -} -function fromReadableStreamLike(readableStream) { - return fromAsyncIterable(Object(_util_isReadableStreamLike__WEBPACK_IMPORTED_MODULE_8__[/* readableStreamLikeToAsyncGenerator */ "b"])(readableStream)); -} -function process(asyncIterable, subscriber) { - var asyncIterable_1, asyncIterable_1_1; - var e_2, _a; - return Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __awaiter */ "d"])(this, void 0, void 0, function () { - var value, e_2_1; - return Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __generator */ "f"])(this, function (_b) { - switch (_b.label) { - case 0: - _b.trys.push([0, 5, 6, 11]); - asyncIterable_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __asyncValues */ "b"])(asyncIterable); - _b.label = 1; - case 1: return [4, asyncIterable_1.next()]; - case 2: - if (!(asyncIterable_1_1 = _b.sent(), !asyncIterable_1_1.done)) return [3, 4]; - value = asyncIterable_1_1.value; - subscriber.next(value); - if (subscriber.closed) { - return [2]; - } - _b.label = 3; - case 3: return [3, 1]; - case 4: return [3, 11]; - case 5: - e_2_1 = _b.sent(); - e_2 = { error: e_2_1 }; - return [3, 11]; - case 6: - _b.trys.push([6, , 9, 10]); - if (!(asyncIterable_1_1 && !asyncIterable_1_1.done && (_a = asyncIterable_1.return))) return [3, 8]; - return [4, _a.call(asyncIterable_1)]; - case 7: - _b.sent(); - _b.label = 8; - case 8: return [3, 10]; - case 9: - if (e_2) throw e_2.error; - return [7]; - case 10: return [7]; - case 11: - subscriber.complete(); - return [2]; - } - }); - }); -} -//# sourceMappingURL=innerFrom.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/interval.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return interval; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _timer__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/timer.js"); - - -function interval(period, scheduler) { - if (period === void 0) { period = 0; } - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"]; } - if (period < 0) { - period = 0; - } - return Object(_timer__WEBPACK_IMPORTED_MODULE_1__[/* timer */ "a"])(period, period, scheduler); -} -//# sourceMappingURL=interval.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/merge.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return merge; }); -/* harmony import */ var _operators_mergeAll__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeAll.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _empty__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _from__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); - - - - - -function merge() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var scheduler = Object(_util_args__WEBPACK_IMPORTED_MODULE_3__[/* popScheduler */ "c"])(args); - var concurrent = Object(_util_args__WEBPACK_IMPORTED_MODULE_3__[/* popNumber */ "a"])(args, Infinity); - var sources = args; - return !sources.length - ? - _empty__WEBPACK_IMPORTED_MODULE_2__[/* EMPTY */ "a"] - : sources.length === 1 - ? - Object(_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(sources[0]) - : - Object(_operators_mergeAll__WEBPACK_IMPORTED_MODULE_0__[/* mergeAll */ "a"])(concurrent)(Object(_from__WEBPACK_IMPORTED_MODULE_4__[/* from */ "a"])(sources, scheduler)); -} -//# sourceMappingURL=merge.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/never.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return NEVER; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return never; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); - - -var NEVER = new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](_util_noop__WEBPACK_IMPORTED_MODULE_1__[/* noop */ "a"]); -function never() { - return NEVER; -} -//# sourceMappingURL=never.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/of.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return of; }); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _from__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); - - -function of() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var scheduler = Object(_util_args__WEBPACK_IMPORTED_MODULE_0__[/* popScheduler */ "c"])(args); - return Object(_from__WEBPACK_IMPORTED_MODULE_1__[/* from */ "a"])(args, scheduler); -} -//# sourceMappingURL=of.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/onErrorResumeNext.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return onErrorResumeNext; }); -/* harmony import */ var _empty__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony import */ var _operators_onErrorResumeNext__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/onErrorResumeNext.js"); -/* harmony import */ var _util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js"); - - - -function onErrorResumeNext() { - var sources = []; - for (var _i = 0; _i < arguments.length; _i++) { - sources[_i] = arguments[_i]; - } - return Object(_operators_onErrorResumeNext__WEBPACK_IMPORTED_MODULE_1__[/* onErrorResumeNext */ "a"])(Object(_util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_2__[/* argsOrArgArray */ "a"])(sources))(_empty__WEBPACK_IMPORTED_MODULE_0__[/* EMPTY */ "a"]); -} -//# sourceMappingURL=onErrorResumeNext.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/pairs.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return pairs; }); -/* harmony import */ var _from__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); - -function pairs(obj, scheduler) { - return Object(_from__WEBPACK_IMPORTED_MODULE_0__[/* from */ "a"])(Object.entries(obj), scheduler); -} -//# sourceMappingURL=pairs.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/partition.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return partition; }); -/* harmony import */ var _util_not__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/not.js"); -/* harmony import */ var _operators_filter__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - - -function partition(source, predicate, thisArg) { - return [Object(_operators_filter__WEBPACK_IMPORTED_MODULE_1__[/* filter */ "a"])(predicate, thisArg)(Object(_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(source)), Object(_operators_filter__WEBPACK_IMPORTED_MODULE_1__[/* filter */ "a"])(Object(_util_not__WEBPACK_IMPORTED_MODULE_0__[/* not */ "a"])(predicate, thisArg))(Object(_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(source))]; -} -//# sourceMappingURL=partition.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/race.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return race; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return raceInit; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js"); -/* harmony import */ var _operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - - -function race() { - var sources = []; - for (var _i = 0; _i < arguments.length; _i++) { - sources[_i] = arguments[_i]; - } - sources = Object(_util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_2__[/* argsOrArgArray */ "a"])(sources); - return sources.length === 1 ? Object(_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(sources[0]) : new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](raceInit(sources)); -} -function raceInit(sources) { - return function (subscriber) { - var subscriptions = []; - var _loop_1 = function (i) { - subscriptions.push(Object(_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(sources[i]).subscribe(Object(_operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - if (subscriptions) { - for (var s = 0; s < subscriptions.length; s++) { - s !== i && subscriptions[s].unsubscribe(); - } - subscriptions = null; - } - subscriber.next(value); - }))); - }; - for (var i = 0; subscriptions && !subscriber.closed && i < sources.length; i++) { - _loop_1(i); - } - }; -} -//# sourceMappingURL=race.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/range.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return range; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _empty__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); - - -function range(start, count, scheduler) { - if (count == null) { - count = start; - start = 0; - } - if (count <= 0) { - return _empty__WEBPACK_IMPORTED_MODULE_1__[/* EMPTY */ "a"]; - } - var end = count + start; - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](scheduler - ? - function (subscriber) { - var n = start; - return scheduler.schedule(function () { - if (n < end) { - subscriber.next(n++); - this.schedule(); - } - else { - subscriber.complete(); - } - }); - } - : - function (subscriber) { - var n = start; - while (n < end && !subscriber.closed) { - subscriber.next(n++); - } - subscriber.complete(); - }); -} -//# sourceMappingURL=range.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/throwError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return throwError; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function throwError(errorOrErrorFactory, scheduler) { - var errorFactory = Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(errorOrErrorFactory) ? errorOrErrorFactory : function () { return errorOrErrorFactory; }; - var init = function (subscriber) { return subscriber.error(errorFactory()); }; - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](scheduler ? function (subscriber) { return scheduler.schedule(init, 0, subscriber); } : init); -} -//# sourceMappingURL=throwError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/timer.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return timer; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _util_isScheduler__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isScheduler.js"); -/* harmony import */ var _util_isDate__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isDate.js"); - - - - -function timer(dueTime, intervalOrScheduler, scheduler) { - if (dueTime === void 0) { dueTime = 0; } - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_1__[/* async */ "a"]; } - var intervalDuration = -1; - if (intervalOrScheduler != null) { - if (Object(_util_isScheduler__WEBPACK_IMPORTED_MODULE_2__[/* isScheduler */ "a"])(intervalOrScheduler)) { - scheduler = intervalOrScheduler; - } - else { - intervalDuration = intervalOrScheduler; - } - } - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - var due = Object(_util_isDate__WEBPACK_IMPORTED_MODULE_3__[/* isValidDate */ "a"])(dueTime) ? +dueTime - scheduler.now() : dueTime; - if (due < 0) { - due = 0; - } - var n = 0; - return scheduler.schedule(function () { - if (!subscriber.closed) { - subscriber.next(n++); - if (0 <= intervalDuration) { - this.schedule(undefined, intervalDuration); - } - else { - subscriber.complete(); - } - } - }, due); - }); -} -//# sourceMappingURL=timer.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/using.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return using; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _empty__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); - - - -function using(resourceFactory, observableFactory) { - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - var resource = resourceFactory(); - var result = observableFactory(resource); - var source = result ? Object(_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(result) : _empty__WEBPACK_IMPORTED_MODULE_2__[/* EMPTY */ "a"]; - source.subscribe(subscriber); - return function () { - if (resource) { - resource.unsubscribe(); - } - }; - }); -} -//# sourceMappingURL=using.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/observable/zip.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return zip; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _innerFrom__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js"); -/* harmony import */ var _empty__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony import */ var _operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); - - - - - - - -function zip() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var resultSelector = Object(_util_args__WEBPACK_IMPORTED_MODULE_6__[/* popResultSelector */ "b"])(args); - var sources = Object(_util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_3__[/* argsOrArgArray */ "a"])(args); - return sources.length - ? new _Observable__WEBPACK_IMPORTED_MODULE_1__[/* Observable */ "a"](function (subscriber) { - var buffers = sources.map(function () { return []; }); - var completed = sources.map(function () { return false; }); - subscriber.add(function () { - buffers = completed = null; - }); - var _loop_1 = function (sourceIndex) { - Object(_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(sources[sourceIndex]).subscribe(Object(_operators_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - buffers[sourceIndex].push(value); - if (buffers.every(function (buffer) { return buffer.length; })) { - var result = buffers.map(function (buffer) { return buffer.shift(); }); - subscriber.next(resultSelector ? resultSelector.apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(result))) : result); - if (buffers.some(function (buffer, i) { return !buffer.length && completed[i]; })) { - subscriber.complete(); - } - } - }, function () { - completed[sourceIndex] = true; - !buffers[sourceIndex].length && subscriber.complete(); - })); - }; - for (var sourceIndex = 0; !subscriber.closed && sourceIndex < sources.length; sourceIndex++) { - _loop_1(sourceIndex); - } - return function () { - buffers = completed = null; - }; - }) - : _empty__WEBPACK_IMPORTED_MODULE_4__[/* EMPTY */ "a"]; -} -//# sourceMappingURL=zip.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return createOperatorSubscriber; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return OperatorSubscriber; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscriber.js"); - - -function createOperatorSubscriber(destination, onNext, onComplete, onError, onFinalize) { - return new OperatorSubscriber(destination, onNext, onComplete, onError, onFinalize); -} -var OperatorSubscriber = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(OperatorSubscriber, _super); - function OperatorSubscriber(destination, onNext, onComplete, onError, onFinalize, shouldUnsubscribe) { - var _this = _super.call(this, destination) || this; - _this.onFinalize = onFinalize; - _this.shouldUnsubscribe = shouldUnsubscribe; - _this._next = onNext - ? function (value) { - try { - onNext(value); - } - catch (err) { - destination.error(err); - } - } - : _super.prototype._next; - _this._error = onError - ? function (err) { - try { - onError(err); - } - catch (err) { - destination.error(err); - } - finally { - this.unsubscribe(); - } - } - : _super.prototype._error; - _this._complete = onComplete - ? function () { - try { - onComplete(); - } - catch (err) { - destination.error(err); - } - finally { - this.unsubscribe(); - } - } - : _super.prototype._complete; - return _this; - } - OperatorSubscriber.prototype.unsubscribe = function () { - var _a; - if (!this.shouldUnsubscribe || this.shouldUnsubscribe()) { - var closed_1 = this.closed; - _super.prototype.unsubscribe.call(this); - !closed_1 && ((_a = this.onFinalize) === null || _a === void 0 ? void 0 : _a.call(this)); - } - }; - return OperatorSubscriber; -}(_Subscriber__WEBPACK_IMPORTED_MODULE_1__[/* Subscriber */ "b"])); - -//# sourceMappingURL=OperatorSubscriber.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/audit.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return audit; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function audit(durationSelector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var hasValue = false; - var lastValue = null; - var durationSubscriber = null; - var isComplete = false; - var endDuration = function () { - durationSubscriber === null || durationSubscriber === void 0 ? void 0 : durationSubscriber.unsubscribe(); - durationSubscriber = null; - if (hasValue) { - hasValue = false; - var value = lastValue; - lastValue = null; - subscriber.next(value); - } - isComplete && subscriber.complete(); - }; - var cleanupDuration = function () { - durationSubscriber = null; - isComplete && subscriber.complete(); - }; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - hasValue = true; - lastValue = value; - if (!durationSubscriber) { - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(durationSelector(value)).subscribe((durationSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, endDuration, cleanupDuration))); - } - }, function () { - isComplete = true; - (!hasValue || !durationSubscriber || durationSubscriber.closed) && subscriber.complete(); - })); - }); -} -//# sourceMappingURL=audit.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/auditTime.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return auditTime; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _audit__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/audit.js"); -/* harmony import */ var _observable_timer__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/timer.js"); - - - -function auditTime(duration, scheduler) { - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"]; } - return Object(_audit__WEBPACK_IMPORTED_MODULE_1__[/* audit */ "a"])(function () { return Object(_observable_timer__WEBPACK_IMPORTED_MODULE_2__[/* timer */ "a"])(duration, scheduler); }); -} -//# sourceMappingURL=auditTime.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/buffer.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return buffer; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function buffer(closingNotifier) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var currentBuffer = []; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return currentBuffer.push(value); }, function () { - subscriber.next(currentBuffer); - subscriber.complete(); - })); - closingNotifier.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - var b = currentBuffer; - currentBuffer = []; - subscriber.next(b); - }, _util_noop__WEBPACK_IMPORTED_MODULE_1__[/* noop */ "a"])); - return function () { - currentBuffer = null; - }; - }); -} -//# sourceMappingURL=buffer.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/bufferCount.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return bufferCount; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); - - - - -function bufferCount(bufferSize, startBufferEvery) { - if (startBufferEvery === void 0) { startBufferEvery = null; } - startBufferEvery = startBufferEvery !== null && startBufferEvery !== void 0 ? startBufferEvery : bufferSize; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var buffers = []; - var count = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var e_1, _a, e_2, _b; - var toEmit = null; - if (count++ % startBufferEvery === 0) { - buffers.push([]); - } - try { - for (var buffers_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(buffers), buffers_1_1 = buffers_1.next(); !buffers_1_1.done; buffers_1_1 = buffers_1.next()) { - var buffer = buffers_1_1.value; - buffer.push(value); - if (bufferSize <= buffer.length) { - toEmit = toEmit !== null && toEmit !== void 0 ? toEmit : []; - toEmit.push(buffer); - } - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (buffers_1_1 && !buffers_1_1.done && (_a = buffers_1.return)) _a.call(buffers_1); - } - finally { if (e_1) throw e_1.error; } - } - if (toEmit) { - try { - for (var toEmit_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(toEmit), toEmit_1_1 = toEmit_1.next(); !toEmit_1_1.done; toEmit_1_1 = toEmit_1.next()) { - var buffer = toEmit_1_1.value; - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_3__[/* arrRemove */ "a"])(buffers, buffer); - subscriber.next(buffer); - } - } - catch (e_2_1) { e_2 = { error: e_2_1 }; } - finally { - try { - if (toEmit_1_1 && !toEmit_1_1.done && (_b = toEmit_1.return)) _b.call(toEmit_1); - } - finally { if (e_2) throw e_2.error; } - } - } - }, function () { - var e_3, _a; - try { - for (var buffers_2 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(buffers), buffers_2_1 = buffers_2.next(); !buffers_2_1.done; buffers_2_1 = buffers_2.next()) { - var buffer = buffers_2_1.value; - subscriber.next(buffer); - } - } - catch (e_3_1) { e_3 = { error: e_3_1 }; } - finally { - try { - if (buffers_2_1 && !buffers_2_1.done && (_a = buffers_2.return)) _a.call(buffers_2); - } - finally { if (e_3) throw e_3.error; } - } - subscriber.complete(); - }, undefined, function () { - buffers = null; - })); - }); -} -//# sourceMappingURL=bufferCount.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/bufferTime.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return bufferTime; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); - - - - - - - - -function bufferTime(bufferTimeSpan) { - var _a, _b; - var otherArgs = []; - for (var _i = 1; _i < arguments.length; _i++) { - otherArgs[_i - 1] = arguments[_i]; - } - var scheduler = (_a = Object(_util_args__WEBPACK_IMPORTED_MODULE_6__[/* popScheduler */ "c"])(otherArgs)) !== null && _a !== void 0 ? _a : _scheduler_async__WEBPACK_IMPORTED_MODULE_5__[/* asyncScheduler */ "b"]; - var bufferCreationInterval = (_b = otherArgs[0]) !== null && _b !== void 0 ? _b : null; - var maxBufferSize = otherArgs[1] || Infinity; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var bufferRecords = []; - var restartOnEmit = false; - var emit = function (record) { - var buffer = record.buffer, subs = record.subs; - subs.unsubscribe(); - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_4__[/* arrRemove */ "a"])(bufferRecords, record); - subscriber.next(buffer); - restartOnEmit && startBuffer(); - }; - var startBuffer = function () { - if (bufferRecords) { - var subs = new _Subscription__WEBPACK_IMPORTED_MODULE_1__[/* Subscription */ "b"](); - subscriber.add(subs); - var buffer = []; - var record_1 = { - buffer: buffer, - subs: subs, - }; - bufferRecords.push(record_1); - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_7__[/* executeSchedule */ "a"])(subs, scheduler, function () { return emit(record_1); }, bufferTimeSpan); - } - }; - if (bufferCreationInterval !== null && bufferCreationInterval >= 0) { - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_7__[/* executeSchedule */ "a"])(subscriber, scheduler, startBuffer, bufferCreationInterval, true); - } - else { - restartOnEmit = true; - } - startBuffer(); - var bufferTimeSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var e_1, _a; - var recordsCopy = bufferRecords.slice(); - try { - for (var recordsCopy_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(recordsCopy), recordsCopy_1_1 = recordsCopy_1.next(); !recordsCopy_1_1.done; recordsCopy_1_1 = recordsCopy_1.next()) { - var record = recordsCopy_1_1.value; - var buffer = record.buffer; - buffer.push(value); - maxBufferSize <= buffer.length && emit(record); - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (recordsCopy_1_1 && !recordsCopy_1_1.done && (_a = recordsCopy_1.return)) _a.call(recordsCopy_1); - } - finally { if (e_1) throw e_1.error; } - } - }, function () { - while (bufferRecords === null || bufferRecords === void 0 ? void 0 : bufferRecords.length) { - subscriber.next(bufferRecords.shift().buffer); - } - bufferTimeSubscriber === null || bufferTimeSubscriber === void 0 ? void 0 : bufferTimeSubscriber.unsubscribe(); - subscriber.complete(); - subscriber.unsubscribe(); - }, undefined, function () { return (bufferRecords = null); }); - source.subscribe(bufferTimeSubscriber); - }); -} -//# sourceMappingURL=bufferTime.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/bufferToggle.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return bufferToggle; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); - - - - - - - -function bufferToggle(openings, closingSelector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var buffers = []; - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(openings).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subscriber, function (openValue) { - var buffer = []; - buffers.push(buffer); - var closingSubscription = new _Subscription__WEBPACK_IMPORTED_MODULE_1__[/* Subscription */ "b"](); - var emitBuffer = function () { - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_6__[/* arrRemove */ "a"])(buffers, buffer); - subscriber.next(buffer); - closingSubscription.unsubscribe(); - }; - closingSubscription.add(Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(closingSelector(openValue)).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subscriber, emitBuffer, _util_noop__WEBPACK_IMPORTED_MODULE_5__[/* noop */ "a"]))); - }, _util_noop__WEBPACK_IMPORTED_MODULE_5__[/* noop */ "a"])); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var e_1, _a; - try { - for (var buffers_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(buffers), buffers_1_1 = buffers_1.next(); !buffers_1_1.done; buffers_1_1 = buffers_1.next()) { - var buffer = buffers_1_1.value; - buffer.push(value); - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (buffers_1_1 && !buffers_1_1.done && (_a = buffers_1.return)) _a.call(buffers_1); - } - finally { if (e_1) throw e_1.error; } - } - }, function () { - while (buffers.length > 0) { - subscriber.next(buffers.shift()); - } - subscriber.complete(); - })); - }); -} -//# sourceMappingURL=bufferToggle.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/bufferWhen.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return bufferWhen; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - - - -function bufferWhen(closingSelector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var buffer = null; - var closingSubscriber = null; - var openBuffer = function () { - closingSubscriber === null || closingSubscriber === void 0 ? void 0 : closingSubscriber.unsubscribe(); - var b = buffer; - buffer = []; - b && subscriber.next(b); - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(closingSelector()).subscribe((closingSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, openBuffer, _util_noop__WEBPACK_IMPORTED_MODULE_1__[/* noop */ "a"]))); - }; - openBuffer(); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return buffer === null || buffer === void 0 ? void 0 : buffer.push(value); }, function () { - buffer && subscriber.next(buffer); - subscriber.complete(); - }, undefined, function () { return (buffer = closingSubscriber = null); })); - }); -} -//# sourceMappingURL=bufferWhen.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/catchError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return catchError; }); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - - -function catchError(selector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var innerSub = null; - var syncUnsub = false; - var handledResult; - innerSub = source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, undefined, function (err) { - handledResult = Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__[/* innerFrom */ "a"])(selector(err, catchError(selector)(source))); - if (innerSub) { - innerSub.unsubscribe(); - innerSub = null; - handledResult.subscribe(subscriber); - } - else { - syncUnsub = true; - } - })); - if (syncUnsub) { - innerSub.unsubscribe(); - innerSub = null; - handledResult.subscribe(subscriber); - } - }); -} -//# sourceMappingURL=catchError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/combineAll.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return combineAll; }); -/* harmony import */ var _combineLatestAll__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineLatestAll.js"); - -var combineAll = _combineLatestAll__WEBPACK_IMPORTED_MODULE_0__[/* combineLatestAll */ "a"]; -//# sourceMappingURL=combineAll.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/combineLatest.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return combineLatest; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _observable_combineLatest__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/combineLatest.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js"); -/* harmony import */ var _util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js"); -/* harmony import */ var _util_pipe__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/pipe.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); - - - - - - - -function combineLatest() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var resultSelector = Object(_util_args__WEBPACK_IMPORTED_MODULE_6__[/* popResultSelector */ "b"])(args); - return resultSelector - ? Object(_util_pipe__WEBPACK_IMPORTED_MODULE_5__[/* pipe */ "a"])(combineLatest.apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))), Object(_util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_4__[/* mapOneOrManyArgs */ "a"])(resultSelector)) - : Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - Object(_observable_combineLatest__WEBPACK_IMPORTED_MODULE_1__[/* combineLatestInit */ "b"])(Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([source], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(Object(_util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_3__[/* argsOrArgArray */ "a"])(args))))(subscriber); - }); -} -//# sourceMappingURL=combineLatest.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/combineLatestAll.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return combineLatestAll; }); -/* harmony import */ var _observable_combineLatest__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/combineLatest.js"); -/* harmony import */ var _joinAllInternals__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/joinAllInternals.js"); - - -function combineLatestAll(project) { - return Object(_joinAllInternals__WEBPACK_IMPORTED_MODULE_1__[/* joinAllInternals */ "a"])(_observable_combineLatest__WEBPACK_IMPORTED_MODULE_0__[/* combineLatest */ "a"], project); -} -//# sourceMappingURL=combineLatestAll.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/combineLatestWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return combineLatestWith; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _combineLatest__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineLatest.js"); - - -function combineLatestWith() { - var otherSources = []; - for (var _i = 0; _i < arguments.length; _i++) { - otherSources[_i] = arguments[_i]; - } - return _combineLatest__WEBPACK_IMPORTED_MODULE_1__[/* combineLatest */ "a"].apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(otherSources))); -} -//# sourceMappingURL=combineLatestWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/concat.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return concat; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _concatAll__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatAll.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _observable_from__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); - - - - - -function concat() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var scheduler = Object(_util_args__WEBPACK_IMPORTED_MODULE_3__[/* popScheduler */ "c"])(args); - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - Object(_concatAll__WEBPACK_IMPORTED_MODULE_2__[/* concatAll */ "a"])()(Object(_observable_from__WEBPACK_IMPORTED_MODULE_4__[/* from */ "a"])(Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([source], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args)), scheduler)).subscribe(subscriber); - }); -} -//# sourceMappingURL=concat.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/concatAll.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return concatAll; }); -/* harmony import */ var _mergeAll__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeAll.js"); - -function concatAll() { - return Object(_mergeAll__WEBPACK_IMPORTED_MODULE_0__[/* mergeAll */ "a"])(1); -} -//# sourceMappingURL=concatAll.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/concatMap.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return concatMap; }); -/* harmony import */ var _mergeMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function concatMap(project, resultSelector) { - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(resultSelector) ? Object(_mergeMap__WEBPACK_IMPORTED_MODULE_0__[/* mergeMap */ "a"])(project, resultSelector, 1) : Object(_mergeMap__WEBPACK_IMPORTED_MODULE_0__[/* mergeMap */ "a"])(project, 1); -} -//# sourceMappingURL=concatMap.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/concatMapTo.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return concatMapTo; }); -/* harmony import */ var _concatMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatMap.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function concatMapTo(innerObservable, resultSelector) { - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(resultSelector) ? Object(_concatMap__WEBPACK_IMPORTED_MODULE_0__[/* concatMap */ "a"])(function () { return innerObservable; }, resultSelector) : Object(_concatMap__WEBPACK_IMPORTED_MODULE_0__[/* concatMap */ "a"])(function () { return innerObservable; }); -} -//# sourceMappingURL=concatMapTo.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/concatWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return concatWith; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _concat__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concat.js"); - - -function concatWith() { - var otherSources = []; - for (var _i = 0; _i < arguments.length; _i++) { - otherSources[_i] = arguments[_i]; - } - return _concat__WEBPACK_IMPORTED_MODULE_1__[/* concat */ "a"].apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(otherSources))); -} -//# sourceMappingURL=concatWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/connect.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return connect; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _observable_from__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _observable_fromSubscribable__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/fromSubscribable.js"); - - - - -var DEFAULT_CONFIG = { - connector: function () { return new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"](); }, -}; -function connect(selector, config) { - if (config === void 0) { config = DEFAULT_CONFIG; } - var connector = config.connector; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var subject = connector(); - Object(_observable_from__WEBPACK_IMPORTED_MODULE_1__[/* from */ "a"])(selector(Object(_observable_fromSubscribable__WEBPACK_IMPORTED_MODULE_3__[/* fromSubscribable */ "a"])(subject))).subscribe(subscriber); - subscriber.add(source.subscribe(subject)); - }); -} -//# sourceMappingURL=connect.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/count.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return count; }); -/* harmony import */ var _reduce__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/reduce.js"); - -function count(predicate) { - return Object(_reduce__WEBPACK_IMPORTED_MODULE_0__[/* reduce */ "a"])(function (total, value, i) { return (!predicate || predicate(value, i) ? total + 1 : total); }, 0); -} -//# sourceMappingURL=count.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/debounce.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return debounce; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - - - -function debounce(durationSelector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var hasValue = false; - var lastValue = null; - var durationSubscriber = null; - var emit = function () { - durationSubscriber === null || durationSubscriber === void 0 ? void 0 : durationSubscriber.unsubscribe(); - durationSubscriber = null; - if (hasValue) { - hasValue = false; - var value = lastValue; - lastValue = null; - subscriber.next(value); - } - }; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - durationSubscriber === null || durationSubscriber === void 0 ? void 0 : durationSubscriber.unsubscribe(); - hasValue = true; - lastValue = value; - durationSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, emit, _util_noop__WEBPACK_IMPORTED_MODULE_1__[/* noop */ "a"]); - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(durationSelector(value)).subscribe(durationSubscriber); - }, function () { - emit(); - subscriber.complete(); - }, undefined, function () { - lastValue = durationSubscriber = null; - })); - }); -} -//# sourceMappingURL=debounce.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/debounceTime.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return debounceTime; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function debounceTime(dueTime, scheduler) { - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"]; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var activeTask = null; - var lastValue = null; - var lastTime = null; - var emit = function () { - if (activeTask) { - activeTask.unsubscribe(); - activeTask = null; - var value = lastValue; - lastValue = null; - subscriber.next(value); - } - }; - function emitWhenIdle() { - var targetTime = lastTime + dueTime; - var now = scheduler.now(); - if (now < targetTime) { - activeTask = this.schedule(undefined, targetTime - now); - subscriber.add(activeTask); - return; - } - emit(); - } - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - lastValue = value; - lastTime = scheduler.now(); - if (!activeTask) { - activeTask = scheduler.schedule(emitWhenIdle, dueTime); - subscriber.add(activeTask); - } - }, function () { - emit(); - subscriber.complete(); - }, undefined, function () { - lastValue = activeTask = null; - })); - }); -} -//# sourceMappingURL=debounceTime.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/defaultIfEmpty.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return defaultIfEmpty; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function defaultIfEmpty(defaultValue) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var hasValue = false; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - hasValue = true; - subscriber.next(value); - }, function () { - if (!hasValue) { - subscriber.next(defaultValue); - } - subscriber.complete(); - })); - }); -} -//# sourceMappingURL=defaultIfEmpty.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/delay.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return delay; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _delayWhen__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/delayWhen.js"); -/* harmony import */ var _observable_timer__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/timer.js"); - - - -function delay(due, scheduler) { - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"]; } - var duration = Object(_observable_timer__WEBPACK_IMPORTED_MODULE_2__[/* timer */ "a"])(due, scheduler); - return Object(_delayWhen__WEBPACK_IMPORTED_MODULE_1__[/* delayWhen */ "a"])(function () { return duration; }); -} -//# sourceMappingURL=delay.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/delayWhen.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return delayWhen; }); -/* harmony import */ var _observable_concat__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/concat.js"); -/* harmony import */ var _take__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/take.js"); -/* harmony import */ var _ignoreElements__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/ignoreElements.js"); -/* harmony import */ var _mapTo__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mapTo.js"); -/* harmony import */ var _mergeMap__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); - - - - - -function delayWhen(delayDurationSelector, subscriptionDelay) { - if (subscriptionDelay) { - return function (source) { - return Object(_observable_concat__WEBPACK_IMPORTED_MODULE_0__[/* concat */ "a"])(subscriptionDelay.pipe(Object(_take__WEBPACK_IMPORTED_MODULE_1__[/* take */ "a"])(1), Object(_ignoreElements__WEBPACK_IMPORTED_MODULE_2__[/* ignoreElements */ "a"])()), source.pipe(delayWhen(delayDurationSelector))); - }; - } - return Object(_mergeMap__WEBPACK_IMPORTED_MODULE_4__[/* mergeMap */ "a"])(function (value, index) { return delayDurationSelector(value, index).pipe(Object(_take__WEBPACK_IMPORTED_MODULE_1__[/* take */ "a"])(1), Object(_mapTo__WEBPACK_IMPORTED_MODULE_3__[/* mapTo */ "a"])(value)); }); -} -//# sourceMappingURL=delayWhen.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/dematerialize.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return dematerialize; }); -/* harmony import */ var _Notification__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Notification.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function dematerialize() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (notification) { return Object(_Notification__WEBPACK_IMPORTED_MODULE_0__[/* observeNotification */ "c"])(notification, subscriber); })); - }); -} -//# sourceMappingURL=dematerialize.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/distinct.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return distinct; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); - - - -function distinct(keySelector, flushes) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var distinctKeys = new Set(); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var key = keySelector ? keySelector(value) : value; - if (!distinctKeys.has(key)) { - distinctKeys.add(key); - subscriber.next(value); - } - })); - flushes === null || flushes === void 0 ? void 0 : flushes.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function () { return distinctKeys.clear(); }, _util_noop__WEBPACK_IMPORTED_MODULE_2__[/* noop */ "a"])); - }); -} -//# sourceMappingURL=distinct.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/distinctUntilChanged.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return distinctUntilChanged; }); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function distinctUntilChanged(comparator, keySelector) { - if (keySelector === void 0) { keySelector = _util_identity__WEBPACK_IMPORTED_MODULE_0__[/* identity */ "a"]; } - comparator = comparator !== null && comparator !== void 0 ? comparator : defaultCompare; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var previousKey; - var first = true; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var currentKey = keySelector(value); - if (first || !comparator(previousKey, currentKey)) { - first = false; - previousKey = currentKey; - subscriber.next(value); - } - })); - }); -} -function defaultCompare(a, b) { - return a === b; -} -//# sourceMappingURL=distinctUntilChanged.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/distinctUntilKeyChanged.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return distinctUntilKeyChanged; }); -/* harmony import */ var _distinctUntilChanged__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/distinctUntilChanged.js"); - -function distinctUntilKeyChanged(key, compare) { - return Object(_distinctUntilChanged__WEBPACK_IMPORTED_MODULE_0__[/* distinctUntilChanged */ "a"])(function (x, y) { return compare ? compare(x[key], y[key]) : x[key] === y[key]; }); -} -//# sourceMappingURL=distinctUntilKeyChanged.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/elementAt.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return elementAt; }); -/* harmony import */ var _util_ArgumentOutOfRangeError__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/ArgumentOutOfRangeError.js"); -/* harmony import */ var _filter__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); -/* harmony import */ var _throwIfEmpty__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throwIfEmpty.js"); -/* harmony import */ var _defaultIfEmpty__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/defaultIfEmpty.js"); -/* harmony import */ var _take__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/take.js"); - - - - - -function elementAt(index, defaultValue) { - if (index < 0) { - throw new _util_ArgumentOutOfRangeError__WEBPACK_IMPORTED_MODULE_0__[/* ArgumentOutOfRangeError */ "a"](); - } - var hasDefaultValue = arguments.length >= 2; - return function (source) { - return source.pipe(Object(_filter__WEBPACK_IMPORTED_MODULE_1__[/* filter */ "a"])(function (v, i) { return i === index; }), Object(_take__WEBPACK_IMPORTED_MODULE_4__[/* take */ "a"])(1), hasDefaultValue ? Object(_defaultIfEmpty__WEBPACK_IMPORTED_MODULE_3__[/* defaultIfEmpty */ "a"])(defaultValue) : Object(_throwIfEmpty__WEBPACK_IMPORTED_MODULE_2__[/* throwIfEmpty */ "a"])(function () { return new _util_ArgumentOutOfRangeError__WEBPACK_IMPORTED_MODULE_0__[/* ArgumentOutOfRangeError */ "a"](); })); - }; -} -//# sourceMappingURL=elementAt.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/endWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return endWith; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _observable_concat__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/concat.js"); -/* harmony import */ var _observable_of__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/of.js"); - - - -function endWith() { - var values = []; - for (var _i = 0; _i < arguments.length; _i++) { - values[_i] = arguments[_i]; - } - return function (source) { return Object(_observable_concat__WEBPACK_IMPORTED_MODULE_1__[/* concat */ "a"])(source, _observable_of__WEBPACK_IMPORTED_MODULE_2__[/* of */ "a"].apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(values)))); }; -} -//# sourceMappingURL=endWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/every.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return every; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function every(predicate, thisArg) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - if (!predicate.call(thisArg, value, index++, source)) { - subscriber.next(false); - subscriber.complete(); - } - }, function () { - subscriber.next(true); - subscriber.complete(); - })); - }); -} -//# sourceMappingURL=every.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/exhaust.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return exhaust; }); -/* harmony import */ var _exhaustAll__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/exhaustAll.js"); - -var exhaust = _exhaustAll__WEBPACK_IMPORTED_MODULE_0__[/* exhaustAll */ "a"]; -//# sourceMappingURL=exhaust.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/exhaustAll.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return exhaustAll; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function exhaustAll() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var isComplete = false; - var innerSub = null; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (inner) { - if (!innerSub) { - innerSub = Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(inner).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, function () { - innerSub = null; - isComplete && subscriber.complete(); - })); - } - }, function () { - isComplete = true; - !innerSub && subscriber.complete(); - })); - }); -} -//# sourceMappingURL=exhaustAll.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/exhaustMap.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return exhaustMap; }); -/* harmony import */ var _map__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - - -function exhaustMap(project, resultSelector) { - if (resultSelector) { - return function (source) { - return source.pipe(exhaustMap(function (a, i) { return Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(project(a, i)).pipe(Object(_map__WEBPACK_IMPORTED_MODULE_0__[/* map */ "a"])(function (b, ii) { return resultSelector(a, b, i, ii); })); })); - }; - } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var index = 0; - var innerSub = null; - var isComplete = false; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__[/* createOperatorSubscriber */ "b"])(subscriber, function (outerValue) { - if (!innerSub) { - innerSub = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, function () { - innerSub = null; - isComplete && subscriber.complete(); - }); - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(project(outerValue, index++)).subscribe(innerSub); - } - }, function () { - isComplete = true; - !innerSub && subscriber.complete(); - })); - }); -} -//# sourceMappingURL=exhaustMap.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/expand.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return expand; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _mergeInternals__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeInternals.js"); - - -function expand(project, concurrent, scheduler) { - if (concurrent === void 0) { concurrent = Infinity; } - concurrent = (concurrent || 0) < 1 ? Infinity : concurrent; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - return Object(_mergeInternals__WEBPACK_IMPORTED_MODULE_1__[/* mergeInternals */ "a"])(source, subscriber, project, concurrent, undefined, true, scheduler); - }); -} -//# sourceMappingURL=expand.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/filter.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return filter; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function filter(predicate, thisArg) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return predicate.call(thisArg, value, index++) && subscriber.next(value); })); - }); -} -//# sourceMappingURL=filter.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/finalize.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return finalize; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - -function finalize(callback) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - try { - source.subscribe(subscriber); - } - finally { - subscriber.add(callback); - } - }); -} -//# sourceMappingURL=finalize.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/find.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return find; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return createFind; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function find(predicate, thisArg) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(createFind(predicate, thisArg, 'value')); -} -function createFind(predicate, thisArg, emit) { - var findIndex = emit === 'index'; - return function (source, subscriber) { - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var i = index++; - if (predicate.call(thisArg, value, i, source)) { - subscriber.next(findIndex ? i : value); - subscriber.complete(); - } - }, function () { - subscriber.next(findIndex ? -1 : undefined); - subscriber.complete(); - })); - }; -} -//# sourceMappingURL=find.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/findIndex.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return findIndex; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _find__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/find.js"); - - -function findIndex(predicate, thisArg) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(Object(_find__WEBPACK_IMPORTED_MODULE_1__[/* createFind */ "a"])(predicate, thisArg, 'index')); -} -//# sourceMappingURL=findIndex.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/first.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return first; }); -/* harmony import */ var _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js"); -/* harmony import */ var _filter__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); -/* harmony import */ var _take__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/take.js"); -/* harmony import */ var _defaultIfEmpty__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/defaultIfEmpty.js"); -/* harmony import */ var _throwIfEmpty__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throwIfEmpty.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); - - - - - - -function first(predicate, defaultValue) { - var hasDefaultValue = arguments.length >= 2; - return function (source) { - return source.pipe(predicate ? Object(_filter__WEBPACK_IMPORTED_MODULE_1__[/* filter */ "a"])(function (v, i) { return predicate(v, i, source); }) : _util_identity__WEBPACK_IMPORTED_MODULE_5__[/* identity */ "a"], Object(_take__WEBPACK_IMPORTED_MODULE_2__[/* take */ "a"])(1), hasDefaultValue ? Object(_defaultIfEmpty__WEBPACK_IMPORTED_MODULE_3__[/* defaultIfEmpty */ "a"])(defaultValue) : Object(_throwIfEmpty__WEBPACK_IMPORTED_MODULE_4__[/* throwIfEmpty */ "a"])(function () { return new _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__[/* EmptyError */ "a"](); })); - }; -} -//# sourceMappingURL=first.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/flatMap.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return flatMap; }); -/* harmony import */ var _mergeMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); - -var flatMap = _mergeMap__WEBPACK_IMPORTED_MODULE_0__[/* mergeMap */ "a"]; -//# sourceMappingURL=flatMap.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/groupBy.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return groupBy; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - - - -function groupBy(keySelector, elementOrOptions, duration, connector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_3__[/* operate */ "b"])(function (source, subscriber) { - var element; - if (!elementOrOptions || typeof elementOrOptions === 'function') { - element = elementOrOptions; - } - else { - (duration = elementOrOptions.duration, element = elementOrOptions.element, connector = elementOrOptions.connector); - } - var groups = new Map(); - var notify = function (cb) { - groups.forEach(cb); - cb(subscriber); - }; - var handleError = function (err) { return notify(function (consumer) { return consumer.error(err); }); }; - var activeGroups = 0; - var teardownAttempted = false; - var groupBySourceSubscriber = new _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* OperatorSubscriber */ "a"](subscriber, function (value) { - try { - var key_1 = keySelector(value); - var group_1 = groups.get(key_1); - if (!group_1) { - groups.set(key_1, (group_1 = connector ? connector() : new _Subject__WEBPACK_IMPORTED_MODULE_2__[/* Subject */ "a"]())); - var grouped = createGroupedObservable(key_1, group_1); - subscriber.next(grouped); - if (duration) { - var durationSubscriber_1 = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(group_1, function () { - group_1.complete(); - durationSubscriber_1 === null || durationSubscriber_1 === void 0 ? void 0 : durationSubscriber_1.unsubscribe(); - }, undefined, undefined, function () { return groups.delete(key_1); }); - groupBySourceSubscriber.add(Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(duration(grouped)).subscribe(durationSubscriber_1)); - } - } - group_1.next(element ? element(value) : value); - } - catch (err) { - handleError(err); - } - }, function () { return notify(function (consumer) { return consumer.complete(); }); }, handleError, function () { return groups.clear(); }, function () { - teardownAttempted = true; - return activeGroups === 0; - }); - source.subscribe(groupBySourceSubscriber); - function createGroupedObservable(key, groupSubject) { - var result = new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (groupSubscriber) { - activeGroups++; - var innerSub = groupSubject.subscribe(groupSubscriber); - return function () { - innerSub.unsubscribe(); - --activeGroups === 0 && teardownAttempted && groupBySourceSubscriber.unsubscribe(); - }; - }); - result.key = key; - return result; - } - }); -} -//# sourceMappingURL=groupBy.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/ignoreElements.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return ignoreElements; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); - - - -function ignoreElements() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, _util_noop__WEBPACK_IMPORTED_MODULE_2__[/* noop */ "a"])); - }); -} -//# sourceMappingURL=ignoreElements.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/isEmpty.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isEmpty; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function isEmpty() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - subscriber.next(false); - subscriber.complete(); - }, function () { - subscriber.next(true); - subscriber.complete(); - })); - }); -} -//# sourceMappingURL=isEmpty.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/joinAllInternals.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return joinAllInternals; }); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony import */ var _util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js"); -/* harmony import */ var _util_pipe__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/pipe.js"); -/* harmony import */ var _mergeMap__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); -/* harmony import */ var _toArray__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/toArray.js"); - - - - - -function joinAllInternals(joinFn, project) { - return Object(_util_pipe__WEBPACK_IMPORTED_MODULE_2__[/* pipe */ "a"])(Object(_toArray__WEBPACK_IMPORTED_MODULE_4__[/* toArray */ "a"])(), Object(_mergeMap__WEBPACK_IMPORTED_MODULE_3__[/* mergeMap */ "a"])(function (sources) { return joinFn(sources); }), project ? Object(_util_mapOneOrManyArgs__WEBPACK_IMPORTED_MODULE_1__[/* mapOneOrManyArgs */ "a"])(project) : _util_identity__WEBPACK_IMPORTED_MODULE_0__[/* identity */ "a"]); -} -//# sourceMappingURL=joinAllInternals.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/last.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return last; }); -/* harmony import */ var _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js"); -/* harmony import */ var _filter__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); -/* harmony import */ var _takeLast__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/takeLast.js"); -/* harmony import */ var _throwIfEmpty__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throwIfEmpty.js"); -/* harmony import */ var _defaultIfEmpty__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/defaultIfEmpty.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); - - - - - - -function last(predicate, defaultValue) { - var hasDefaultValue = arguments.length >= 2; - return function (source) { - return source.pipe(predicate ? Object(_filter__WEBPACK_IMPORTED_MODULE_1__[/* filter */ "a"])(function (v, i) { return predicate(v, i, source); }) : _util_identity__WEBPACK_IMPORTED_MODULE_5__[/* identity */ "a"], Object(_takeLast__WEBPACK_IMPORTED_MODULE_2__[/* takeLast */ "a"])(1), hasDefaultValue ? Object(_defaultIfEmpty__WEBPACK_IMPORTED_MODULE_4__[/* defaultIfEmpty */ "a"])(defaultValue) : Object(_throwIfEmpty__WEBPACK_IMPORTED_MODULE_3__[/* throwIfEmpty */ "a"])(function () { return new _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__[/* EmptyError */ "a"](); })); - }; -} -//# sourceMappingURL=last.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/map.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return map; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function map(project, thisArg) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - subscriber.next(project.call(thisArg, value, index++)); - })); - }); -} -//# sourceMappingURL=map.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/mapTo.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mapTo; }); -/* harmony import */ var _map__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); - -function mapTo(value) { - return Object(_map__WEBPACK_IMPORTED_MODULE_0__[/* map */ "a"])(function () { return value; }); -} -//# sourceMappingURL=mapTo.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/materialize.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return materialize; }); -/* harmony import */ var _Notification__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Notification.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function materialize() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - subscriber.next(_Notification__WEBPACK_IMPORTED_MODULE_0__[/* Notification */ "a"].createNext(value)); - }, function () { - subscriber.next(_Notification__WEBPACK_IMPORTED_MODULE_0__[/* Notification */ "a"].createComplete()); - subscriber.complete(); - }, function (err) { - subscriber.next(_Notification__WEBPACK_IMPORTED_MODULE_0__[/* Notification */ "a"].createError(err)); - subscriber.complete(); - })); - }); -} -//# sourceMappingURL=materialize.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/max.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return max; }); -/* harmony import */ var _reduce__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/reduce.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function max(comparer) { - return Object(_reduce__WEBPACK_IMPORTED_MODULE_0__[/* reduce */ "a"])(Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(comparer) ? function (x, y) { return (comparer(x, y) > 0 ? x : y); } : function (x, y) { return (x > y ? x : y); }); -} -//# sourceMappingURL=max.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/merge.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return merge; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js"); -/* harmony import */ var _mergeAll__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeAll.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _observable_from__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); - - - - - - -function merge() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var scheduler = Object(_util_args__WEBPACK_IMPORTED_MODULE_4__[/* popScheduler */ "c"])(args); - var concurrent = Object(_util_args__WEBPACK_IMPORTED_MODULE_4__[/* popNumber */ "a"])(args, Infinity); - args = Object(_util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_2__[/* argsOrArgArray */ "a"])(args); - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - Object(_mergeAll__WEBPACK_IMPORTED_MODULE_3__[/* mergeAll */ "a"])(concurrent)(Object(_observable_from__WEBPACK_IMPORTED_MODULE_5__[/* from */ "a"])(Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([source], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args)), scheduler)).subscribe(subscriber); - }); -} -//# sourceMappingURL=merge.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/mergeAll.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mergeAll; }); -/* harmony import */ var _mergeMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); - - -function mergeAll(concurrent) { - if (concurrent === void 0) { concurrent = Infinity; } - return Object(_mergeMap__WEBPACK_IMPORTED_MODULE_0__[/* mergeMap */ "a"])(_util_identity__WEBPACK_IMPORTED_MODULE_1__[/* identity */ "a"], concurrent); -} -//# sourceMappingURL=mergeAll.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/mergeInternals.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mergeInternals; }); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function mergeInternals(source, subscriber, project, concurrent, onBeforeNext, expand, innerSubScheduler, additionalFinalizer) { - var buffer = []; - var active = 0; - var index = 0; - var isComplete = false; - var checkComplete = function () { - if (isComplete && !buffer.length && !active) { - subscriber.complete(); - } - }; - var outerNext = function (value) { return (active < concurrent ? doInnerSub(value) : buffer.push(value)); }; - var doInnerSub = function (value) { - expand && subscriber.next(value); - active++; - var innerComplete = false; - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__[/* innerFrom */ "a"])(project(value, index++)).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (innerValue) { - onBeforeNext === null || onBeforeNext === void 0 ? void 0 : onBeforeNext(innerValue); - if (expand) { - outerNext(innerValue); - } - else { - subscriber.next(innerValue); - } - }, function () { - innerComplete = true; - }, undefined, function () { - if (innerComplete) { - try { - active--; - var _loop_1 = function () { - var bufferedValue = buffer.shift(); - if (innerSubScheduler) { - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_1__[/* executeSchedule */ "a"])(subscriber, innerSubScheduler, function () { return doInnerSub(bufferedValue); }); - } - else { - doInnerSub(bufferedValue); - } - }; - while (buffer.length && active < concurrent) { - _loop_1(); - } - checkComplete(); - } - catch (err) { - subscriber.error(err); - } - } - })); - }; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, outerNext, function () { - isComplete = true; - checkComplete(); - })); - return function () { - additionalFinalizer === null || additionalFinalizer === void 0 ? void 0 : additionalFinalizer(); - }; -} -//# sourceMappingURL=mergeInternals.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mergeMap; }); -/* harmony import */ var _map__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _mergeInternals__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeInternals.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - - - - -function mergeMap(project, resultSelector, concurrent) { - if (concurrent === void 0) { concurrent = Infinity; } - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_4__[/* isFunction */ "a"])(resultSelector)) { - return mergeMap(function (a, i) { return Object(_map__WEBPACK_IMPORTED_MODULE_0__[/* map */ "a"])(function (b, ii) { return resultSelector(a, b, i, ii); })(Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_1__[/* innerFrom */ "a"])(project(a, i))); }, concurrent); - } - else if (typeof resultSelector === 'number') { - concurrent = resultSelector; - } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { return Object(_mergeInternals__WEBPACK_IMPORTED_MODULE_3__[/* mergeInternals */ "a"])(source, subscriber, project, concurrent); }); -} -//# sourceMappingURL=mergeMap.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/mergeMapTo.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mergeMapTo; }); -/* harmony import */ var _mergeMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function mergeMapTo(innerObservable, resultSelector, concurrent) { - if (concurrent === void 0) { concurrent = Infinity; } - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(resultSelector)) { - return Object(_mergeMap__WEBPACK_IMPORTED_MODULE_0__[/* mergeMap */ "a"])(function () { return innerObservable; }, resultSelector, concurrent); - } - if (typeof resultSelector === 'number') { - concurrent = resultSelector; - } - return Object(_mergeMap__WEBPACK_IMPORTED_MODULE_0__[/* mergeMap */ "a"])(function () { return innerObservable; }, concurrent); -} -//# sourceMappingURL=mergeMapTo.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/mergeScan.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mergeScan; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _mergeInternals__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeInternals.js"); - - -function mergeScan(accumulator, seed, concurrent) { - if (concurrent === void 0) { concurrent = Infinity; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var state = seed; - return Object(_mergeInternals__WEBPACK_IMPORTED_MODULE_1__[/* mergeInternals */ "a"])(source, subscriber, function (value, index) { return accumulator(state, value, index); }, concurrent, function (value) { - state = value; - }, false, undefined, function () { return (state = null); }); - }); -} -//# sourceMappingURL=mergeScan.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/mergeWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mergeWith; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _merge__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/merge.js"); - - -function mergeWith() { - var otherSources = []; - for (var _i = 0; _i < arguments.length; _i++) { - otherSources[_i] = arguments[_i]; - } - return _merge__WEBPACK_IMPORTED_MODULE_1__[/* merge */ "a"].apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(otherSources))); -} -//# sourceMappingURL=mergeWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/min.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return min; }); -/* harmony import */ var _reduce__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/reduce.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function min(comparer) { - return Object(_reduce__WEBPACK_IMPORTED_MODULE_0__[/* reduce */ "a"])(Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(comparer) ? function (x, y) { return (comparer(x, y) < 0 ? x : y); } : function (x, y) { return (x < y ? x : y); }); -} -//# sourceMappingURL=min.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/multicast.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return multicast; }); -/* harmony import */ var _observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/ConnectableObservable.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _connect__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/connect.js"); - - - -function multicast(subjectOrSubjectFactory, selector) { - var subjectFactory = Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(subjectOrSubjectFactory) ? subjectOrSubjectFactory : function () { return subjectOrSubjectFactory; }; - if (Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(selector)) { - return Object(_connect__WEBPACK_IMPORTED_MODULE_2__[/* connect */ "a"])(selector, { - connector: subjectFactory, - }); - } - return function (source) { return new _observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_0__[/* ConnectableObservable */ "a"](source, subjectFactory); }; -} -//# sourceMappingURL=multicast.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/observeOn.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return observeOn; }); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function observeOn(scheduler, delay) { - if (delay === void 0) { delay = 0; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_0__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { return subscriber.next(value); }, delay); }, function () { return Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_0__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { return subscriber.complete(); }, delay); }, function (err) { return Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_0__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { return subscriber.error(err); }, delay); })); - }); -} -//# sourceMappingURL=observeOn.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/onErrorResumeNext.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return onErrorResumeNext; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); - - - - - - -function onErrorResumeNext() { - var sources = []; - for (var _i = 0; _i < arguments.length; _i++) { - sources[_i] = arguments[_i]; - } - var nextSources = Object(_util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_3__[/* argsOrArgArray */ "a"])(sources); - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var remaining = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([source], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(nextSources)); - var subscribeNext = function () { - if (!subscriber.closed) { - if (remaining.length > 0) { - var nextSource = void 0; - try { - nextSource = Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(remaining.shift()); - } - catch (err) { - subscribeNext(); - return; - } - var innerSub = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, _util_noop__WEBPACK_IMPORTED_MODULE_5__[/* noop */ "a"], _util_noop__WEBPACK_IMPORTED_MODULE_5__[/* noop */ "a"]); - nextSource.subscribe(innerSub); - innerSub.add(subscribeNext); - } - else { - subscriber.complete(); - } - } - }; - subscribeNext(); - }); -} -//# sourceMappingURL=onErrorResumeNext.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/pairwise.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return pairwise; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function pairwise() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var prev; - var hasPrev = false; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var p = prev; - prev = value; - hasPrev && subscriber.next([p, value]); - hasPrev = true; - })); - }); -} -//# sourceMappingURL=pairwise.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/partition.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return partition; }); -/* harmony import */ var _util_not__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/not.js"); -/* harmony import */ var _filter__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); - - -function partition(predicate, thisArg) { - return function (source) { - return [Object(_filter__WEBPACK_IMPORTED_MODULE_1__[/* filter */ "a"])(predicate, thisArg)(source), Object(_filter__WEBPACK_IMPORTED_MODULE_1__[/* filter */ "a"])(Object(_util_not__WEBPACK_IMPORTED_MODULE_0__[/* not */ "a"])(predicate, thisArg))(source)]; - }; -} -//# sourceMappingURL=partition.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/pluck.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return pluck; }); -/* harmony import */ var _map__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); - -function pluck() { - var properties = []; - for (var _i = 0; _i < arguments.length; _i++) { - properties[_i] = arguments[_i]; - } - var length = properties.length; - if (length === 0) { - throw new Error('list of properties cannot be empty.'); - } - return Object(_map__WEBPACK_IMPORTED_MODULE_0__[/* map */ "a"])(function (x) { - var currentProp = x; - for (var i = 0; i < length; i++) { - var p = currentProp === null || currentProp === void 0 ? void 0 : currentProp[properties[i]]; - if (typeof p !== 'undefined') { - currentProp = p; - } - else { - return undefined; - } - } - return currentProp; - }); -} -//# sourceMappingURL=pluck.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/publish.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return publish; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _multicast__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/multicast.js"); -/* harmony import */ var _connect__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/connect.js"); - - - -function publish(selector) { - return selector ? function (source) { return Object(_connect__WEBPACK_IMPORTED_MODULE_2__[/* connect */ "a"])(selector)(source); } : function (source) { return Object(_multicast__WEBPACK_IMPORTED_MODULE_1__[/* multicast */ "a"])(new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"]())(source); }; -} -//# sourceMappingURL=publish.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/publishBehavior.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return publishBehavior; }); -/* harmony import */ var _BehaviorSubject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/BehaviorSubject.js"); -/* harmony import */ var _observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/ConnectableObservable.js"); - - -function publishBehavior(initialValue) { - return function (source) { - var subject = new _BehaviorSubject__WEBPACK_IMPORTED_MODULE_0__[/* BehaviorSubject */ "a"](initialValue); - return new _observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_1__[/* ConnectableObservable */ "a"](source, function () { return subject; }); - }; -} -//# sourceMappingURL=publishBehavior.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/publishLast.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return publishLast; }); -/* harmony import */ var _AsyncSubject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/AsyncSubject.js"); -/* harmony import */ var _observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/ConnectableObservable.js"); - - -function publishLast() { - return function (source) { - var subject = new _AsyncSubject__WEBPACK_IMPORTED_MODULE_0__[/* AsyncSubject */ "a"](); - return new _observable_ConnectableObservable__WEBPACK_IMPORTED_MODULE_1__[/* ConnectableObservable */ "a"](source, function () { return subject; }); - }; -} -//# sourceMappingURL=publishLast.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/publishReplay.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return publishReplay; }); -/* harmony import */ var _ReplaySubject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/ReplaySubject.js"); -/* harmony import */ var _multicast__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/multicast.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - - -function publishReplay(bufferSize, windowTime, selectorOrScheduler, timestampProvider) { - if (selectorOrScheduler && !Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_2__[/* isFunction */ "a"])(selectorOrScheduler)) { - timestampProvider = selectorOrScheduler; - } - var selector = Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_2__[/* isFunction */ "a"])(selectorOrScheduler) ? selectorOrScheduler : undefined; - return function (source) { return Object(_multicast__WEBPACK_IMPORTED_MODULE_1__[/* multicast */ "a"])(new _ReplaySubject__WEBPACK_IMPORTED_MODULE_0__[/* ReplaySubject */ "a"](bufferSize, windowTime, timestampProvider), selector)(source); }; -} -//# sourceMappingURL=publishReplay.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/race.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return race; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js"); -/* harmony import */ var _raceWith__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/raceWith.js"); - - - -function race() { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - return _raceWith__WEBPACK_IMPORTED_MODULE_2__[/* raceWith */ "a"].apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(Object(_util_argsOrArgArray__WEBPACK_IMPORTED_MODULE_1__[/* argsOrArgArray */ "a"])(args)))); -} -//# sourceMappingURL=race.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/raceWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return raceWith; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _observable_race__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/race.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); - - - - -function raceWith() { - var otherSources = []; - for (var _i = 0; _i < arguments.length; _i++) { - otherSources[_i] = arguments[_i]; - } - return !otherSources.length - ? _util_identity__WEBPACK_IMPORTED_MODULE_3__[/* identity */ "a"] - : Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - Object(_observable_race__WEBPACK_IMPORTED_MODULE_1__[/* raceInit */ "b"])(Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([source], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(otherSources)))(subscriber); - }); -} -//# sourceMappingURL=raceWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/reduce.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return reduce; }); -/* harmony import */ var _scanInternals__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/scanInternals.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - -function reduce(accumulator, seed) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(Object(_scanInternals__WEBPACK_IMPORTED_MODULE_0__[/* scanInternals */ "a"])(accumulator, seed, arguments.length >= 2, false, true)); -} -//# sourceMappingURL=reduce.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/refCount.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return refCount; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function refCount() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var connection = null; - source._refCount++; - var refCounter = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, undefined, undefined, function () { - if (!source || source._refCount <= 0 || 0 < --source._refCount) { - connection = null; - return; - } - var sharedConnection = source._connection; - var conn = connection; - connection = null; - if (sharedConnection && (!conn || sharedConnection === conn)) { - sharedConnection.unsubscribe(); - } - subscriber.unsubscribe(); - }); - source.subscribe(refCounter); - if (!refCounter.closed) { - connection = source.connect(); - } - }); -} -//# sourceMappingURL=refCount.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/repeat.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return repeat; }); -/* harmony import */ var _observable_empty__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _observable_timer__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/timer.js"); - - - - - -function repeat(countOrConfig) { - var _a; - var count = Infinity; - var delay; - if (countOrConfig != null) { - if (typeof countOrConfig === 'object') { - (_a = countOrConfig.count, count = _a === void 0 ? Infinity : _a, delay = countOrConfig.delay); - } - else { - count = countOrConfig; - } - } - return count <= 0 - ? function () { return _observable_empty__WEBPACK_IMPORTED_MODULE_0__[/* EMPTY */ "a"]; } - : Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var soFar = 0; - var sourceSub; - var resubscribe = function () { - sourceSub === null || sourceSub === void 0 ? void 0 : sourceSub.unsubscribe(); - sourceSub = null; - if (delay != null) { - var notifier = typeof delay === 'number' ? Object(_observable_timer__WEBPACK_IMPORTED_MODULE_4__[/* timer */ "a"])(delay) : Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(delay(soFar)); - var notifierSubscriber_1 = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - notifierSubscriber_1.unsubscribe(); - subscribeToSource(); - }); - notifier.subscribe(notifierSubscriber_1); - } - else { - subscribeToSource(); - } - }; - var subscribeToSource = function () { - var syncUnsub = false; - sourceSub = source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, function () { - if (++soFar < count) { - if (sourceSub) { - resubscribe(); - } - else { - syncUnsub = true; - } - } - else { - subscriber.complete(); - } - })); - if (syncUnsub) { - resubscribe(); - } - }; - subscribeToSource(); - }); -} -//# sourceMappingURL=repeat.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/repeatWhen.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return repeatWhen; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function repeatWhen(notifier) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var innerSub; - var syncResub = false; - var completions$; - var isNotifierComplete = false; - var isMainComplete = false; - var checkComplete = function () { return isMainComplete && isNotifierComplete && (subscriber.complete(), true); }; - var getCompletionSubject = function () { - if (!completions$) { - completions$ = new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"](); - notifier(completions$).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - if (innerSub) { - subscribeForRepeatWhen(); - } - else { - syncResub = true; - } - }, function () { - isNotifierComplete = true; - checkComplete(); - })); - } - return completions$; - }; - var subscribeForRepeatWhen = function () { - isMainComplete = false; - innerSub = source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, function () { - isMainComplete = true; - !checkComplete() && getCompletionSubject().next(); - })); - if (syncResub) { - innerSub.unsubscribe(); - innerSub = null; - syncResub = false; - subscribeForRepeatWhen(); - } - }; - subscribeForRepeatWhen(); - }); -} -//# sourceMappingURL=repeatWhen.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/retry.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return retry; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony import */ var _observable_timer__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/timer.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - - - - -function retry(configOrCount) { - if (configOrCount === void 0) { configOrCount = Infinity; } - var config; - if (configOrCount && typeof configOrCount === 'object') { - config = configOrCount; - } - else { - config = { - count: configOrCount, - }; - } - var _a = config.count, count = _a === void 0 ? Infinity : _a, delay = config.delay, _b = config.resetOnSuccess, resetOnSuccess = _b === void 0 ? false : _b; - return count <= 0 - ? _util_identity__WEBPACK_IMPORTED_MODULE_2__[/* identity */ "a"] - : Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var soFar = 0; - var innerSub; - var subscribeForRetry = function () { - var syncUnsub = false; - innerSub = source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - if (resetOnSuccess) { - soFar = 0; - } - subscriber.next(value); - }, undefined, function (err) { - if (soFar++ < count) { - var resub_1 = function () { - if (innerSub) { - innerSub.unsubscribe(); - innerSub = null; - subscribeForRetry(); - } - else { - syncUnsub = true; - } - }; - if (delay != null) { - var notifier = typeof delay === 'number' ? Object(_observable_timer__WEBPACK_IMPORTED_MODULE_3__[/* timer */ "a"])(delay) : Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_4__[/* innerFrom */ "a"])(delay(err, soFar)); - var notifierSubscriber_1 = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - notifierSubscriber_1.unsubscribe(); - resub_1(); - }, function () { - subscriber.complete(); - }); - notifier.subscribe(notifierSubscriber_1); - } - else { - resub_1(); - } - } - else { - subscriber.error(err); - } - })); - if (syncUnsub) { - innerSub.unsubscribe(); - innerSub = null; - subscribeForRetry(); - } - }; - subscribeForRetry(); - }); -} -//# sourceMappingURL=retry.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/retryWhen.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return retryWhen; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function retryWhen(notifier) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var innerSub; - var syncResub = false; - var errors$; - var subscribeForRetryWhen = function () { - innerSub = source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, undefined, undefined, function (err) { - if (!errors$) { - errors$ = new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"](); - notifier(errors$).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - return innerSub ? subscribeForRetryWhen() : (syncResub = true); - })); - } - if (errors$) { - errors$.next(err); - } - })); - if (syncResub) { - innerSub.unsubscribe(); - innerSub = null; - syncResub = false; - subscribeForRetryWhen(); - } - }; - subscribeForRetryWhen(); - }); -} -//# sourceMappingURL=retryWhen.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/sample.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return sample; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function sample(notifier) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var hasValue = false; - var lastValue = null; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - hasValue = true; - lastValue = value; - })); - notifier.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - if (hasValue) { - hasValue = false; - var value = lastValue; - lastValue = null; - subscriber.next(value); - } - }, _util_noop__WEBPACK_IMPORTED_MODULE_1__[/* noop */ "a"])); - }); -} -//# sourceMappingURL=sample.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/sampleTime.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return sampleTime; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _sample__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/sample.js"); -/* harmony import */ var _observable_interval__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/interval.js"); - - - -function sampleTime(period, scheduler) { - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"]; } - return Object(_sample__WEBPACK_IMPORTED_MODULE_1__[/* sample */ "a"])(Object(_observable_interval__WEBPACK_IMPORTED_MODULE_2__[/* interval */ "a"])(period, scheduler)); -} -//# sourceMappingURL=sampleTime.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/scan.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scan; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _scanInternals__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/scanInternals.js"); - - -function scan(accumulator, seed) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(Object(_scanInternals__WEBPACK_IMPORTED_MODULE_1__[/* scanInternals */ "a"])(accumulator, seed, arguments.length >= 2, true)); -} -//# sourceMappingURL=scan.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/scanInternals.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scanInternals; }); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - -function scanInternals(accumulator, seed, hasSeed, emitOnNext, emitBeforeComplete) { - return function (source, subscriber) { - var hasState = hasSeed; - var state = seed; - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_0__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var i = index++; - state = hasState - ? - accumulator(state, value, i) - : - ((hasState = true), value); - emitOnNext && subscriber.next(state); - }, emitBeforeComplete && - (function () { - hasState && subscriber.next(state); - subscriber.complete(); - }))); - }; -} -//# sourceMappingURL=scanInternals.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/sequenceEqual.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return sequenceEqual; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function sequenceEqual(compareTo, comparator) { - if (comparator === void 0) { comparator = function (a, b) { return a === b; }; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var aState = createState(); - var bState = createState(); - var emit = function (isEqual) { - subscriber.next(isEqual); - subscriber.complete(); - }; - var createSubscriber = function (selfState, otherState) { - var sequenceEqualSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (a) { - var buffer = otherState.buffer, complete = otherState.complete; - if (buffer.length === 0) { - complete ? emit(false) : selfState.buffer.push(a); - } - else { - !comparator(a, buffer.shift()) && emit(false); - } - }, function () { - selfState.complete = true; - var complete = otherState.complete, buffer = otherState.buffer; - complete && emit(buffer.length === 0); - sequenceEqualSubscriber === null || sequenceEqualSubscriber === void 0 ? void 0 : sequenceEqualSubscriber.unsubscribe(); - }); - return sequenceEqualSubscriber; - }; - source.subscribe(createSubscriber(aState, bState)); - compareTo.subscribe(createSubscriber(bState, aState)); - }); -} -function createState() { - return { - buffer: [], - complete: false, - }; -} -//# sourceMappingURL=sequenceEqual.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/share.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return share; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _observable_from__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/from.js"); -/* harmony import */ var _operators_take__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/take.js"); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _Subscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscriber.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - - - - - -function share(options) { - if (options === void 0) { options = {}; } - var _a = options.connector, connector = _a === void 0 ? function () { return new _Subject__WEBPACK_IMPORTED_MODULE_3__[/* Subject */ "a"](); } : _a, _b = options.resetOnError, resetOnError = _b === void 0 ? true : _b, _c = options.resetOnComplete, resetOnComplete = _c === void 0 ? true : _c, _d = options.resetOnRefCountZero, resetOnRefCountZero = _d === void 0 ? true : _d; - return function (wrapperSource) { - var connection = null; - var resetConnection = null; - var subject = null; - var refCount = 0; - var hasCompleted = false; - var hasErrored = false; - var cancelReset = function () { - resetConnection === null || resetConnection === void 0 ? void 0 : resetConnection.unsubscribe(); - resetConnection = null; - }; - var reset = function () { - cancelReset(); - connection = subject = null; - hasCompleted = hasErrored = false; - }; - var resetAndUnsubscribe = function () { - var conn = connection; - reset(); - conn === null || conn === void 0 ? void 0 : conn.unsubscribe(); - }; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_5__[/* operate */ "b"])(function (source, subscriber) { - refCount++; - if (!hasErrored && !hasCompleted) { - cancelReset(); - } - var dest = (subject = subject !== null && subject !== void 0 ? subject : connector()); - subscriber.add(function () { - refCount--; - if (refCount === 0 && !hasErrored && !hasCompleted) { - resetConnection = handleReset(resetAndUnsubscribe, resetOnRefCountZero); - } - }); - dest.subscribe(subscriber); - if (!connection) { - connection = new _Subscriber__WEBPACK_IMPORTED_MODULE_4__[/* SafeSubscriber */ "a"]({ - next: function (value) { return dest.next(value); }, - error: function (err) { - hasErrored = true; - cancelReset(); - resetConnection = handleReset(reset, resetOnError, err); - dest.error(err); - }, - complete: function () { - hasCompleted = true; - cancelReset(); - resetConnection = handleReset(reset, resetOnComplete); - dest.complete(); - }, - }); - Object(_observable_from__WEBPACK_IMPORTED_MODULE_1__[/* from */ "a"])(source).subscribe(connection); - } - })(wrapperSource); - }; -} -function handleReset(reset, on) { - var args = []; - for (var _i = 2; _i < arguments.length; _i++) { - args[_i - 2] = arguments[_i]; - } - if (on === true) { - reset(); - return null; - } - if (on === false) { - return null; - } - return on.apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))).pipe(Object(_operators_take__WEBPACK_IMPORTED_MODULE_2__[/* take */ "a"])(1)) - .subscribe(function () { return reset(); }); -} -//# sourceMappingURL=share.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/shareReplay.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return shareReplay; }); -/* harmony import */ var _ReplaySubject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/ReplaySubject.js"); -/* harmony import */ var _share__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/share.js"); - - -function shareReplay(configOrBufferSize, windowTime, scheduler) { - var _a, _b, _c; - var bufferSize; - var refCount = false; - if (configOrBufferSize && typeof configOrBufferSize === 'object') { - (_a = configOrBufferSize.bufferSize, bufferSize = _a === void 0 ? Infinity : _a, _b = configOrBufferSize.windowTime, windowTime = _b === void 0 ? Infinity : _b, _c = configOrBufferSize.refCount, refCount = _c === void 0 ? false : _c, scheduler = configOrBufferSize.scheduler); - } - else { - bufferSize = configOrBufferSize !== null && configOrBufferSize !== void 0 ? configOrBufferSize : Infinity; - } - return Object(_share__WEBPACK_IMPORTED_MODULE_1__[/* share */ "a"])({ - connector: function () { return new _ReplaySubject__WEBPACK_IMPORTED_MODULE_0__[/* ReplaySubject */ "a"](bufferSize, windowTime, scheduler); }, - resetOnError: true, - resetOnComplete: false, - resetOnRefCountZero: refCount, - }); -} -//# sourceMappingURL=shareReplay.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/single.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return single; }); -/* harmony import */ var _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js"); -/* harmony import */ var _util_SequenceError__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/SequenceError.js"); -/* harmony import */ var _util_NotFoundError__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/NotFoundError.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - - - -function single(predicate) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_3__[/* operate */ "b"])(function (source, subscriber) { - var hasValue = false; - var singleValue; - var seenValue = false; - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - seenValue = true; - if (!predicate || predicate(value, index++, source)) { - hasValue && subscriber.error(new _util_SequenceError__WEBPACK_IMPORTED_MODULE_1__[/* SequenceError */ "a"]('Too many matching values')); - hasValue = true; - singleValue = value; - } - }, function () { - if (hasValue) { - subscriber.next(singleValue); - subscriber.complete(); - } - else { - subscriber.error(seenValue ? new _util_NotFoundError__WEBPACK_IMPORTED_MODULE_2__[/* NotFoundError */ "a"]('No matching values') : new _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__[/* EmptyError */ "a"]()); - } - })); - }); -} -//# sourceMappingURL=single.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/skip.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return skip; }); -/* harmony import */ var _filter__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); - -function skip(count) { - return Object(_filter__WEBPACK_IMPORTED_MODULE_0__[/* filter */ "a"])(function (_, index) { return count <= index; }); -} -//# sourceMappingURL=skip.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/skipLast.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return skipLast; }); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function skipLast(skipCount) { - return skipCount <= 0 - ? - _util_identity__WEBPACK_IMPORTED_MODULE_0__[/* identity */ "a"] - : Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var ring = new Array(skipCount); - var seen = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var valueIndex = seen++; - if (valueIndex < skipCount) { - ring[valueIndex] = value; - } - else { - var index = valueIndex % skipCount; - var oldValue = ring[index]; - ring[index] = value; - subscriber.next(oldValue); - } - })); - return function () { - ring = null; - }; - }); -} -//# sourceMappingURL=skipLast.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/skipUntil.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return skipUntil; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); - - - - -function skipUntil(notifier) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var taking = false; - var skipSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - skipSubscriber === null || skipSubscriber === void 0 ? void 0 : skipSubscriber.unsubscribe(); - taking = true; - }, _util_noop__WEBPACK_IMPORTED_MODULE_3__[/* noop */ "a"]); - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(notifier).subscribe(skipSubscriber); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return taking && subscriber.next(value); })); - }); -} -//# sourceMappingURL=skipUntil.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/skipWhile.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return skipWhile; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function skipWhile(predicate) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var taking = false; - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return (taking || (taking = !predicate(value, index++))) && subscriber.next(value); })); - }); -} -//# sourceMappingURL=skipWhile.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/startWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return startWith; }); -/* harmony import */ var _observable_concat__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/concat.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - - -function startWith() { - var values = []; - for (var _i = 0; _i < arguments.length; _i++) { - values[_i] = arguments[_i]; - } - var scheduler = Object(_util_args__WEBPACK_IMPORTED_MODULE_1__[/* popScheduler */ "c"])(values); - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - (scheduler ? Object(_observable_concat__WEBPACK_IMPORTED_MODULE_0__[/* concat */ "a"])(values, source, scheduler) : Object(_observable_concat__WEBPACK_IMPORTED_MODULE_0__[/* concat */ "a"])(values, source)).subscribe(subscriber); - }); -} -//# sourceMappingURL=startWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/subscribeOn.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return subscribeOn; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - -function subscribeOn(scheduler, delay) { - if (delay === void 0) { delay = 0; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - subscriber.add(scheduler.schedule(function () { return source.subscribe(subscriber); }, delay)); - }); -} -//# sourceMappingURL=subscribeOn.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/switchAll.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return switchAll; }); -/* harmony import */ var _switchMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchMap.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); - - -function switchAll() { - return Object(_switchMap__WEBPACK_IMPORTED_MODULE_0__[/* switchMap */ "a"])(_util_identity__WEBPACK_IMPORTED_MODULE_1__[/* identity */ "a"]); -} -//# sourceMappingURL=switchAll.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/switchMap.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return switchMap; }); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function switchMap(project, resultSelector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var innerSubscriber = null; - var index = 0; - var isComplete = false; - var checkComplete = function () { return isComplete && !innerSubscriber && subscriber.complete(); }; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - innerSubscriber === null || innerSubscriber === void 0 ? void 0 : innerSubscriber.unsubscribe(); - var innerIndex = 0; - var outerIndex = index++; - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__[/* innerFrom */ "a"])(project(value, outerIndex)).subscribe((innerSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (innerValue) { return subscriber.next(resultSelector ? resultSelector(value, innerValue, outerIndex, innerIndex++) : innerValue); }, function () { - innerSubscriber = null; - checkComplete(); - }))); - }, function () { - isComplete = true; - checkComplete(); - })); - }); -} -//# sourceMappingURL=switchMap.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/switchMapTo.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return switchMapTo; }); -/* harmony import */ var _switchMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchMap.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function switchMapTo(innerObservable, resultSelector) { - return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(resultSelector) ? Object(_switchMap__WEBPACK_IMPORTED_MODULE_0__[/* switchMap */ "a"])(function () { return innerObservable; }, resultSelector) : Object(_switchMap__WEBPACK_IMPORTED_MODULE_0__[/* switchMap */ "a"])(function () { return innerObservable; }); -} -//# sourceMappingURL=switchMapTo.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/switchScan.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return switchScan; }); -/* harmony import */ var _switchMap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchMap.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - -function switchScan(accumulator, seed) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var state = seed; - Object(_switchMap__WEBPACK_IMPORTED_MODULE_0__[/* switchMap */ "a"])(function (value, index) { return accumulator(state, value, index); }, function (_, innerValue) { return ((state = innerValue), innerValue); })(source).subscribe(subscriber); - return function () { - state = null; - }; - }); -} -//# sourceMappingURL=switchScan.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/take.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return take; }); -/* harmony import */ var _observable_empty__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function take(count) { - return count <= 0 - ? - function () { return _observable_empty__WEBPACK_IMPORTED_MODULE_0__[/* EMPTY */ "a"]; } - : Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var seen = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - if (++seen <= count) { - subscriber.next(value); - if (count <= seen) { - subscriber.complete(); - } - } - })); - }); -} -//# sourceMappingURL=take.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/takeLast.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return takeLast; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _observable_empty__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/empty.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - - -function takeLast(count) { - return count <= 0 - ? function () { return _observable_empty__WEBPACK_IMPORTED_MODULE_1__[/* EMPTY */ "a"]; } - : Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var buffer = []; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - buffer.push(value); - count < buffer.length && buffer.shift(); - }, function () { - var e_1, _a; - try { - for (var buffer_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(buffer), buffer_1_1 = buffer_1.next(); !buffer_1_1.done; buffer_1_1 = buffer_1.next()) { - var value = buffer_1_1.value; - subscriber.next(value); - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (buffer_1_1 && !buffer_1_1.done && (_a = buffer_1.return)) _a.call(buffer_1); - } - finally { if (e_1) throw e_1.error; } - } - subscriber.complete(); - }, undefined, function () { - buffer = null; - })); - }); -} -//# sourceMappingURL=takeLast.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/takeUntil.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return takeUntil; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); - - - - -function takeUntil(notifier) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(notifier).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function () { return subscriber.complete(); }, _util_noop__WEBPACK_IMPORTED_MODULE_3__[/* noop */ "a"])); - !subscriber.closed && source.subscribe(subscriber); - }); -} -//# sourceMappingURL=takeUntil.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/takeWhile.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return takeWhile; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - -function takeWhile(predicate, inclusive) { - if (inclusive === void 0) { inclusive = false; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var index = 0; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var result = predicate(value, index++); - (result || inclusive) && subscriber.next(value); - !result && subscriber.complete(); - })); - }); -} -//# sourceMappingURL=takeWhile.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/tap.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return tap; }); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); - - - - -function tap(observerOrNext, error, complete) { - var tapObserver = Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_0__[/* isFunction */ "a"])(observerOrNext) || error || complete - ? - { next: observerOrNext, error: error, complete: complete } - : observerOrNext; - return tapObserver - ? Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var _a; - (_a = tapObserver.subscribe) === null || _a === void 0 ? void 0 : _a.call(tapObserver); - var isUnsub = true; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var _a; - (_a = tapObserver.next) === null || _a === void 0 ? void 0 : _a.call(tapObserver, value); - subscriber.next(value); - }, function () { - var _a; - isUnsub = false; - (_a = tapObserver.complete) === null || _a === void 0 ? void 0 : _a.call(tapObserver); - subscriber.complete(); - }, function (err) { - var _a; - isUnsub = false; - (_a = tapObserver.error) === null || _a === void 0 ? void 0 : _a.call(tapObserver, err); - subscriber.error(err); - }, function () { - var _a, _b; - if (isUnsub) { - (_a = tapObserver.unsubscribe) === null || _a === void 0 ? void 0 : _a.call(tapObserver); - } - (_b = tapObserver.finalize) === null || _b === void 0 ? void 0 : _b.call(tapObserver); - })); - }) - : - _util_identity__WEBPACK_IMPORTED_MODULE_3__[/* identity */ "a"]; -} -//# sourceMappingURL=tap.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/throttle.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return defaultThrottleConfig; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return throttle; }); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - - -var defaultThrottleConfig = { - leading: true, - trailing: false, -}; -function throttle(durationSelector, config) { - if (config === void 0) { config = defaultThrottleConfig; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_0__[/* operate */ "b"])(function (source, subscriber) { - var leading = config.leading, trailing = config.trailing; - var hasValue = false; - var sendValue = null; - var throttled = null; - var isComplete = false; - var endThrottling = function () { - throttled === null || throttled === void 0 ? void 0 : throttled.unsubscribe(); - throttled = null; - if (trailing) { - send(); - isComplete && subscriber.complete(); - } - }; - var cleanupThrottling = function () { - throttled = null; - isComplete && subscriber.complete(); - }; - var startThrottle = function (value) { - return (throttled = Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_2__[/* innerFrom */ "a"])(durationSelector(value)).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, endThrottling, cleanupThrottling))); - }; - var send = function () { - if (hasValue) { - hasValue = false; - var value = sendValue; - sendValue = null; - subscriber.next(value); - !isComplete && startThrottle(value); - } - }; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_1__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - hasValue = true; - sendValue = value; - !(throttled && !throttled.closed) && (leading ? send() : startThrottle(value)); - }, function () { - isComplete = true; - !(trailing && hasValue && throttled && !throttled.closed) && subscriber.complete(); - })); - }); -} -//# sourceMappingURL=throttle.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/throttleTime.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return throttleTime; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _throttle__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throttle.js"); -/* harmony import */ var _observable_timer__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/timer.js"); - - - -function throttleTime(duration, scheduler, config) { - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"]; } - if (config === void 0) { config = _throttle__WEBPACK_IMPORTED_MODULE_1__[/* defaultThrottleConfig */ "a"]; } - var duration$ = Object(_observable_timer__WEBPACK_IMPORTED_MODULE_2__[/* timer */ "a"])(duration, scheduler); - return Object(_throttle__WEBPACK_IMPORTED_MODULE_1__[/* throttle */ "b"])(function () { return duration$; }, config); -} -//# sourceMappingURL=throttleTime.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/throwIfEmpty.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return throwIfEmpty; }); -/* harmony import */ var _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function throwIfEmpty(errorFactory) { - if (errorFactory === void 0) { errorFactory = defaultErrorFactory; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var hasValue = false; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - hasValue = true; - subscriber.next(value); - }, function () { return (hasValue ? subscriber.complete() : subscriber.error(errorFactory())); })); - }); -} -function defaultErrorFactory() { - return new _util_EmptyError__WEBPACK_IMPORTED_MODULE_0__[/* EmptyError */ "a"](); -} -//# sourceMappingURL=throwIfEmpty.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/timeInterval.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return timeInterval; }); -/* unused harmony export TimeInterval */ -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - -function timeInterval(scheduler) { - if (scheduler === void 0) { scheduler = _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"]; } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var last = scheduler.now(); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var now = scheduler.now(); - var interval = now - last; - last = now; - subscriber.next(new TimeInterval(value, interval)); - })); - }); -} -var TimeInterval = (function () { - function TimeInterval(value, interval) { - this.value = value; - this.interval = interval; - } - return TimeInterval; -}()); - -//# sourceMappingURL=timeInterval.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/timeout.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return TimeoutError; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return timeout; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _util_isDate__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isDate.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_createErrorClass__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); - - - - - - - -var TimeoutError = Object(_util_createErrorClass__WEBPACK_IMPORTED_MODULE_4__[/* createErrorClass */ "a"])(function (_super) { - return function TimeoutErrorImpl(info) { - if (info === void 0) { info = null; } - _super(this); - this.message = 'Timeout has occurred'; - this.name = 'TimeoutError'; - this.info = info; - }; -}); -function timeout(config, schedulerArg) { - var _a = (Object(_util_isDate__WEBPACK_IMPORTED_MODULE_1__[/* isValidDate */ "a"])(config) ? { first: config } : typeof config === 'number' ? { each: config } : config), first = _a.first, each = _a.each, _b = _a.with, _with = _b === void 0 ? timeoutErrorFactory : _b, _c = _a.scheduler, scheduler = _c === void 0 ? schedulerArg !== null && schedulerArg !== void 0 ? schedulerArg : _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* asyncScheduler */ "b"] : _c, _d = _a.meta, meta = _d === void 0 ? null : _d; - if (first == null && each == null) { - throw new TypeError('No timeout provided.'); - } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var originalSourceSubscription; - var timerSubscription; - var lastValue = null; - var seen = 0; - var startTimer = function (delay) { - timerSubscription = Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_6__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { - try { - originalSourceSubscription.unsubscribe(); - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(_with({ - meta: meta, - lastValue: lastValue, - seen: seen, - })).subscribe(subscriber); - } - catch (err) { - subscriber.error(err); - } - }, delay); - }; - originalSourceSubscription = source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - timerSubscription === null || timerSubscription === void 0 ? void 0 : timerSubscription.unsubscribe(); - seen++; - subscriber.next((lastValue = value)); - each > 0 && startTimer(each); - }, undefined, undefined, function () { - if (!(timerSubscription === null || timerSubscription === void 0 ? void 0 : timerSubscription.closed)) { - timerSubscription === null || timerSubscription === void 0 ? void 0 : timerSubscription.unsubscribe(); - } - lastValue = null; - })); - !seen && startTimer(first != null ? (typeof first === 'number' ? first : +first - scheduler.now()) : each); - }); -} -function timeoutErrorFactory(info) { - throw new TimeoutError(info); -} -//# sourceMappingURL=timeout.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/timeoutWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return timeoutWith; }); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _util_isDate__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isDate.js"); -/* harmony import */ var _timeout__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timeout.js"); - - - -function timeoutWith(due, withObservable, scheduler) { - var first; - var each; - var _with; - scheduler = scheduler !== null && scheduler !== void 0 ? scheduler : _scheduler_async__WEBPACK_IMPORTED_MODULE_0__[/* async */ "a"]; - if (Object(_util_isDate__WEBPACK_IMPORTED_MODULE_1__[/* isValidDate */ "a"])(due)) { - first = due; - } - else if (typeof due === 'number') { - each = due; - } - if (withObservable) { - _with = function () { return withObservable; }; - } - else { - throw new TypeError('No observable provided to switch to'); - } - if (first == null && each == null) { - throw new TypeError('No timeout provided.'); - } - return Object(_timeout__WEBPACK_IMPORTED_MODULE_2__[/* timeout */ "b"])({ - first: first, - each: each, - scheduler: scheduler, - with: _with, - }); -} -//# sourceMappingURL=timeoutWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/timestamp.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return timestamp; }); -/* harmony import */ var _scheduler_dateTimestampProvider__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/dateTimestampProvider.js"); -/* harmony import */ var _map__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); - - -function timestamp(timestampProvider) { - if (timestampProvider === void 0) { timestampProvider = _scheduler_dateTimestampProvider__WEBPACK_IMPORTED_MODULE_0__[/* dateTimestampProvider */ "a"]; } - return Object(_map__WEBPACK_IMPORTED_MODULE_1__[/* map */ "a"])(function (value) { return ({ value: value, timestamp: timestampProvider.now() }); }); -} -//# sourceMappingURL=timestamp.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/toArray.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return toArray; }); -/* harmony import */ var _reduce__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/reduce.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - -var arrReducer = function (arr, value) { return (arr.push(value), arr); }; -function toArray() { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - Object(_reduce__WEBPACK_IMPORTED_MODULE_0__[/* reduce */ "a"])(arrReducer, [])(source).subscribe(subscriber); - }); -} -//# sourceMappingURL=toArray.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/window.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return window; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); - - - - -function window(windowBoundaries) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var windowSubject = new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"](); - subscriber.next(windowSubject.asObservable()); - var errorHandler = function (err) { - windowSubject.error(err); - subscriber.error(err); - }; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return windowSubject === null || windowSubject === void 0 ? void 0 : windowSubject.next(value); }, function () { - windowSubject.complete(); - subscriber.complete(); - }, errorHandler)); - windowBoundaries.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function () { - windowSubject.complete(); - subscriber.next((windowSubject = new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"]())); - }, _util_noop__WEBPACK_IMPORTED_MODULE_3__[/* noop */ "a"], errorHandler)); - return function () { - windowSubject === null || windowSubject === void 0 ? void 0 : windowSubject.unsubscribe(); - windowSubject = null; - }; - }); -} -//# sourceMappingURL=window.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/windowCount.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return windowCount; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); - - - - -function windowCount(windowSize, startWindowEvery) { - if (startWindowEvery === void 0) { startWindowEvery = 0; } - var startEvery = startWindowEvery > 0 ? startWindowEvery : windowSize; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - var windows = [new _Subject__WEBPACK_IMPORTED_MODULE_1__[/* Subject */ "a"]()]; - var starts = []; - var count = 0; - subscriber.next(windows[0].asObservable()); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_3__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var e_1, _a; - try { - for (var windows_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(windows), windows_1_1 = windows_1.next(); !windows_1_1.done; windows_1_1 = windows_1.next()) { - var window_1 = windows_1_1.value; - window_1.next(value); - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (windows_1_1 && !windows_1_1.done && (_a = windows_1.return)) _a.call(windows_1); - } - finally { if (e_1) throw e_1.error; } - } - var c = count - windowSize + 1; - if (c >= 0 && c % startEvery === 0) { - windows.shift().complete(); - } - if (++count % startEvery === 0) { - var window_2 = new _Subject__WEBPACK_IMPORTED_MODULE_1__[/* Subject */ "a"](); - windows.push(window_2); - subscriber.next(window_2.asObservable()); - } - }, function () { - while (windows.length > 0) { - windows.shift().complete(); - } - subscriber.complete(); - }, function (err) { - while (windows.length > 0) { - windows.shift().error(err); - } - subscriber.error(err); - }, function () { - starts = null; - windows = null; - })); - }); -} -//# sourceMappingURL=windowCount.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/windowTime.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return windowTime; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _scheduler_async__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); - - - - - - - - -function windowTime(windowTimeSpan) { - var _a, _b; - var otherArgs = []; - for (var _i = 1; _i < arguments.length; _i++) { - otherArgs[_i - 1] = arguments[_i]; - } - var scheduler = (_a = Object(_util_args__WEBPACK_IMPORTED_MODULE_6__[/* popScheduler */ "c"])(otherArgs)) !== null && _a !== void 0 ? _a : _scheduler_async__WEBPACK_IMPORTED_MODULE_1__[/* asyncScheduler */ "b"]; - var windowCreationInterval = (_b = otherArgs[0]) !== null && _b !== void 0 ? _b : null; - var maxWindowSize = otherArgs[1] || Infinity; - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_3__[/* operate */ "b"])(function (source, subscriber) { - var windowRecords = []; - var restartOnClose = false; - var closeWindow = function (record) { - var window = record.window, subs = record.subs; - window.complete(); - subs.unsubscribe(); - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_5__[/* arrRemove */ "a"])(windowRecords, record); - restartOnClose && startWindow(); - }; - var startWindow = function () { - if (windowRecords) { - var subs = new _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* Subscription */ "b"](); - subscriber.add(subs); - var window_1 = new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"](); - var record_1 = { - window: window_1, - subs: subs, - seen: 0, - }; - windowRecords.push(record_1); - subscriber.next(window_1.asObservable()); - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_7__[/* executeSchedule */ "a"])(subs, scheduler, function () { return closeWindow(record_1); }, windowTimeSpan); - } - }; - if (windowCreationInterval !== null && windowCreationInterval >= 0) { - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_7__[/* executeSchedule */ "a"])(subscriber, scheduler, startWindow, windowCreationInterval, true); - } - else { - restartOnClose = true; - } - startWindow(); - var loop = function (cb) { return windowRecords.slice().forEach(cb); }; - var terminate = function (cb) { - loop(function (_a) { - var window = _a.window; - return cb(window); - }); - cb(subscriber); - subscriber.unsubscribe(); - }; - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_4__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - loop(function (record) { - record.window.next(value); - maxWindowSize <= ++record.seen && closeWindow(record); - }); - }, function () { return terminate(function (consumer) { return consumer.complete(); }); }, function (err) { return terminate(function (consumer) { return consumer.error(err); }); })); - return function () { - windowRecords = null; - }; - }); -} -//# sourceMappingURL=windowTime.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/windowToggle.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return windowToggle; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); - - - - - - - - -function windowToggle(openings, closingSelector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_3__[/* operate */ "b"])(function (source, subscriber) { - var windows = []; - var handleError = function (err) { - while (0 < windows.length) { - windows.shift().error(err); - } - subscriber.error(err); - }; - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_4__[/* innerFrom */ "a"])(openings).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__[/* createOperatorSubscriber */ "b"])(subscriber, function (openValue) { - var window = new _Subject__WEBPACK_IMPORTED_MODULE_1__[/* Subject */ "a"](); - windows.push(window); - var closingSubscription = new _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* Subscription */ "b"](); - var closeWindow = function () { - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_7__[/* arrRemove */ "a"])(windows, window); - window.complete(); - closingSubscription.unsubscribe(); - }; - var closingNotifier; - try { - closingNotifier = Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_4__[/* innerFrom */ "a"])(closingSelector(openValue)); - } - catch (err) { - handleError(err); - return; - } - subscriber.next(window.asObservable()); - closingSubscription.add(closingNotifier.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__[/* createOperatorSubscriber */ "b"])(subscriber, closeWindow, _util_noop__WEBPACK_IMPORTED_MODULE_6__[/* noop */ "a"], handleError))); - }, _util_noop__WEBPACK_IMPORTED_MODULE_6__[/* noop */ "a"])); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_5__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - var e_1, _a; - var windowsCopy = windows.slice(); - try { - for (var windowsCopy_1 = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __values */ "i"])(windowsCopy), windowsCopy_1_1 = windowsCopy_1.next(); !windowsCopy_1_1.done; windowsCopy_1_1 = windowsCopy_1.next()) { - var window_1 = windowsCopy_1_1.value; - window_1.next(value); - } - } - catch (e_1_1) { e_1 = { error: e_1_1 }; } - finally { - try { - if (windowsCopy_1_1 && !windowsCopy_1_1.done && (_a = windowsCopy_1.return)) _a.call(windowsCopy_1); - } - finally { if (e_1) throw e_1.error; } - } - }, function () { - while (0 < windows.length) { - windows.shift().complete(); - } - subscriber.complete(); - }, handleError, function () { - while (0 < windows.length) { - windows.shift().unsubscribe(); - } - })); - }); -} -//# sourceMappingURL=windowToggle.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/windowWhen.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return windowWhen; }); -/* harmony import */ var _Subject__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subject.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); - - - - -function windowWhen(closingSelector) { - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var window; - var closingSubscriber; - var handleError = function (err) { - window.error(err); - subscriber.error(err); - }; - var openWindow = function () { - closingSubscriber === null || closingSubscriber === void 0 ? void 0 : closingSubscriber.unsubscribe(); - window === null || window === void 0 ? void 0 : window.complete(); - window = new _Subject__WEBPACK_IMPORTED_MODULE_0__[/* Subject */ "a"](); - subscriber.next(window.asObservable()); - var closingNotifier; - try { - closingNotifier = Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(closingSelector()); - } - catch (err) { - handleError(err); - return; - } - closingNotifier.subscribe((closingSubscriber = Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, openWindow, openWindow, handleError))); - }; - openWindow(); - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { return window.next(value); }, function () { - window.complete(); - subscriber.complete(); - }, handleError, function () { - closingSubscriber === null || closingSubscriber === void 0 ? void 0 : closingSubscriber.unsubscribe(); - window = null; - })); - }); -} -//# sourceMappingURL=windowWhen.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/withLatestFrom.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return withLatestFrom; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); -/* harmony import */ var _OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/OperatorSubscriber.js"); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _util_identity__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); -/* harmony import */ var _util_noop__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/noop.js"); -/* harmony import */ var _util_args__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/args.js"); - - - - - - - -function withLatestFrom() { - var inputs = []; - for (var _i = 0; _i < arguments.length; _i++) { - inputs[_i] = arguments[_i]; - } - var project = Object(_util_args__WEBPACK_IMPORTED_MODULE_6__[/* popResultSelector */ "b"])(inputs); - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_1__[/* operate */ "b"])(function (source, subscriber) { - var len = inputs.length; - var otherValues = new Array(len); - var hasValue = inputs.map(function () { return false; }); - var ready = false; - var _loop_1 = function (i) { - Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_3__[/* innerFrom */ "a"])(inputs[i]).subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - otherValues[i] = value; - if (!ready && !hasValue[i]) { - hasValue[i] = true; - (ready = hasValue.every(_util_identity__WEBPACK_IMPORTED_MODULE_4__[/* identity */ "a"])) && (hasValue = null); - } - }, _util_noop__WEBPACK_IMPORTED_MODULE_5__[/* noop */ "a"])); - }; - for (var i = 0; i < len; i++) { - _loop_1(i); - } - source.subscribe(Object(_OperatorSubscriber__WEBPACK_IMPORTED_MODULE_2__[/* createOperatorSubscriber */ "b"])(subscriber, function (value) { - if (ready) { - var values = Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([value], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(otherValues)); - subscriber.next(project ? project.apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(values))) : values); - } - })); - }); -} -//# sourceMappingURL=withLatestFrom.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/zip.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return zip; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _observable_zip__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/zip.js"); -/* harmony import */ var _util_lift__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/lift.js"); - - - -function zip() { - var sources = []; - for (var _i = 0; _i < arguments.length; _i++) { - sources[_i] = arguments[_i]; - } - return Object(_util_lift__WEBPACK_IMPORTED_MODULE_2__[/* operate */ "b"])(function (source, subscriber) { - _observable_zip__WEBPACK_IMPORTED_MODULE_1__[/* zip */ "a"].apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([source], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(sources))).subscribe(subscriber); - }); -} -//# sourceMappingURL=zip.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/zipAll.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return zipAll; }); -/* harmony import */ var _observable_zip__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/zip.js"); -/* harmony import */ var _joinAllInternals__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/joinAllInternals.js"); - - -function zipAll(project) { - return Object(_joinAllInternals__WEBPACK_IMPORTED_MODULE_1__[/* joinAllInternals */ "a"])(_observable_zip__WEBPACK_IMPORTED_MODULE_0__[/* zip */ "a"], project); -} -//# sourceMappingURL=zipAll.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/operators/zipWith.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return zipWith; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _zip__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/zip.js"); - - -function zipWith() { - var otherInputs = []; - for (var _i = 0; _i < arguments.length; _i++) { - otherInputs[_i] = arguments[_i]; - } - return _zip__WEBPACK_IMPORTED_MODULE_1__[/* zip */ "a"].apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(otherInputs))); -} -//# sourceMappingURL=zipWith.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleArray.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scheduleArray; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); - -function scheduleArray(input, scheduler) { - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - var i = 0; - return scheduler.schedule(function () { - if (i === input.length) { - subscriber.complete(); - } - else { - subscriber.next(input[i++]); - if (!subscriber.closed) { - this.schedule(); - } - } - }); - }); -} -//# sourceMappingURL=scheduleArray.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleAsyncIterable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scheduleAsyncIterable; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); - - -function scheduleAsyncIterable(input, scheduler) { - if (!input) { - throw new Error('Iterable cannot be null'); - } - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_1__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { - var iterator = input[Symbol.asyncIterator](); - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_1__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { - iterator.next().then(function (result) { - if (result.done) { - subscriber.complete(); - } - else { - subscriber.next(result.value); - } - }); - }, 0, true); - }); - }); -} -//# sourceMappingURL=scheduleAsyncIterable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleIterable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scheduleIterable; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _symbol_iterator__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/symbol/iterator.js"); -/* harmony import */ var _util_isFunction__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _util_executeSchedule__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js"); - - - - -function scheduleIterable(input, scheduler) { - return new _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"](function (subscriber) { - var iterator; - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_3__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { - iterator = input[_symbol_iterator__WEBPACK_IMPORTED_MODULE_1__[/* iterator */ "a"]](); - Object(_util_executeSchedule__WEBPACK_IMPORTED_MODULE_3__[/* executeSchedule */ "a"])(subscriber, scheduler, function () { - var _a; - var value; - var done; - try { - (_a = iterator.next(), value = _a.value, done = _a.done); - } - catch (err) { - subscriber.error(err); - return; - } - if (done) { - subscriber.complete(); - } - else { - subscriber.next(value); - } - }, 0, true); - }); - return function () { return Object(_util_isFunction__WEBPACK_IMPORTED_MODULE_2__[/* isFunction */ "a"])(iterator === null || iterator === void 0 ? void 0 : iterator.return) && iterator.return(); }; - }); -} -//# sourceMappingURL=scheduleIterable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleObservable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scheduleObservable; }); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _operators_observeOn__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/observeOn.js"); -/* harmony import */ var _operators_subscribeOn__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/subscribeOn.js"); - - - -function scheduleObservable(input, scheduler) { - return Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__[/* innerFrom */ "a"])(input).pipe(Object(_operators_subscribeOn__WEBPACK_IMPORTED_MODULE_2__[/* subscribeOn */ "a"])(scheduler), Object(_operators_observeOn__WEBPACK_IMPORTED_MODULE_1__[/* observeOn */ "a"])(scheduler)); -} -//# sourceMappingURL=scheduleObservable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduled/schedulePromise.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return schedulePromise; }); -/* harmony import */ var _observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/observable/innerFrom.js"); -/* harmony import */ var _operators_observeOn__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/observeOn.js"); -/* harmony import */ var _operators_subscribeOn__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/subscribeOn.js"); - - - -function schedulePromise(input, scheduler) { - return Object(_observable_innerFrom__WEBPACK_IMPORTED_MODULE_0__[/* innerFrom */ "a"])(input).pipe(Object(_operators_subscribeOn__WEBPACK_IMPORTED_MODULE_2__[/* subscribeOn */ "a"])(scheduler), Object(_operators_observeOn__WEBPACK_IMPORTED_MODULE_1__[/* observeOn */ "a"])(scheduler)); -} -//# sourceMappingURL=schedulePromise.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleReadableStreamLike.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scheduleReadableStreamLike; }); -/* harmony import */ var _scheduleAsyncIterable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleAsyncIterable.js"); -/* harmony import */ var _util_isReadableStreamLike__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isReadableStreamLike.js"); - - -function scheduleReadableStreamLike(input, scheduler) { - return Object(_scheduleAsyncIterable__WEBPACK_IMPORTED_MODULE_0__[/* scheduleAsyncIterable */ "a"])(Object(_util_isReadableStreamLike__WEBPACK_IMPORTED_MODULE_1__[/* readableStreamLikeToAsyncGenerator */ "b"])(input), scheduler); -} -//# sourceMappingURL=scheduleReadableStreamLike.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduled.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return scheduled; }); -/* harmony import */ var _scheduleObservable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleObservable.js"); -/* harmony import */ var _schedulePromise__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/schedulePromise.js"); -/* harmony import */ var _scheduleArray__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleArray.js"); -/* harmony import */ var _scheduleIterable__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleIterable.js"); -/* harmony import */ var _scheduleAsyncIterable__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleAsyncIterable.js"); -/* harmony import */ var _util_isInteropObservable__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isInteropObservable.js"); -/* harmony import */ var _util_isPromise__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isPromise.js"); -/* harmony import */ var _util_isArrayLike__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isArrayLike.js"); -/* harmony import */ var _util_isIterable__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isIterable.js"); -/* harmony import */ var _util_isAsyncIterable__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isAsyncIterable.js"); -/* harmony import */ var _util_throwUnobservableError__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/throwUnobservableError.js"); -/* harmony import */ var _util_isReadableStreamLike__WEBPACK_IMPORTED_MODULE_11__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isReadableStreamLike.js"); -/* harmony import */ var _scheduleReadableStreamLike__WEBPACK_IMPORTED_MODULE_12__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduled/scheduleReadableStreamLike.js"); - - - - - - - - - - - - - -function scheduled(input, scheduler) { - if (input != null) { - if (Object(_util_isInteropObservable__WEBPACK_IMPORTED_MODULE_5__[/* isInteropObservable */ "a"])(input)) { - return Object(_scheduleObservable__WEBPACK_IMPORTED_MODULE_0__[/* scheduleObservable */ "a"])(input, scheduler); - } - if (Object(_util_isArrayLike__WEBPACK_IMPORTED_MODULE_7__[/* isArrayLike */ "a"])(input)) { - return Object(_scheduleArray__WEBPACK_IMPORTED_MODULE_2__[/* scheduleArray */ "a"])(input, scheduler); - } - if (Object(_util_isPromise__WEBPACK_IMPORTED_MODULE_6__[/* isPromise */ "a"])(input)) { - return Object(_schedulePromise__WEBPACK_IMPORTED_MODULE_1__[/* schedulePromise */ "a"])(input, scheduler); - } - if (Object(_util_isAsyncIterable__WEBPACK_IMPORTED_MODULE_9__[/* isAsyncIterable */ "a"])(input)) { - return Object(_scheduleAsyncIterable__WEBPACK_IMPORTED_MODULE_4__[/* scheduleAsyncIterable */ "a"])(input, scheduler); - } - if (Object(_util_isIterable__WEBPACK_IMPORTED_MODULE_8__[/* isIterable */ "a"])(input)) { - return Object(_scheduleIterable__WEBPACK_IMPORTED_MODULE_3__[/* scheduleIterable */ "a"])(input, scheduler); - } - if (Object(_util_isReadableStreamLike__WEBPACK_IMPORTED_MODULE_11__[/* isReadableStreamLike */ "a"])(input)) { - return Object(_scheduleReadableStreamLike__WEBPACK_IMPORTED_MODULE_12__[/* scheduleReadableStreamLike */ "a"])(input, scheduler); - } - } - throw Object(_util_throwUnobservableError__WEBPACK_IMPORTED_MODULE_10__[/* createInvalidObservableTypeError */ "a"])(input); -} -//# sourceMappingURL=scheduled.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/Action.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Action; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); - - -var Action = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(Action, _super); - function Action(scheduler, work) { - return _super.call(this) || this; - } - Action.prototype.schedule = function (state, delay) { - if (delay === void 0) { delay = 0; } - return this; - }; - return Action; -}(_Subscription__WEBPACK_IMPORTED_MODULE_1__[/* Subscription */ "b"])); - -//# sourceMappingURL=Action.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/AnimationFrameAction.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return AnimationFrameAction; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _AsyncAction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncAction.js"); -/* harmony import */ var _animationFrameProvider__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/animationFrameProvider.js"); - - - -var AnimationFrameAction = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AnimationFrameAction, _super); - function AnimationFrameAction(scheduler, work) { - var _this = _super.call(this, scheduler, work) || this; - _this.scheduler = scheduler; - _this.work = work; - return _this; - } - AnimationFrameAction.prototype.requestAsyncId = function (scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - if (delay !== null && delay > 0) { - return _super.prototype.requestAsyncId.call(this, scheduler, id, delay); - } - scheduler.actions.push(this); - return scheduler._scheduled || (scheduler._scheduled = _animationFrameProvider__WEBPACK_IMPORTED_MODULE_2__[/* animationFrameProvider */ "a"].requestAnimationFrame(function () { return scheduler.flush(undefined); })); - }; - AnimationFrameAction.prototype.recycleAsyncId = function (scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - if ((delay != null && delay > 0) || (delay == null && this.delay > 0)) { - return _super.prototype.recycleAsyncId.call(this, scheduler, id, delay); - } - if (!scheduler.actions.some(function (action) { return action.id === id; })) { - _animationFrameProvider__WEBPACK_IMPORTED_MODULE_2__[/* animationFrameProvider */ "a"].cancelAnimationFrame(id); - scheduler._scheduled = undefined; - } - return undefined; - }; - return AnimationFrameAction; -}(_AsyncAction__WEBPACK_IMPORTED_MODULE_1__[/* AsyncAction */ "a"])); - -//# sourceMappingURL=AnimationFrameAction.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/AnimationFrameScheduler.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return AnimationFrameScheduler; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncScheduler.js"); - - -var AnimationFrameScheduler = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AnimationFrameScheduler, _super); - function AnimationFrameScheduler() { - return _super !== null && _super.apply(this, arguments) || this; - } - AnimationFrameScheduler.prototype.flush = function (action) { - this._active = true; - var flushId = this._scheduled; - this._scheduled = undefined; - var actions = this.actions; - var error; - action = action || actions.shift(); - do { - if ((error = action.execute(action.state, action.delay))) { - break; - } - } while ((action = actions[0]) && action.id === flushId && actions.shift()); - this._active = false; - if (error) { - while ((action = actions[0]) && action.id === flushId && actions.shift()) { - action.unsubscribe(); - } - throw error; - } - }; - return AnimationFrameScheduler; -}(_AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__[/* AsyncScheduler */ "a"])); - -//# sourceMappingURL=AnimationFrameScheduler.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/AsapAction.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return AsapAction; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _AsyncAction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncAction.js"); -/* harmony import */ var _immediateProvider__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/immediateProvider.js"); - - - -var AsapAction = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AsapAction, _super); - function AsapAction(scheduler, work) { - var _this = _super.call(this, scheduler, work) || this; - _this.scheduler = scheduler; - _this.work = work; - return _this; - } - AsapAction.prototype.requestAsyncId = function (scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - if (delay !== null && delay > 0) { - return _super.prototype.requestAsyncId.call(this, scheduler, id, delay); - } - scheduler.actions.push(this); - return scheduler._scheduled || (scheduler._scheduled = _immediateProvider__WEBPACK_IMPORTED_MODULE_2__[/* immediateProvider */ "a"].setImmediate(scheduler.flush.bind(scheduler, undefined))); - }; - AsapAction.prototype.recycleAsyncId = function (scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - if ((delay != null && delay > 0) || (delay == null && this.delay > 0)) { - return _super.prototype.recycleAsyncId.call(this, scheduler, id, delay); - } - if (!scheduler.actions.some(function (action) { return action.id === id; })) { - _immediateProvider__WEBPACK_IMPORTED_MODULE_2__[/* immediateProvider */ "a"].clearImmediate(id); - scheduler._scheduled = undefined; - } - return undefined; - }; - return AsapAction; -}(_AsyncAction__WEBPACK_IMPORTED_MODULE_1__[/* AsyncAction */ "a"])); - -//# sourceMappingURL=AsapAction.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/AsapScheduler.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return AsapScheduler; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncScheduler.js"); - - -var AsapScheduler = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AsapScheduler, _super); - function AsapScheduler() { - return _super !== null && _super.apply(this, arguments) || this; - } - AsapScheduler.prototype.flush = function (action) { - this._active = true; - var flushId = this._scheduled; - this._scheduled = undefined; - var actions = this.actions; - var error; - action = action || actions.shift(); - do { - if ((error = action.execute(action.state, action.delay))) { - break; - } - } while ((action = actions[0]) && action.id === flushId && actions.shift()); - this._active = false; - if (error) { - while ((action = actions[0]) && action.id === flushId && actions.shift()) { - action.unsubscribe(); - } - throw error; - } - }; - return AsapScheduler; -}(_AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__[/* AsyncScheduler */ "a"])); - -//# sourceMappingURL=AsapScheduler.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncAction.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return AsyncAction; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Action__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/Action.js"); -/* harmony import */ var _intervalProvider__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/intervalProvider.js"); -/* harmony import */ var _util_arrRemove__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js"); - - - - -var AsyncAction = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AsyncAction, _super); - function AsyncAction(scheduler, work) { - var _this = _super.call(this, scheduler, work) || this; - _this.scheduler = scheduler; - _this.work = work; - _this.pending = false; - return _this; - } - AsyncAction.prototype.schedule = function (state, delay) { - if (delay === void 0) { delay = 0; } - if (this.closed) { - return this; - } - this.state = state; - var id = this.id; - var scheduler = this.scheduler; - if (id != null) { - this.id = this.recycleAsyncId(scheduler, id, delay); - } - this.pending = true; - this.delay = delay; - this.id = this.id || this.requestAsyncId(scheduler, this.id, delay); - return this; - }; - AsyncAction.prototype.requestAsyncId = function (scheduler, _id, delay) { - if (delay === void 0) { delay = 0; } - return _intervalProvider__WEBPACK_IMPORTED_MODULE_2__[/* intervalProvider */ "a"].setInterval(scheduler.flush.bind(scheduler, this), delay); - }; - AsyncAction.prototype.recycleAsyncId = function (_scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - if (delay != null && this.delay === delay && this.pending === false) { - return id; - } - _intervalProvider__WEBPACK_IMPORTED_MODULE_2__[/* intervalProvider */ "a"].clearInterval(id); - return undefined; - }; - AsyncAction.prototype.execute = function (state, delay) { - if (this.closed) { - return new Error('executing a cancelled action'); - } - this.pending = false; - var error = this._execute(state, delay); - if (error) { - return error; - } - else if (this.pending === false && this.id != null) { - this.id = this.recycleAsyncId(this.scheduler, this.id, null); - } - }; - AsyncAction.prototype._execute = function (state, _delay) { - var errored = false; - var errorValue; - try { - this.work(state); - } - catch (e) { - errored = true; - errorValue = e ? e : new Error('Scheduled action threw falsy error'); - } - if (errored) { - this.unsubscribe(); - return errorValue; - } - }; - AsyncAction.prototype.unsubscribe = function () { - if (!this.closed) { - var _a = this, id = _a.id, scheduler = _a.scheduler; - var actions = scheduler.actions; - this.work = this.state = this.scheduler = null; - this.pending = false; - Object(_util_arrRemove__WEBPACK_IMPORTED_MODULE_3__[/* arrRemove */ "a"])(actions, this); - if (id != null) { - this.id = this.recycleAsyncId(scheduler, id, null); - } - this.delay = null; - _super.prototype.unsubscribe.call(this); - } - }; - return AsyncAction; -}(_Action__WEBPACK_IMPORTED_MODULE_1__[/* Action */ "a"])); - -//# sourceMappingURL=AsyncAction.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncScheduler.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return AsyncScheduler; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Scheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Scheduler.js"); - - -var AsyncScheduler = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(AsyncScheduler, _super); - function AsyncScheduler(SchedulerAction, now) { - if (now === void 0) { now = _Scheduler__WEBPACK_IMPORTED_MODULE_1__[/* Scheduler */ "a"].now; } - var _this = _super.call(this, SchedulerAction, now) || this; - _this.actions = []; - _this._active = false; - _this._scheduled = undefined; - return _this; - } - AsyncScheduler.prototype.flush = function (action) { - var actions = this.actions; - if (this._active) { - actions.push(action); - return; - } - var error; - this._active = true; - do { - if ((error = action.execute(action.state, action.delay))) { - break; - } - } while ((action = actions.shift())); - this._active = false; - if (error) { - while ((action = actions.shift())) { - action.unsubscribe(); - } - throw error; - } - }; - return AsyncScheduler; -}(_Scheduler__WEBPACK_IMPORTED_MODULE_1__[/* Scheduler */ "a"])); - -//# sourceMappingURL=AsyncScheduler.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/QueueAction.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return QueueAction; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _AsyncAction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncAction.js"); - - -var QueueAction = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(QueueAction, _super); - function QueueAction(scheduler, work) { - var _this = _super.call(this, scheduler, work) || this; - _this.scheduler = scheduler; - _this.work = work; - return _this; - } - QueueAction.prototype.schedule = function (state, delay) { - if (delay === void 0) { delay = 0; } - if (delay > 0) { - return _super.prototype.schedule.call(this, state, delay); - } - this.delay = delay; - this.state = state; - this.scheduler.flush(this); - return this; - }; - QueueAction.prototype.execute = function (state, delay) { - return (delay > 0 || this.closed) ? - _super.prototype.execute.call(this, state, delay) : - this._execute(state, delay); - }; - QueueAction.prototype.requestAsyncId = function (scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - if ((delay != null && delay > 0) || (delay == null && this.delay > 0)) { - return _super.prototype.requestAsyncId.call(this, scheduler, id, delay); - } - return scheduler.flush(this); - }; - return QueueAction; -}(_AsyncAction__WEBPACK_IMPORTED_MODULE_1__[/* AsyncAction */ "a"])); - -//# sourceMappingURL=QueueAction.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/QueueScheduler.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return QueueScheduler; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncScheduler.js"); - - -var QueueScheduler = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(QueueScheduler, _super); - function QueueScheduler() { - return _super !== null && _super.apply(this, arguments) || this; - } - return QueueScheduler; -}(_AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__[/* AsyncScheduler */ "a"])); - -//# sourceMappingURL=QueueScheduler.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/VirtualTimeScheduler.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return VirtualTimeScheduler; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return VirtualAction; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _AsyncAction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncAction.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); -/* harmony import */ var _AsyncScheduler__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncScheduler.js"); - - - - -var VirtualTimeScheduler = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(VirtualTimeScheduler, _super); - function VirtualTimeScheduler(schedulerActionCtor, maxFrames) { - if (schedulerActionCtor === void 0) { schedulerActionCtor = VirtualAction; } - if (maxFrames === void 0) { maxFrames = Infinity; } - var _this = _super.call(this, schedulerActionCtor, function () { return _this.frame; }) || this; - _this.maxFrames = maxFrames; - _this.frame = 0; - _this.index = -1; - return _this; - } - VirtualTimeScheduler.prototype.flush = function () { - var _a = this, actions = _a.actions, maxFrames = _a.maxFrames; - var error; - var action; - while ((action = actions[0]) && action.delay <= maxFrames) { - actions.shift(); - this.frame = action.delay; - if ((error = action.execute(action.state, action.delay))) { - break; - } - } - if (error) { - while ((action = actions.shift())) { - action.unsubscribe(); - } - throw error; - } - }; - VirtualTimeScheduler.frameTimeFactor = 10; - return VirtualTimeScheduler; -}(_AsyncScheduler__WEBPACK_IMPORTED_MODULE_3__[/* AsyncScheduler */ "a"])); - -var VirtualAction = (function (_super) { - Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __extends */ "e"])(VirtualAction, _super); - function VirtualAction(scheduler, work, index) { - if (index === void 0) { index = (scheduler.index += 1); } - var _this = _super.call(this, scheduler, work) || this; - _this.scheduler = scheduler; - _this.work = work; - _this.index = index; - _this.active = true; - _this.index = scheduler.index = index; - return _this; - } - VirtualAction.prototype.schedule = function (state, delay) { - if (delay === void 0) { delay = 0; } - if (Number.isFinite(delay)) { - if (!this.id) { - return _super.prototype.schedule.call(this, state, delay); - } - this.active = false; - var action = new VirtualAction(this.scheduler, this.work); - this.add(action); - return action.schedule(state, delay); - } - else { - return _Subscription__WEBPACK_IMPORTED_MODULE_2__[/* Subscription */ "b"].EMPTY; - } - }; - VirtualAction.prototype.requestAsyncId = function (scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - this.delay = scheduler.frame + delay; - var actions = scheduler.actions; - actions.push(this); - actions.sort(VirtualAction.sortActions); - return true; - }; - VirtualAction.prototype.recycleAsyncId = function (scheduler, id, delay) { - if (delay === void 0) { delay = 0; } - return undefined; - }; - VirtualAction.prototype._execute = function (state, delay) { - if (this.active === true) { - return _super.prototype._execute.call(this, state, delay); - } - }; - VirtualAction.sortActions = function (a, b) { - if (a.delay === b.delay) { - if (a.index === b.index) { - return 0; - } - else if (a.index > b.index) { - return 1; - } - else { - return -1; - } - } - else if (a.delay > b.delay) { - return 1; - } - else { - return -1; - } - }; - return VirtualAction; -}(_AsyncAction__WEBPACK_IMPORTED_MODULE_1__[/* AsyncAction */ "a"])); - -//# sourceMappingURL=VirtualTimeScheduler.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/animationFrame.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return animationFrameScheduler; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return animationFrame; }); -/* harmony import */ var _AnimationFrameAction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AnimationFrameAction.js"); -/* harmony import */ var _AnimationFrameScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AnimationFrameScheduler.js"); - - -var animationFrameScheduler = new _AnimationFrameScheduler__WEBPACK_IMPORTED_MODULE_1__[/* AnimationFrameScheduler */ "a"](_AnimationFrameAction__WEBPACK_IMPORTED_MODULE_0__[/* AnimationFrameAction */ "a"]); -var animationFrame = animationFrameScheduler; -//# sourceMappingURL=animationFrame.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/animationFrameProvider.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return animationFrameProvider; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _Subscription__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Subscription.js"); - - -var animationFrameProvider = { - schedule: function (callback) { - var request = requestAnimationFrame; - var cancel = cancelAnimationFrame; - var delegate = animationFrameProvider.delegate; - if (delegate) { - request = delegate.requestAnimationFrame; - cancel = delegate.cancelAnimationFrame; - } - var handle = request(function (timestamp) { - cancel = undefined; - callback(timestamp); - }); - return new _Subscription__WEBPACK_IMPORTED_MODULE_1__[/* Subscription */ "b"](function () { return cancel === null || cancel === void 0 ? void 0 : cancel(handle); }); - }, - requestAnimationFrame: function () { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var delegate = animationFrameProvider.delegate; - return ((delegate === null || delegate === void 0 ? void 0 : delegate.requestAnimationFrame) || requestAnimationFrame).apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))); - }, - cancelAnimationFrame: function () { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var delegate = animationFrameProvider.delegate; - return ((delegate === null || delegate === void 0 ? void 0 : delegate.cancelAnimationFrame) || cancelAnimationFrame).apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))); - }, - delegate: undefined, -}; -//# sourceMappingURL=animationFrameProvider.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/asap.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return asapScheduler; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return asap; }); -/* harmony import */ var _AsapAction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsapAction.js"); -/* harmony import */ var _AsapScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsapScheduler.js"); - - -var asapScheduler = new _AsapScheduler__WEBPACK_IMPORTED_MODULE_1__[/* AsapScheduler */ "a"](_AsapAction__WEBPACK_IMPORTED_MODULE_0__[/* AsapAction */ "a"]); -var asap = asapScheduler; -//# sourceMappingURL=asap.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/async.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return asyncScheduler; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return async; }); -/* harmony import */ var _AsyncAction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncAction.js"); -/* harmony import */ var _AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/AsyncScheduler.js"); - - -var asyncScheduler = new _AsyncScheduler__WEBPACK_IMPORTED_MODULE_1__[/* AsyncScheduler */ "a"](_AsyncAction__WEBPACK_IMPORTED_MODULE_0__[/* AsyncAction */ "a"]); -var async = asyncScheduler; -//# sourceMappingURL=async.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/dateTimestampProvider.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return dateTimestampProvider; }); -var dateTimestampProvider = { - now: function () { - return (dateTimestampProvider.delegate || Date).now(); - }, - delegate: undefined, -}; -//# sourceMappingURL=dateTimestampProvider.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/immediateProvider.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return immediateProvider; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _util_Immediate__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/Immediate.js"); - - -var setImmediate = _util_Immediate__WEBPACK_IMPORTED_MODULE_1__[/* Immediate */ "a"].setImmediate, clearImmediate = _util_Immediate__WEBPACK_IMPORTED_MODULE_1__[/* Immediate */ "a"].clearImmediate; -var immediateProvider = { - setImmediate: function () { - var args = []; - for (var _i = 0; _i < arguments.length; _i++) { - args[_i] = arguments[_i]; - } - var delegate = immediateProvider.delegate; - return ((delegate === null || delegate === void 0 ? void 0 : delegate.setImmediate) || setImmediate).apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))); - }, - clearImmediate: function (handle) { - var delegate = immediateProvider.delegate; - return ((delegate === null || delegate === void 0 ? void 0 : delegate.clearImmediate) || clearImmediate)(handle); - }, - delegate: undefined, -}; -//# sourceMappingURL=immediateProvider.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/intervalProvider.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return intervalProvider; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); - -var intervalProvider = { - setInterval: function (handler, timeout) { - var args = []; - for (var _i = 2; _i < arguments.length; _i++) { - args[_i - 2] = arguments[_i]; - } - var delegate = intervalProvider.delegate; - if (delegate === null || delegate === void 0 ? void 0 : delegate.setInterval) { - return delegate.setInterval.apply(delegate, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([handler, timeout], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))); - } - return setInterval.apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([handler, timeout], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))); - }, - clearInterval: function (handle) { - var delegate = intervalProvider.delegate; - return ((delegate === null || delegate === void 0 ? void 0 : delegate.clearInterval) || clearInterval)(handle); - }, - delegate: undefined, -}; -//# sourceMappingURL=intervalProvider.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/performanceTimestampProvider.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return performanceTimestampProvider; }); -var performanceTimestampProvider = { - now: function () { - return (performanceTimestampProvider.delegate || performance).now(); - }, - delegate: undefined, -}; -//# sourceMappingURL=performanceTimestampProvider.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/queue.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return queueScheduler; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return queue; }); -/* harmony import */ var _QueueAction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/QueueAction.js"); -/* harmony import */ var _QueueScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/QueueScheduler.js"); - - -var queueScheduler = new _QueueScheduler__WEBPACK_IMPORTED_MODULE_1__[/* QueueScheduler */ "a"](_QueueAction__WEBPACK_IMPORTED_MODULE_0__[/* QueueAction */ "a"]); -var queue = queueScheduler; -//# sourceMappingURL=queue.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/scheduler/timeoutProvider.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return timeoutProvider; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); - -var timeoutProvider = { - setTimeout: function (handler, timeout) { - var args = []; - for (var _i = 2; _i < arguments.length; _i++) { - args[_i - 2] = arguments[_i]; - } - var delegate = timeoutProvider.delegate; - if (delegate === null || delegate === void 0 ? void 0 : delegate.setTimeout) { - return delegate.setTimeout.apply(delegate, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([handler, timeout], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))); - } - return setTimeout.apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([handler, timeout], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))); - }, - clearTimeout: function (handle) { - var delegate = timeoutProvider.delegate; - return ((delegate === null || delegate === void 0 ? void 0 : delegate.clearTimeout) || clearTimeout)(handle); - }, - delegate: undefined, -}; -//# sourceMappingURL=timeoutProvider.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/symbol/iterator.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* unused harmony export getSymbolIterator */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return iterator; }); -function getSymbolIterator() { - if (typeof Symbol !== 'function' || !Symbol.iterator) { - return '@@iterator'; - } - return Symbol.iterator; -} -var iterator = getSymbolIterator(); -//# sourceMappingURL=iterator.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/symbol/observable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return observable; }); -var observable = (function () { return (typeof Symbol === 'function' && Symbol.observable) || '@@observable'; })(); -//# sourceMappingURL=observable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/ArgumentOutOfRangeError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return ArgumentOutOfRangeError; }); -/* harmony import */ var _createErrorClass__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js"); - -var ArgumentOutOfRangeError = Object(_createErrorClass__WEBPACK_IMPORTED_MODULE_0__[/* createErrorClass */ "a"])(function (_super) { - return function ArgumentOutOfRangeErrorImpl() { - _super(this); - this.name = 'ArgumentOutOfRangeError'; - this.message = 'argument out of range'; - }; -}); -//# sourceMappingURL=ArgumentOutOfRangeError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/EmptyError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return EmptyError; }); -/* harmony import */ var _createErrorClass__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js"); - -var EmptyError = Object(_createErrorClass__WEBPACK_IMPORTED_MODULE_0__[/* createErrorClass */ "a"])(function (_super) { return function EmptyErrorImpl() { - _super(this); - this.name = 'EmptyError'; - this.message = 'no elements in sequence'; -}; }); -//# sourceMappingURL=EmptyError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/Immediate.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Immediate; }); -/* unused harmony export TestTools */ -var nextHandle = 1; -var resolved; -var activeHandles = {}; -function findAndClearHandle(handle) { - if (handle in activeHandles) { - delete activeHandles[handle]; - return true; - } - return false; -} -var Immediate = { - setImmediate: function (cb) { - var handle = nextHandle++; - activeHandles[handle] = true; - if (!resolved) { - resolved = Promise.resolve(); - } - resolved.then(function () { return findAndClearHandle(handle) && cb(); }); - return handle; - }, - clearImmediate: function (handle) { - findAndClearHandle(handle); - }, -}; -var TestTools = { - pending: function () { - return Object.keys(activeHandles).length; - } -}; -//# sourceMappingURL=Immediate.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/NotFoundError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return NotFoundError; }); -/* harmony import */ var _createErrorClass__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js"); - -var NotFoundError = Object(_createErrorClass__WEBPACK_IMPORTED_MODULE_0__[/* createErrorClass */ "a"])(function (_super) { - return function NotFoundErrorImpl(message) { - _super(this); - this.name = 'NotFoundError'; - this.message = message; - }; -}); -//# sourceMappingURL=NotFoundError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/ObjectUnsubscribedError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return ObjectUnsubscribedError; }); -/* harmony import */ var _createErrorClass__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js"); - -var ObjectUnsubscribedError = Object(_createErrorClass__WEBPACK_IMPORTED_MODULE_0__[/* createErrorClass */ "a"])(function (_super) { - return function ObjectUnsubscribedErrorImpl() { - _super(this); - this.name = 'ObjectUnsubscribedError'; - this.message = 'object unsubscribed'; - }; -}); -//# sourceMappingURL=ObjectUnsubscribedError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/SequenceError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return SequenceError; }); -/* harmony import */ var _createErrorClass__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js"); - -var SequenceError = Object(_createErrorClass__WEBPACK_IMPORTED_MODULE_0__[/* createErrorClass */ "a"])(function (_super) { - return function SequenceErrorImpl(message) { - _super(this); - this.name = 'SequenceError'; - this.message = message; - }; -}); -//# sourceMappingURL=SequenceError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/UnsubscriptionError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return UnsubscriptionError; }); -/* harmony import */ var _createErrorClass__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js"); - -var UnsubscriptionError = Object(_createErrorClass__WEBPACK_IMPORTED_MODULE_0__[/* createErrorClass */ "a"])(function (_super) { - return function UnsubscriptionErrorImpl(errors) { - _super(this); - this.message = errors - ? errors.length + " errors occurred during unsubscription:\n" + errors.map(function (err, i) { return i + 1 + ") " + err.toString(); }).join('\n ') - : ''; - this.name = 'UnsubscriptionError'; - this.errors = errors; - }; -}); -//# sourceMappingURL=UnsubscriptionError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/args.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return popResultSelector; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return popScheduler; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return popNumber; }); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); -/* harmony import */ var _isScheduler__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isScheduler.js"); - - -function last(arr) { - return arr[arr.length - 1]; -} -function popResultSelector(args) { - return Object(_isFunction__WEBPACK_IMPORTED_MODULE_0__[/* isFunction */ "a"])(last(args)) ? args.pop() : undefined; -} -function popScheduler(args) { - return Object(_isScheduler__WEBPACK_IMPORTED_MODULE_1__[/* isScheduler */ "a"])(last(args)) ? args.pop() : undefined; -} -function popNumber(args, defaultValue) { - return typeof last(args) === 'number' ? args.pop() : defaultValue; -} -//# sourceMappingURL=args.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/argsArgArrayOrObject.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return argsArgArrayOrObject; }); -var isArray = Array.isArray; -var getPrototypeOf = Object.getPrototypeOf, objectProto = Object.prototype, getKeys = Object.keys; -function argsArgArrayOrObject(args) { - if (args.length === 1) { - var first_1 = args[0]; - if (isArray(first_1)) { - return { args: first_1, keys: null }; - } - if (isPOJO(first_1)) { - var keys = getKeys(first_1); - return { - args: keys.map(function (key) { return first_1[key]; }), - keys: keys, - }; - } - } - return { args: args, keys: null }; -} -function isPOJO(obj) { - return obj && typeof obj === 'object' && getPrototypeOf(obj) === objectProto; -} -//# sourceMappingURL=argsArgArrayOrObject.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/argsOrArgArray.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return argsOrArgArray; }); -var isArray = Array.isArray; -function argsOrArgArray(args) { - return args.length === 1 && isArray(args[0]) ? args[0] : args; -} -//# sourceMappingURL=argsOrArgArray.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/arrRemove.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return arrRemove; }); -function arrRemove(arr, item) { - if (arr) { - var index = arr.indexOf(item); - 0 <= index && arr.splice(index, 1); - } -} -//# sourceMappingURL=arrRemove.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/createErrorClass.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return createErrorClass; }); -function createErrorClass(createImpl) { - var _super = function (instance) { - Error.call(instance); - instance.stack = new Error().stack; - }; - var ctorFunc = createImpl(_super); - ctorFunc.prototype = Object.create(Error.prototype); - ctorFunc.prototype.constructor = ctorFunc; - return ctorFunc; -} -//# sourceMappingURL=createErrorClass.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/createObject.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return createObject; }); -function createObject(keys, values) { - return keys.reduce(function (result, key, i) { return ((result[key] = values[i]), result); }, {}); -} -//# sourceMappingURL=createObject.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/errorContext.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return errorContext; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return captureError; }); -/* harmony import */ var _config__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/config.js"); - -var context = null; -function errorContext(cb) { - if (_config__WEBPACK_IMPORTED_MODULE_0__[/* config */ "a"].useDeprecatedSynchronousErrorHandling) { - var isRoot = !context; - if (isRoot) { - context = { errorThrown: false, error: null }; - } - cb(); - if (isRoot) { - var _a = context, errorThrown = _a.errorThrown, error = _a.error; - context = null; - if (errorThrown) { - throw error; - } - } - } - else { - cb(); - } -} -function captureError(err) { - if (_config__WEBPACK_IMPORTED_MODULE_0__[/* config */ "a"].useDeprecatedSynchronousErrorHandling && context) { - context.errorThrown = true; - context.error = err; - } -} -//# sourceMappingURL=errorContext.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/executeSchedule.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return executeSchedule; }); -function executeSchedule(parentSubscription, scheduler, work, delay, repeat) { - if (delay === void 0) { delay = 0; } - if (repeat === void 0) { repeat = false; } - var scheduleSubscription = scheduler.schedule(function () { - work(); - if (repeat) { - parentSubscription.add(this.schedule(null, delay)); - } - else { - this.unsubscribe(); - } - }, delay); - parentSubscription.add(scheduleSubscription); - if (!repeat) { - return scheduleSubscription; - } -} -//# sourceMappingURL=executeSchedule.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/identity.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return identity; }); -function identity(x) { - return x; -} -//# sourceMappingURL=identity.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isArrayLike.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isArrayLike; }); -var isArrayLike = (function (x) { return x && typeof x.length === 'number' && typeof x !== 'function'; }); -//# sourceMappingURL=isArrayLike.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isAsyncIterable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isAsyncIterable; }); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - -function isAsyncIterable(obj) { - return Symbol.asyncIterator && Object(_isFunction__WEBPACK_IMPORTED_MODULE_0__[/* isFunction */ "a"])(obj === null || obj === void 0 ? void 0 : obj[Symbol.asyncIterator]); -} -//# sourceMappingURL=isAsyncIterable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isDate.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isValidDate; }); -function isValidDate(value) { - return value instanceof Date && !isNaN(value); -} -//# sourceMappingURL=isDate.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isFunction; }); -function isFunction(value) { - return typeof value === 'function'; -} -//# sourceMappingURL=isFunction.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isInteropObservable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isInteropObservable; }); -/* harmony import */ var _symbol_observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/symbol/observable.js"); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function isInteropObservable(input) { - return Object(_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(input[_symbol_observable__WEBPACK_IMPORTED_MODULE_0__[/* observable */ "a"]]); -} -//# sourceMappingURL=isInteropObservable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isIterable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isIterable; }); -/* harmony import */ var _symbol_iterator__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/symbol/iterator.js"); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function isIterable(input) { - return Object(_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(input === null || input === void 0 ? void 0 : input[_symbol_iterator__WEBPACK_IMPORTED_MODULE_0__[/* iterator */ "a"]]); -} -//# sourceMappingURL=isIterable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isObservable.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isObservable; }); -/* harmony import */ var _Observable__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/Observable.js"); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function isObservable(obj) { - return !!obj && (obj instanceof _Observable__WEBPACK_IMPORTED_MODULE_0__[/* Observable */ "a"] || (Object(_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(obj.lift) && Object(_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(obj.subscribe))); -} -//# sourceMappingURL=isObservable.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isPromise.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isPromise; }); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - -function isPromise(value) { - return Object(_isFunction__WEBPACK_IMPORTED_MODULE_0__[/* isFunction */ "a"])(value === null || value === void 0 ? void 0 : value.then); -} -//# sourceMappingURL=isPromise.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isReadableStreamLike.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return readableStreamLikeToAsyncGenerator; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isReadableStreamLike; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - - -function readableStreamLikeToAsyncGenerator(readableStream) { - return Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __asyncGenerator */ "a"])(this, arguments, function readableStreamLikeToAsyncGenerator_1() { - var reader, _a, value, done; - return Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __generator */ "f"])(this, function (_b) { - switch (_b.label) { - case 0: - reader = readableStream.getReader(); - _b.label = 1; - case 1: - _b.trys.push([1, , 9, 10]); - _b.label = 2; - case 2: - if (false) {} - return [4, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __await */ "c"])(reader.read())]; - case 3: - _a = _b.sent(), value = _a.value, done = _a.done; - if (!done) return [3, 5]; - return [4, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __await */ "c"])(void 0)]; - case 4: return [2, _b.sent()]; - case 5: return [4, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __await */ "c"])(value)]; - case 6: return [4, _b.sent()]; - case 7: - _b.sent(); - return [3, 2]; - case 8: return [3, 10]; - case 9: - reader.releaseLock(); - return [7]; - case 10: return [2]; - } - }); - }); -} -function isReadableStreamLike(obj) { - return Object(_isFunction__WEBPACK_IMPORTED_MODULE_1__[/* isFunction */ "a"])(obj === null || obj === void 0 ? void 0 : obj.getReader); -} -//# sourceMappingURL=isReadableStreamLike.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/isScheduler.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isScheduler; }); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - -function isScheduler(value) { - return value && Object(_isFunction__WEBPACK_IMPORTED_MODULE_0__[/* isFunction */ "a"])(value.schedule); -} -//# sourceMappingURL=isScheduler.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/lift.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return hasLift; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return operate; }); -/* harmony import */ var _isFunction__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/isFunction.js"); - -function hasLift(source) { - return Object(_isFunction__WEBPACK_IMPORTED_MODULE_0__[/* isFunction */ "a"])(source === null || source === void 0 ? void 0 : source.lift); -} -function operate(init) { - return function (source) { - if (hasLift(source)) { - return source.lift(function (liftedSource) { - try { - return init(liftedSource, this); - } - catch (err) { - this.error(err); - } - }); - } - throw new TypeError('Unable to lift unknown Observable type'); - }; -} -//# sourceMappingURL=lift.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/mapOneOrManyArgs.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return mapOneOrManyArgs; }); -/* harmony import */ var tslib__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/node_modules/tslib/tslib.es6.js"); -/* harmony import */ var _operators_map__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); - - -var isArray = Array.isArray; -function callOrApply(fn, args) { - return isArray(args) ? fn.apply(void 0, Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __spreadArray */ "h"])([], Object(tslib__WEBPACK_IMPORTED_MODULE_0__[/* __read */ "g"])(args))) : fn(args); -} -function mapOneOrManyArgs(fn) { - return Object(_operators_map__WEBPACK_IMPORTED_MODULE_1__[/* map */ "a"])(function (args) { return callOrApply(fn, args); }); -} -//# sourceMappingURL=mapOneOrManyArgs.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/noop.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return noop; }); -function noop() { } -//# sourceMappingURL=noop.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/not.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return not; }); -function not(pred, thisArg) { - return function (value, index) { return !pred.call(thisArg, value, index); }; -} -//# sourceMappingURL=not.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/pipe.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return pipe; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return pipeFromArray; }); -/* harmony import */ var _identity__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/util/identity.js"); - -function pipe() { - var fns = []; - for (var _i = 0; _i < arguments.length; _i++) { - fns[_i] = arguments[_i]; - } - return pipeFromArray(fns); -} -function pipeFromArray(fns) { - if (fns.length === 0) { - return _identity__WEBPACK_IMPORTED_MODULE_0__[/* identity */ "a"]; - } - if (fns.length === 1) { - return fns[0]; - } - return function piped(input) { - return fns.reduce(function (prev, fn) { return fn(prev); }, input); - }; -} -//# sourceMappingURL=pipe.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/reportUnhandledError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return reportUnhandledError; }); -/* harmony import */ var _config__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/config.js"); -/* harmony import */ var _scheduler_timeoutProvider__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/scheduler/timeoutProvider.js"); - - -function reportUnhandledError(err) { - _scheduler_timeoutProvider__WEBPACK_IMPORTED_MODULE_1__[/* timeoutProvider */ "a"].setTimeout(function () { - var onUnhandledError = _config__WEBPACK_IMPORTED_MODULE_0__[/* config */ "a"].onUnhandledError; - if (onUnhandledError) { - onUnhandledError(err); - } - else { - throw err; - } - }); -} -//# sourceMappingURL=reportUnhandledError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/internal/util/throwUnobservableError.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return createInvalidObservableTypeError; }); -function createInvalidObservableTypeError(input) { - return new TypeError("You provided " + (input !== null && typeof input === 'object' ? 'an invalid object' : "'" + input + "'") + " where a stream was expected. You can provide an Observable, Promise, ReadableStream, Array, AsyncIterable, or Iterable."); -} -//# sourceMappingURL=throwUnobservableError.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/dist/esm5/operators/index.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -__webpack_require__.r(__webpack_exports__); -/* harmony import */ var _internal_operators_audit__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/audit.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "audit", function() { return _internal_operators_audit__WEBPACK_IMPORTED_MODULE_0__["a"]; }); - -/* harmony import */ var _internal_operators_auditTime__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/auditTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "auditTime", function() { return _internal_operators_auditTime__WEBPACK_IMPORTED_MODULE_1__["a"]; }); - -/* harmony import */ var _internal_operators_buffer__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/buffer.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "buffer", function() { return _internal_operators_buffer__WEBPACK_IMPORTED_MODULE_2__["a"]; }); - -/* harmony import */ var _internal_operators_bufferCount__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferCount.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferCount", function() { return _internal_operators_bufferCount__WEBPACK_IMPORTED_MODULE_3__["a"]; }); - -/* harmony import */ var _internal_operators_bufferTime__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferTime", function() { return _internal_operators_bufferTime__WEBPACK_IMPORTED_MODULE_4__["a"]; }); - -/* harmony import */ var _internal_operators_bufferToggle__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferToggle.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferToggle", function() { return _internal_operators_bufferToggle__WEBPACK_IMPORTED_MODULE_5__["a"]; }); - -/* harmony import */ var _internal_operators_bufferWhen__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/bufferWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "bufferWhen", function() { return _internal_operators_bufferWhen__WEBPACK_IMPORTED_MODULE_6__["a"]; }); - -/* harmony import */ var _internal_operators_catchError__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/catchError.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "catchError", function() { return _internal_operators_catchError__WEBPACK_IMPORTED_MODULE_7__["a"]; }); - -/* harmony import */ var _internal_operators_combineAll__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineAll", function() { return _internal_operators_combineAll__WEBPACK_IMPORTED_MODULE_8__["a"]; }); - -/* harmony import */ var _internal_operators_combineLatestAll__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineLatestAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineLatestAll", function() { return _internal_operators_combineLatestAll__WEBPACK_IMPORTED_MODULE_9__["a"]; }); - -/* harmony import */ var _internal_operators_combineLatest__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineLatest.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineLatest", function() { return _internal_operators_combineLatest__WEBPACK_IMPORTED_MODULE_10__["a"]; }); - -/* harmony import */ var _internal_operators_combineLatestWith__WEBPACK_IMPORTED_MODULE_11__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/combineLatestWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "combineLatestWith", function() { return _internal_operators_combineLatestWith__WEBPACK_IMPORTED_MODULE_11__["a"]; }); - -/* harmony import */ var _internal_operators_concat__WEBPACK_IMPORTED_MODULE_12__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concat.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concat", function() { return _internal_operators_concat__WEBPACK_IMPORTED_MODULE_12__["a"]; }); - -/* harmony import */ var _internal_operators_concatAll__WEBPACK_IMPORTED_MODULE_13__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatAll", function() { return _internal_operators_concatAll__WEBPACK_IMPORTED_MODULE_13__["a"]; }); - -/* harmony import */ var _internal_operators_concatMap__WEBPACK_IMPORTED_MODULE_14__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatMap", function() { return _internal_operators_concatMap__WEBPACK_IMPORTED_MODULE_14__["a"]; }); - -/* harmony import */ var _internal_operators_concatMapTo__WEBPACK_IMPORTED_MODULE_15__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatMapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatMapTo", function() { return _internal_operators_concatMapTo__WEBPACK_IMPORTED_MODULE_15__["a"]; }); - -/* harmony import */ var _internal_operators_concatWith__WEBPACK_IMPORTED_MODULE_16__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/concatWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "concatWith", function() { return _internal_operators_concatWith__WEBPACK_IMPORTED_MODULE_16__["a"]; }); - -/* harmony import */ var _internal_operators_connect__WEBPACK_IMPORTED_MODULE_17__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/connect.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "connect", function() { return _internal_operators_connect__WEBPACK_IMPORTED_MODULE_17__["a"]; }); - -/* harmony import */ var _internal_operators_count__WEBPACK_IMPORTED_MODULE_18__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/count.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "count", function() { return _internal_operators_count__WEBPACK_IMPORTED_MODULE_18__["a"]; }); - -/* harmony import */ var _internal_operators_debounce__WEBPACK_IMPORTED_MODULE_19__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/debounce.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "debounce", function() { return _internal_operators_debounce__WEBPACK_IMPORTED_MODULE_19__["a"]; }); - -/* harmony import */ var _internal_operators_debounceTime__WEBPACK_IMPORTED_MODULE_20__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/debounceTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "debounceTime", function() { return _internal_operators_debounceTime__WEBPACK_IMPORTED_MODULE_20__["a"]; }); - -/* harmony import */ var _internal_operators_defaultIfEmpty__WEBPACK_IMPORTED_MODULE_21__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/defaultIfEmpty.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "defaultIfEmpty", function() { return _internal_operators_defaultIfEmpty__WEBPACK_IMPORTED_MODULE_21__["a"]; }); - -/* harmony import */ var _internal_operators_delay__WEBPACK_IMPORTED_MODULE_22__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/delay.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "delay", function() { return _internal_operators_delay__WEBPACK_IMPORTED_MODULE_22__["a"]; }); - -/* harmony import */ var _internal_operators_delayWhen__WEBPACK_IMPORTED_MODULE_23__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/delayWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "delayWhen", function() { return _internal_operators_delayWhen__WEBPACK_IMPORTED_MODULE_23__["a"]; }); - -/* harmony import */ var _internal_operators_dematerialize__WEBPACK_IMPORTED_MODULE_24__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/dematerialize.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "dematerialize", function() { return _internal_operators_dematerialize__WEBPACK_IMPORTED_MODULE_24__["a"]; }); - -/* harmony import */ var _internal_operators_distinct__WEBPACK_IMPORTED_MODULE_25__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/distinct.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "distinct", function() { return _internal_operators_distinct__WEBPACK_IMPORTED_MODULE_25__["a"]; }); - -/* harmony import */ var _internal_operators_distinctUntilChanged__WEBPACK_IMPORTED_MODULE_26__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/distinctUntilChanged.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "distinctUntilChanged", function() { return _internal_operators_distinctUntilChanged__WEBPACK_IMPORTED_MODULE_26__["a"]; }); - -/* harmony import */ var _internal_operators_distinctUntilKeyChanged__WEBPACK_IMPORTED_MODULE_27__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/distinctUntilKeyChanged.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "distinctUntilKeyChanged", function() { return _internal_operators_distinctUntilKeyChanged__WEBPACK_IMPORTED_MODULE_27__["a"]; }); - -/* harmony import */ var _internal_operators_elementAt__WEBPACK_IMPORTED_MODULE_28__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/elementAt.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "elementAt", function() { return _internal_operators_elementAt__WEBPACK_IMPORTED_MODULE_28__["a"]; }); - -/* harmony import */ var _internal_operators_endWith__WEBPACK_IMPORTED_MODULE_29__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/endWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "endWith", function() { return _internal_operators_endWith__WEBPACK_IMPORTED_MODULE_29__["a"]; }); - -/* harmony import */ var _internal_operators_every__WEBPACK_IMPORTED_MODULE_30__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/every.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "every", function() { return _internal_operators_every__WEBPACK_IMPORTED_MODULE_30__["a"]; }); - -/* harmony import */ var _internal_operators_exhaust__WEBPACK_IMPORTED_MODULE_31__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/exhaust.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "exhaust", function() { return _internal_operators_exhaust__WEBPACK_IMPORTED_MODULE_31__["a"]; }); - -/* harmony import */ var _internal_operators_exhaustAll__WEBPACK_IMPORTED_MODULE_32__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/exhaustAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "exhaustAll", function() { return _internal_operators_exhaustAll__WEBPACK_IMPORTED_MODULE_32__["a"]; }); - -/* harmony import */ var _internal_operators_exhaustMap__WEBPACK_IMPORTED_MODULE_33__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/exhaustMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "exhaustMap", function() { return _internal_operators_exhaustMap__WEBPACK_IMPORTED_MODULE_33__["a"]; }); - -/* harmony import */ var _internal_operators_expand__WEBPACK_IMPORTED_MODULE_34__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/expand.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "expand", function() { return _internal_operators_expand__WEBPACK_IMPORTED_MODULE_34__["a"]; }); - -/* harmony import */ var _internal_operators_filter__WEBPACK_IMPORTED_MODULE_35__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/filter.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "filter", function() { return _internal_operators_filter__WEBPACK_IMPORTED_MODULE_35__["a"]; }); - -/* harmony import */ var _internal_operators_finalize__WEBPACK_IMPORTED_MODULE_36__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/finalize.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "finalize", function() { return _internal_operators_finalize__WEBPACK_IMPORTED_MODULE_36__["a"]; }); - -/* harmony import */ var _internal_operators_find__WEBPACK_IMPORTED_MODULE_37__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/find.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "find", function() { return _internal_operators_find__WEBPACK_IMPORTED_MODULE_37__["b"]; }); - -/* harmony import */ var _internal_operators_findIndex__WEBPACK_IMPORTED_MODULE_38__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/findIndex.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "findIndex", function() { return _internal_operators_findIndex__WEBPACK_IMPORTED_MODULE_38__["a"]; }); - -/* harmony import */ var _internal_operators_first__WEBPACK_IMPORTED_MODULE_39__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/first.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "first", function() { return _internal_operators_first__WEBPACK_IMPORTED_MODULE_39__["a"]; }); - -/* harmony import */ var _internal_operators_groupBy__WEBPACK_IMPORTED_MODULE_40__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/groupBy.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "groupBy", function() { return _internal_operators_groupBy__WEBPACK_IMPORTED_MODULE_40__["a"]; }); - -/* harmony import */ var _internal_operators_ignoreElements__WEBPACK_IMPORTED_MODULE_41__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/ignoreElements.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "ignoreElements", function() { return _internal_operators_ignoreElements__WEBPACK_IMPORTED_MODULE_41__["a"]; }); - -/* harmony import */ var _internal_operators_isEmpty__WEBPACK_IMPORTED_MODULE_42__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/isEmpty.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "isEmpty", function() { return _internal_operators_isEmpty__WEBPACK_IMPORTED_MODULE_42__["a"]; }); - -/* harmony import */ var _internal_operators_last__WEBPACK_IMPORTED_MODULE_43__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/last.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "last", function() { return _internal_operators_last__WEBPACK_IMPORTED_MODULE_43__["a"]; }); - -/* harmony import */ var _internal_operators_map__WEBPACK_IMPORTED_MODULE_44__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/map.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "map", function() { return _internal_operators_map__WEBPACK_IMPORTED_MODULE_44__["a"]; }); - -/* harmony import */ var _internal_operators_mapTo__WEBPACK_IMPORTED_MODULE_45__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mapTo", function() { return _internal_operators_mapTo__WEBPACK_IMPORTED_MODULE_45__["a"]; }); - -/* harmony import */ var _internal_operators_materialize__WEBPACK_IMPORTED_MODULE_46__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/materialize.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "materialize", function() { return _internal_operators_materialize__WEBPACK_IMPORTED_MODULE_46__["a"]; }); - -/* harmony import */ var _internal_operators_max__WEBPACK_IMPORTED_MODULE_47__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/max.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "max", function() { return _internal_operators_max__WEBPACK_IMPORTED_MODULE_47__["a"]; }); - -/* harmony import */ var _internal_operators_merge__WEBPACK_IMPORTED_MODULE_48__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/merge.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "merge", function() { return _internal_operators_merge__WEBPACK_IMPORTED_MODULE_48__["a"]; }); - -/* harmony import */ var _internal_operators_mergeAll__WEBPACK_IMPORTED_MODULE_49__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeAll", function() { return _internal_operators_mergeAll__WEBPACK_IMPORTED_MODULE_49__["a"]; }); - -/* harmony import */ var _internal_operators_flatMap__WEBPACK_IMPORTED_MODULE_50__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/flatMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "flatMap", function() { return _internal_operators_flatMap__WEBPACK_IMPORTED_MODULE_50__["a"]; }); - -/* harmony import */ var _internal_operators_mergeMap__WEBPACK_IMPORTED_MODULE_51__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeMap", function() { return _internal_operators_mergeMap__WEBPACK_IMPORTED_MODULE_51__["a"]; }); - -/* harmony import */ var _internal_operators_mergeMapTo__WEBPACK_IMPORTED_MODULE_52__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeMapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeMapTo", function() { return _internal_operators_mergeMapTo__WEBPACK_IMPORTED_MODULE_52__["a"]; }); - -/* harmony import */ var _internal_operators_mergeScan__WEBPACK_IMPORTED_MODULE_53__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeScan.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeScan", function() { return _internal_operators_mergeScan__WEBPACK_IMPORTED_MODULE_53__["a"]; }); - -/* harmony import */ var _internal_operators_mergeWith__WEBPACK_IMPORTED_MODULE_54__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/mergeWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "mergeWith", function() { return _internal_operators_mergeWith__WEBPACK_IMPORTED_MODULE_54__["a"]; }); - -/* harmony import */ var _internal_operators_min__WEBPACK_IMPORTED_MODULE_55__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/min.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "min", function() { return _internal_operators_min__WEBPACK_IMPORTED_MODULE_55__["a"]; }); - -/* harmony import */ var _internal_operators_multicast__WEBPACK_IMPORTED_MODULE_56__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/multicast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "multicast", function() { return _internal_operators_multicast__WEBPACK_IMPORTED_MODULE_56__["a"]; }); - -/* harmony import */ var _internal_operators_observeOn__WEBPACK_IMPORTED_MODULE_57__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/observeOn.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "observeOn", function() { return _internal_operators_observeOn__WEBPACK_IMPORTED_MODULE_57__["a"]; }); - -/* harmony import */ var _internal_operators_onErrorResumeNext__WEBPACK_IMPORTED_MODULE_58__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/onErrorResumeNext.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "onErrorResumeNext", function() { return _internal_operators_onErrorResumeNext__WEBPACK_IMPORTED_MODULE_58__["a"]; }); - -/* harmony import */ var _internal_operators_pairwise__WEBPACK_IMPORTED_MODULE_59__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/pairwise.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "pairwise", function() { return _internal_operators_pairwise__WEBPACK_IMPORTED_MODULE_59__["a"]; }); - -/* harmony import */ var _internal_operators_partition__WEBPACK_IMPORTED_MODULE_60__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/partition.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "partition", function() { return _internal_operators_partition__WEBPACK_IMPORTED_MODULE_60__["a"]; }); - -/* harmony import */ var _internal_operators_pluck__WEBPACK_IMPORTED_MODULE_61__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/pluck.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "pluck", function() { return _internal_operators_pluck__WEBPACK_IMPORTED_MODULE_61__["a"]; }); - -/* harmony import */ var _internal_operators_publish__WEBPACK_IMPORTED_MODULE_62__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publish.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publish", function() { return _internal_operators_publish__WEBPACK_IMPORTED_MODULE_62__["a"]; }); - -/* harmony import */ var _internal_operators_publishBehavior__WEBPACK_IMPORTED_MODULE_63__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publishBehavior.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publishBehavior", function() { return _internal_operators_publishBehavior__WEBPACK_IMPORTED_MODULE_63__["a"]; }); - -/* harmony import */ var _internal_operators_publishLast__WEBPACK_IMPORTED_MODULE_64__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publishLast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publishLast", function() { return _internal_operators_publishLast__WEBPACK_IMPORTED_MODULE_64__["a"]; }); - -/* harmony import */ var _internal_operators_publishReplay__WEBPACK_IMPORTED_MODULE_65__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/publishReplay.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "publishReplay", function() { return _internal_operators_publishReplay__WEBPACK_IMPORTED_MODULE_65__["a"]; }); - -/* harmony import */ var _internal_operators_race__WEBPACK_IMPORTED_MODULE_66__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/race.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "race", function() { return _internal_operators_race__WEBPACK_IMPORTED_MODULE_66__["a"]; }); - -/* harmony import */ var _internal_operators_raceWith__WEBPACK_IMPORTED_MODULE_67__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/raceWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "raceWith", function() { return _internal_operators_raceWith__WEBPACK_IMPORTED_MODULE_67__["a"]; }); - -/* harmony import */ var _internal_operators_reduce__WEBPACK_IMPORTED_MODULE_68__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/reduce.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "reduce", function() { return _internal_operators_reduce__WEBPACK_IMPORTED_MODULE_68__["a"]; }); - -/* harmony import */ var _internal_operators_repeat__WEBPACK_IMPORTED_MODULE_69__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/repeat.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "repeat", function() { return _internal_operators_repeat__WEBPACK_IMPORTED_MODULE_69__["a"]; }); - -/* harmony import */ var _internal_operators_repeatWhen__WEBPACK_IMPORTED_MODULE_70__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/repeatWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "repeatWhen", function() { return _internal_operators_repeatWhen__WEBPACK_IMPORTED_MODULE_70__["a"]; }); - -/* harmony import */ var _internal_operators_retry__WEBPACK_IMPORTED_MODULE_71__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/retry.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "retry", function() { return _internal_operators_retry__WEBPACK_IMPORTED_MODULE_71__["a"]; }); - -/* harmony import */ var _internal_operators_retryWhen__WEBPACK_IMPORTED_MODULE_72__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/retryWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "retryWhen", function() { return _internal_operators_retryWhen__WEBPACK_IMPORTED_MODULE_72__["a"]; }); - -/* harmony import */ var _internal_operators_refCount__WEBPACK_IMPORTED_MODULE_73__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/refCount.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "refCount", function() { return _internal_operators_refCount__WEBPACK_IMPORTED_MODULE_73__["a"]; }); - -/* harmony import */ var _internal_operators_sample__WEBPACK_IMPORTED_MODULE_74__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/sample.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "sample", function() { return _internal_operators_sample__WEBPACK_IMPORTED_MODULE_74__["a"]; }); - -/* harmony import */ var _internal_operators_sampleTime__WEBPACK_IMPORTED_MODULE_75__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/sampleTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "sampleTime", function() { return _internal_operators_sampleTime__WEBPACK_IMPORTED_MODULE_75__["a"]; }); - -/* harmony import */ var _internal_operators_scan__WEBPACK_IMPORTED_MODULE_76__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/scan.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "scan", function() { return _internal_operators_scan__WEBPACK_IMPORTED_MODULE_76__["a"]; }); - -/* harmony import */ var _internal_operators_sequenceEqual__WEBPACK_IMPORTED_MODULE_77__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/sequenceEqual.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "sequenceEqual", function() { return _internal_operators_sequenceEqual__WEBPACK_IMPORTED_MODULE_77__["a"]; }); - -/* harmony import */ var _internal_operators_share__WEBPACK_IMPORTED_MODULE_78__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/share.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "share", function() { return _internal_operators_share__WEBPACK_IMPORTED_MODULE_78__["a"]; }); - -/* harmony import */ var _internal_operators_shareReplay__WEBPACK_IMPORTED_MODULE_79__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/shareReplay.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "shareReplay", function() { return _internal_operators_shareReplay__WEBPACK_IMPORTED_MODULE_79__["a"]; }); - -/* harmony import */ var _internal_operators_single__WEBPACK_IMPORTED_MODULE_80__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/single.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "single", function() { return _internal_operators_single__WEBPACK_IMPORTED_MODULE_80__["a"]; }); - -/* harmony import */ var _internal_operators_skip__WEBPACK_IMPORTED_MODULE_81__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skip.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skip", function() { return _internal_operators_skip__WEBPACK_IMPORTED_MODULE_81__["a"]; }); - -/* harmony import */ var _internal_operators_skipLast__WEBPACK_IMPORTED_MODULE_82__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skipLast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skipLast", function() { return _internal_operators_skipLast__WEBPACK_IMPORTED_MODULE_82__["a"]; }); - -/* harmony import */ var _internal_operators_skipUntil__WEBPACK_IMPORTED_MODULE_83__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skipUntil.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skipUntil", function() { return _internal_operators_skipUntil__WEBPACK_IMPORTED_MODULE_83__["a"]; }); - -/* harmony import */ var _internal_operators_skipWhile__WEBPACK_IMPORTED_MODULE_84__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/skipWhile.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "skipWhile", function() { return _internal_operators_skipWhile__WEBPACK_IMPORTED_MODULE_84__["a"]; }); - -/* harmony import */ var _internal_operators_startWith__WEBPACK_IMPORTED_MODULE_85__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/startWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "startWith", function() { return _internal_operators_startWith__WEBPACK_IMPORTED_MODULE_85__["a"]; }); - -/* harmony import */ var _internal_operators_subscribeOn__WEBPACK_IMPORTED_MODULE_86__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/subscribeOn.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "subscribeOn", function() { return _internal_operators_subscribeOn__WEBPACK_IMPORTED_MODULE_86__["a"]; }); - -/* harmony import */ var _internal_operators_switchAll__WEBPACK_IMPORTED_MODULE_87__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchAll", function() { return _internal_operators_switchAll__WEBPACK_IMPORTED_MODULE_87__["a"]; }); - -/* harmony import */ var _internal_operators_switchMap__WEBPACK_IMPORTED_MODULE_88__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchMap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchMap", function() { return _internal_operators_switchMap__WEBPACK_IMPORTED_MODULE_88__["a"]; }); - -/* harmony import */ var _internal_operators_switchMapTo__WEBPACK_IMPORTED_MODULE_89__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchMapTo.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchMapTo", function() { return _internal_operators_switchMapTo__WEBPACK_IMPORTED_MODULE_89__["a"]; }); - -/* harmony import */ var _internal_operators_switchScan__WEBPACK_IMPORTED_MODULE_90__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/switchScan.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "switchScan", function() { return _internal_operators_switchScan__WEBPACK_IMPORTED_MODULE_90__["a"]; }); - -/* harmony import */ var _internal_operators_take__WEBPACK_IMPORTED_MODULE_91__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/take.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "take", function() { return _internal_operators_take__WEBPACK_IMPORTED_MODULE_91__["a"]; }); - -/* harmony import */ var _internal_operators_takeLast__WEBPACK_IMPORTED_MODULE_92__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/takeLast.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "takeLast", function() { return _internal_operators_takeLast__WEBPACK_IMPORTED_MODULE_92__["a"]; }); - -/* harmony import */ var _internal_operators_takeUntil__WEBPACK_IMPORTED_MODULE_93__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/takeUntil.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "takeUntil", function() { return _internal_operators_takeUntil__WEBPACK_IMPORTED_MODULE_93__["a"]; }); - -/* harmony import */ var _internal_operators_takeWhile__WEBPACK_IMPORTED_MODULE_94__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/takeWhile.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "takeWhile", function() { return _internal_operators_takeWhile__WEBPACK_IMPORTED_MODULE_94__["a"]; }); - -/* harmony import */ var _internal_operators_tap__WEBPACK_IMPORTED_MODULE_95__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/tap.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "tap", function() { return _internal_operators_tap__WEBPACK_IMPORTED_MODULE_95__["a"]; }); - -/* harmony import */ var _internal_operators_throttle__WEBPACK_IMPORTED_MODULE_96__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throttle.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "throttle", function() { return _internal_operators_throttle__WEBPACK_IMPORTED_MODULE_96__["b"]; }); - -/* harmony import */ var _internal_operators_throttleTime__WEBPACK_IMPORTED_MODULE_97__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throttleTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "throttleTime", function() { return _internal_operators_throttleTime__WEBPACK_IMPORTED_MODULE_97__["a"]; }); - -/* harmony import */ var _internal_operators_throwIfEmpty__WEBPACK_IMPORTED_MODULE_98__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/throwIfEmpty.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "throwIfEmpty", function() { return _internal_operators_throwIfEmpty__WEBPACK_IMPORTED_MODULE_98__["a"]; }); - -/* harmony import */ var _internal_operators_timeInterval__WEBPACK_IMPORTED_MODULE_99__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timeInterval.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timeInterval", function() { return _internal_operators_timeInterval__WEBPACK_IMPORTED_MODULE_99__["a"]; }); - -/* harmony import */ var _internal_operators_timeout__WEBPACK_IMPORTED_MODULE_100__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timeout.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timeout", function() { return _internal_operators_timeout__WEBPACK_IMPORTED_MODULE_100__["b"]; }); - -/* harmony import */ var _internal_operators_timeoutWith__WEBPACK_IMPORTED_MODULE_101__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timeoutWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timeoutWith", function() { return _internal_operators_timeoutWith__WEBPACK_IMPORTED_MODULE_101__["a"]; }); - -/* harmony import */ var _internal_operators_timestamp__WEBPACK_IMPORTED_MODULE_102__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/timestamp.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "timestamp", function() { return _internal_operators_timestamp__WEBPACK_IMPORTED_MODULE_102__["a"]; }); - -/* harmony import */ var _internal_operators_toArray__WEBPACK_IMPORTED_MODULE_103__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/toArray.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "toArray", function() { return _internal_operators_toArray__WEBPACK_IMPORTED_MODULE_103__["a"]; }); - -/* harmony import */ var _internal_operators_window__WEBPACK_IMPORTED_MODULE_104__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/window.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "window", function() { return _internal_operators_window__WEBPACK_IMPORTED_MODULE_104__["a"]; }); - -/* harmony import */ var _internal_operators_windowCount__WEBPACK_IMPORTED_MODULE_105__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowCount.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowCount", function() { return _internal_operators_windowCount__WEBPACK_IMPORTED_MODULE_105__["a"]; }); - -/* harmony import */ var _internal_operators_windowTime__WEBPACK_IMPORTED_MODULE_106__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowTime.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowTime", function() { return _internal_operators_windowTime__WEBPACK_IMPORTED_MODULE_106__["a"]; }); - -/* harmony import */ var _internal_operators_windowToggle__WEBPACK_IMPORTED_MODULE_107__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowToggle.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowToggle", function() { return _internal_operators_windowToggle__WEBPACK_IMPORTED_MODULE_107__["a"]; }); - -/* harmony import */ var _internal_operators_windowWhen__WEBPACK_IMPORTED_MODULE_108__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/windowWhen.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "windowWhen", function() { return _internal_operators_windowWhen__WEBPACK_IMPORTED_MODULE_108__["a"]; }); - -/* harmony import */ var _internal_operators_withLatestFrom__WEBPACK_IMPORTED_MODULE_109__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/withLatestFrom.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "withLatestFrom", function() { return _internal_operators_withLatestFrom__WEBPACK_IMPORTED_MODULE_109__["a"]; }); - -/* harmony import */ var _internal_operators_zip__WEBPACK_IMPORTED_MODULE_110__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/zip.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "zip", function() { return _internal_operators_zip__WEBPACK_IMPORTED_MODULE_110__["a"]; }); - -/* harmony import */ var _internal_operators_zipAll__WEBPACK_IMPORTED_MODULE_111__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/zipAll.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "zipAll", function() { return _internal_operators_zipAll__WEBPACK_IMPORTED_MODULE_111__["a"]; }); - -/* harmony import */ var _internal_operators_zipWith__WEBPACK_IMPORTED_MODULE_112__ = __webpack_require__("../../node_modules/rxjs/dist/esm5/internal/operators/zipWith.js"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "zipWith", function() { return _internal_operators_zipWith__WEBPACK_IMPORTED_MODULE_112__["a"]; }); - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -//# sourceMappingURL=index.js.map - -/***/ }), - -/***/ "../../node_modules/rxjs/node_modules/tslib/tslib.es6.js": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "e", function() { return __extends; }); -/* unused harmony export __assign */ -/* unused harmony export __rest */ -/* unused harmony export __decorate */ -/* unused harmony export __param */ -/* unused harmony export __metadata */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "d", function() { return __awaiter; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "f", function() { return __generator; }); -/* unused harmony export __createBinding */ -/* unused harmony export __exportStar */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "i", function() { return __values; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "g", function() { return __read; }); -/* unused harmony export __spread */ -/* unused harmony export __spreadArrays */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "h", function() { return __spreadArray; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return __await; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return __asyncGenerator; }); -/* unused harmony export __asyncDelegator */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return __asyncValues; }); -/* unused harmony export __makeTemplateObject */ -/* unused harmony export __importStar */ -/* unused harmony export __importDefault */ -/* unused harmony export __classPrivateFieldGet */ -/* unused harmony export __classPrivateFieldSet */ -/*! ***************************************************************************** -Copyright (c) Microsoft Corporation. - -Permission to use, copy, modify, and/or distribute this software for any -purpose with or without fee is hereby granted. - -THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH -REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY -AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, -INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM -LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR -OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR -PERFORMANCE OF THIS SOFTWARE. -***************************************************************************** */ -/* global Reflect, Promise */ - -var extendStatics = function(d, b) { - extendStatics = Object.setPrototypeOf || - ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) || - function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; }; - return extendStatics(d, b); -}; - -function __extends(d, b) { - if (typeof b !== "function" && b !== null) - throw new TypeError("Class extends value " + String(b) + " is not a constructor or null"); - extendStatics(d, b); - function __() { this.constructor = d; } - d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __()); -} - -var __assign = function() { - __assign = Object.assign || function __assign(t) { - for (var s, i = 1, n = arguments.length; i < n; i++) { - s = arguments[i]; - for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p]; - } - return t; - } - return __assign.apply(this, arguments); -} - -function __rest(s, e) { - var t = {}; - for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0) - t[p] = s[p]; - if (s != null && typeof Object.getOwnPropertySymbols === "function") - for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) { - if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) - t[p[i]] = s[p[i]]; - } - return t; -} - -function __decorate(decorators, target, key, desc) { - var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d; - if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc); - else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r; - return c > 3 && r && Object.defineProperty(target, key, r), r; -} - -function __param(paramIndex, decorator) { - return function (target, key) { decorator(target, key, paramIndex); } -} - -function __metadata(metadataKey, metadataValue) { - if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(metadataKey, metadataValue); -} - -function __awaiter(thisArg, _arguments, P, generator) { - function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } - return new (P || (P = Promise))(function (resolve, reject) { - function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } - function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } - function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } - step((generator = generator.apply(thisArg, _arguments || [])).next()); - }); -} - -function __generator(thisArg, body) { - var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g; - return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g; - function verb(n) { return function (v) { return step([n, v]); }; } - function step(op) { - if (f) throw new TypeError("Generator is already executing."); - while (_) try { - if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t; - if (y = 0, t) op = [op[0] & 2, t.value]; - switch (op[0]) { - case 0: case 1: t = op; break; - case 4: _.label++; return { value: op[1], done: false }; - case 5: _.label++; y = op[1]; op = [0]; continue; - case 7: op = _.ops.pop(); _.trys.pop(); continue; - default: - if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; } - if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; } - if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; } - if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; } - if (t[2]) _.ops.pop(); - _.trys.pop(); continue; - } - op = body.call(thisArg, _); - } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; } - if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true }; - } -} - -var __createBinding = Object.create ? (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } }); -}) : (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - o[k2] = m[k]; -}); - -function __exportStar(m, o) { - for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(o, p)) __createBinding(o, m, p); -} - -function __values(o) { - var s = typeof Symbol === "function" && Symbol.iterator, m = s && o[s], i = 0; - if (m) return m.call(o); - if (o && typeof o.length === "number") return { - next: function () { - if (o && i >= o.length) o = void 0; - return { value: o && o[i++], done: !o }; - } - }; - throw new TypeError(s ? "Object is not iterable." : "Symbol.iterator is not defined."); -} - -function __read(o, n) { - var m = typeof Symbol === "function" && o[Symbol.iterator]; - if (!m) return o; - var i = m.call(o), r, ar = [], e; - try { - while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value); - } - catch (error) { e = { error: error }; } - finally { - try { - if (r && !r.done && (m = i["return"])) m.call(i); - } - finally { if (e) throw e.error; } - } - return ar; -} - -/** @deprecated */ -function __spread() { - for (var ar = [], i = 0; i < arguments.length; i++) - ar = ar.concat(__read(arguments[i])); - return ar; -} - -/** @deprecated */ -function __spreadArrays() { - for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length; - for (var r = Array(s), k = 0, i = 0; i < il; i++) - for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++) - r[k] = a[j]; - return r; -} - -function __spreadArray(to, from, pack) { - if (pack || arguments.length === 2) for (var i = 0, l = from.length, ar; i < l; i++) { - if (ar || !(i in from)) { - if (!ar) ar = Array.prototype.slice.call(from, 0, i); - ar[i] = from[i]; - } - } - return to.concat(ar || Array.prototype.slice.call(from)); -} - -function __await(v) { - return this instanceof __await ? (this.v = v, this) : new __await(v); -} - -function __asyncGenerator(thisArg, _arguments, generator) { - if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined."); - var g = generator.apply(thisArg, _arguments || []), i, q = []; - return i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i; - function verb(n) { if (g[n]) i[n] = function (v) { return new Promise(function (a, b) { q.push([n, v, a, b]) > 1 || resume(n, v); }); }; } - function resume(n, v) { try { step(g[n](v)); } catch (e) { settle(q[0][3], e); } } - function step(r) { r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r); } - function fulfill(value) { resume("next", value); } - function reject(value) { resume("throw", value); } - function settle(f, v) { if (f(v), q.shift(), q.length) resume(q[0][0], q[0][1]); } -} - -function __asyncDelegator(o) { - var i, p; - return i = {}, verb("next"), verb("throw", function (e) { throw e; }), verb("return"), i[Symbol.iterator] = function () { return this; }, i; - function verb(n, f) { i[n] = o[n] ? function (v) { return (p = !p) ? { value: __await(o[n](v)), done: n === "return" } : f ? f(v) : v; } : f; } -} - -function __asyncValues(o) { - if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined."); - var m = o[Symbol.asyncIterator], i; - return m ? m.call(o) : (o = typeof __values === "function" ? __values(o) : o[Symbol.iterator](), i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i); - function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; } - function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); } -} - -function __makeTemplateObject(cooked, raw) { - if (Object.defineProperty) { Object.defineProperty(cooked, "raw", { value: raw }); } else { cooked.raw = raw; } - return cooked; -}; - -var __setModuleDefault = Object.create ? (function(o, v) { - Object.defineProperty(o, "default", { enumerable: true, value: v }); -}) : function(o, v) { - o["default"] = v; -}; - -function __importStar(mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k); - __setModuleDefault(result, mod); - return result; -} - -function __importDefault(mod) { - return (mod && mod.__esModule) ? mod : { default: mod }; -} - -function __classPrivateFieldGet(receiver, state, kind, f) { - if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter"); - if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it"); - return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver); -} - -function __classPrivateFieldSet(receiver, state, value, kind, f) { - if (kind === "m") throw new TypeError("Private method is not writable"); - if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter"); - if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it"); - return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value; -} - - -/***/ }), - -/***/ "../../node_modules/shebang-command/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const shebangRegex = __webpack_require__("../../node_modules/shebang-regex/index.js"); - -module.exports = (string = '') => { - const match = string.match(shebangRegex); - - if (!match) { - return null; - } - - const [path, argument] = match[0].replace(/#! ?/, '').split(' '); - const binary = path.split('/').pop(); - - if (binary === 'env') { - return argument; - } - - return argument ? `${binary} ${argument}` : binary; -}; - - -/***/ }), - -/***/ "../../node_modules/shebang-regex/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = /^#!(.*)/; - - -/***/ }), - -/***/ "../../node_modules/signal-exit/index.js": -/***/ (function(module, exports, __webpack_require__) { - -// Note: since nyc uses this module to output coverage, any lines -// that are in the direct sync flow of nyc's outputCoverage are -// ignored, since we can never get coverage for them. -// grab a reference to node's real process object right away -var process = global.process - -const processOk = function (process) { - return process && - typeof process === 'object' && - typeof process.removeListener === 'function' && - typeof process.emit === 'function' && - typeof process.reallyExit === 'function' && - typeof process.listeners === 'function' && - typeof process.kill === 'function' && - typeof process.pid === 'number' && - typeof process.on === 'function' -} - -// some kind of non-node environment, just no-op -/* istanbul ignore if */ -if (!processOk(process)) { - module.exports = function () { - return function () {} - } -} else { - var assert = __webpack_require__("assert") - var signals = __webpack_require__("../../node_modules/signal-exit/signals.js") - var isWin = /^win/i.test(process.platform) - - var EE = __webpack_require__("events") - /* istanbul ignore if */ - if (typeof EE !== 'function') { - EE = EE.EventEmitter - } - - var emitter - if (process.__signal_exit_emitter__) { - emitter = process.__signal_exit_emitter__ - } else { - emitter = process.__signal_exit_emitter__ = new EE() - emitter.count = 0 - emitter.emitted = {} - } - - // Because this emitter is a global, we have to check to see if a - // previous version of this library failed to enable infinite listeners. - // I know what you're about to say. But literally everything about - // signal-exit is a compromise with evil. Get used to it. - if (!emitter.infinite) { - emitter.setMaxListeners(Infinity) - emitter.infinite = true - } - - module.exports = function (cb, opts) { - /* istanbul ignore if */ - if (!processOk(global.process)) { - return function () {} - } - assert.equal(typeof cb, 'function', 'a callback must be provided for exit handler') - - if (loaded === false) { - load() - } - - var ev = 'exit' - if (opts && opts.alwaysLast) { - ev = 'afterexit' - } - - var remove = function () { - emitter.removeListener(ev, cb) - if (emitter.listeners('exit').length === 0 && - emitter.listeners('afterexit').length === 0) { - unload() - } - } - emitter.on(ev, cb) - - return remove - } - - var unload = function unload () { - if (!loaded || !processOk(global.process)) { - return - } - loaded = false - - signals.forEach(function (sig) { - try { - process.removeListener(sig, sigListeners[sig]) - } catch (er) {} - }) - process.emit = originalProcessEmit - process.reallyExit = originalProcessReallyExit - emitter.count -= 1 - } - module.exports.unload = unload - - var emit = function emit (event, code, signal) { - /* istanbul ignore if */ - if (emitter.emitted[event]) { - return - } - emitter.emitted[event] = true - emitter.emit(event, code, signal) - } - - // { : , ... } - var sigListeners = {} - signals.forEach(function (sig) { - sigListeners[sig] = function listener () { - /* istanbul ignore if */ - if (!processOk(global.process)) { - return - } - // If there are no other listeners, an exit is coming! - // Simplest way: remove us and then re-send the signal. - // We know that this will kill the process, so we can - // safely emit now. - var listeners = process.listeners(sig) - if (listeners.length === emitter.count) { - unload() - emit('exit', null, sig) - /* istanbul ignore next */ - emit('afterexit', null, sig) - /* istanbul ignore next */ - if (isWin && sig === 'SIGHUP') { - // "SIGHUP" throws an `ENOSYS` error on Windows, - // so use a supported signal instead - sig = 'SIGINT' - } - /* istanbul ignore next */ - process.kill(process.pid, sig) - } - } - }) - - module.exports.signals = function () { - return signals - } - - var loaded = false - - var load = function load () { - if (loaded || !processOk(global.process)) { - return - } - loaded = true - - // This is the number of onSignalExit's that are in play. - // It's important so that we can count the correct number of - // listeners on signals, and don't wait for the other one to - // handle it instead of us. - emitter.count += 1 - - signals = signals.filter(function (sig) { - try { - process.on(sig, sigListeners[sig]) - return true - } catch (er) { - return false - } - }) - - process.emit = processEmit - process.reallyExit = processReallyExit - } - module.exports.load = load - - var originalProcessReallyExit = process.reallyExit - var processReallyExit = function processReallyExit (code) { - /* istanbul ignore if */ - if (!processOk(global.process)) { - return - } - process.exitCode = code || /* istanbul ignore next */ 0 - emit('exit', process.exitCode, null) - /* istanbul ignore next */ - emit('afterexit', process.exitCode, null) - /* istanbul ignore next */ - originalProcessReallyExit.call(process, process.exitCode) - } - - var originalProcessEmit = process.emit - var processEmit = function processEmit (ev, arg) { - if (ev === 'exit' && processOk(global.process)) { - /* istanbul ignore else */ - if (arg !== undefined) { - process.exitCode = arg - } - var ret = originalProcessEmit.apply(this, arguments) - /* istanbul ignore next */ - emit('exit', process.exitCode, null) - /* istanbul ignore next */ - emit('afterexit', process.exitCode, null) - /* istanbul ignore next */ - return ret - } else { - return originalProcessEmit.apply(this, arguments) - } - } -} - - -/***/ }), - -/***/ "../../node_modules/signal-exit/signals.js": -/***/ (function(module, exports) { - -// This is not the set of all possible signals. -// -// It IS, however, the set of all signals that trigger -// an exit on either Linux or BSD systems. Linux is a -// superset of the signal names supported on BSD, and -// the unknown signals just fail to register, so we can -// catch that easily enough. -// -// Don't bother with SIGKILL. It's uncatchable, which -// means that we can't fire any callbacks anyway. -// -// If a user does happen to register a handler on a non- -// fatal signal like SIGWINCH or something, and then -// exit, it'll end up firing `process.emit('exit')`, so -// the handler will be fired anyway. -// -// SIGBUS, SIGFPE, SIGSEGV and SIGILL, when not raised -// artificially, inherently leave the process in a -// state from which it is not safe to try and enter JS -// listeners. -module.exports = [ - 'SIGABRT', - 'SIGALRM', - 'SIGHUP', - 'SIGINT', - 'SIGTERM' -] - -if (process.platform !== 'win32') { - module.exports.push( - 'SIGVTALRM', - 'SIGXCPU', - 'SIGXFSZ', - 'SIGUSR2', - 'SIGTRAP', - 'SIGSYS', - 'SIGQUIT', - 'SIGIOT' - // should detect profiler and enable/disable accordingly. - // see #21 - // 'SIGPROF' - ) -} - -if (process.platform === 'linux') { - module.exports.push( - 'SIGIO', - 'SIGPOLL', - 'SIGPWR', - 'SIGSTKFLT', - 'SIGUNUSED' - ) -} - - -/***/ }), - -/***/ "../../node_modules/slash/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = path => { - const isExtendedLengthPath = /^\\\\\?\\/.test(path); - const hasNonAscii = /[^\u0000-\u0080]+/.test(path); // eslint-disable-line no-control-regex - - if (isExtendedLengthPath || hasNonAscii) { - return path; - } - - return path.replace(/\\/g, '/'); -}; - - -/***/ }), - -/***/ "../../node_modules/sort-keys/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const isPlainObj = __webpack_require__("../../node_modules/sort-keys/node_modules/is-plain-obj/index.js"); - -module.exports = (obj, opts) => { - if (!isPlainObj(obj)) { - throw new TypeError('Expected a plain object'); - } - - opts = opts || {}; - - // DEPRECATED - if (typeof opts === 'function') { - throw new TypeError('Specify the compare function as an option instead'); - } - - const deep = opts.deep; - const seenInput = []; - const seenOutput = []; - - const sortKeys = x => { - const seenIndex = seenInput.indexOf(x); - - if (seenIndex !== -1) { - return seenOutput[seenIndex]; - } - - const ret = {}; - const keys = Object.keys(x).sort(opts.compare); - - seenInput.push(x); - seenOutput.push(ret); - - for (let i = 0; i < keys.length; i++) { - const key = keys[i]; - const val = x[key]; - - if (deep && Array.isArray(val)) { - const retArr = []; - - for (let j = 0; j < val.length; j++) { - retArr[j] = isPlainObj(val[j]) ? sortKeys(val[j]) : val[j]; - } - - ret[key] = retArr; - continue; - } - - ret[key] = deep && isPlainObj(val) ? sortKeys(val) : val; - } - - return ret; - }; - - return sortKeys(obj); -}; - - -/***/ }), - -/***/ "../../node_modules/sort-keys/node_modules/is-plain-obj/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -var toString = Object.prototype.toString; - -module.exports = function (x) { - var prototype; - return toString.call(x) === '[object Object]' && (prototype = Object.getPrototypeOf(x), prototype === null || prototype === Object.getPrototypeOf({})); -}; - - -/***/ }), - -/***/ "../../node_modules/sort-object-keys/index.js": -/***/ (function(module, exports) { - -module.exports = function sortObjectByKeyNameList(object, sortWith) { - var keys; - var sortFn; - - if (typeof sortWith === 'function') { - sortFn = sortWith; - } else { - keys = sortWith; - } - - var objectKeys = Object.keys(object); - return (keys || []).concat(objectKeys.sort(sortFn)).reduce(function(total, key) { - if (objectKeys.indexOf(key) !== -1) { - total[key] = object[key]; - } - return total; - }, Object.create(null)); -} - - -/***/ }), - -/***/ "../../node_modules/sort-package-json/index.js": -/***/ (function(module, exports, __webpack_require__) { - -const sortObjectKeys = __webpack_require__("../../node_modules/sort-object-keys/index.js") -const detectIndent = __webpack_require__("../../node_modules/detect-indent/index.js") -const detectNewline = __webpack_require__("../../node_modules/detect-newline/index.js").graceful -const gitHooks = __webpack_require__("../../node_modules/git-hooks-list/index.json") -const isPlainObject = __webpack_require__("../../node_modules/is-plain-obj/index.js") - -const hasOwnProperty = (object, property) => - Object.prototype.hasOwnProperty.call(object, property) -const pipe = (fns) => (x, ...args) => - fns.reduce((result, fn) => fn(result, ...args), x) -const onArray = (fn) => (x) => (Array.isArray(x) ? fn(x) : x) -const onStringArray = (fn) => (x) => - Array.isArray(x) && x.every((item) => typeof item === 'string') ? fn(x) : x -const uniq = onStringArray((xs) => xs.filter((x, i) => i === xs.indexOf(x))) -const sortArray = onStringArray((array) => [...array].sort()) -const uniqAndSortArray = pipe([uniq, sortArray]) -const onObject = (fn) => (x, ...args) => (isPlainObject(x) ? fn(x, ...args) : x) -const sortObjectBy = (comparator, deep) => { - const over = onObject((object) => { - object = sortObjectKeys(object, comparator) - if (deep) { - for (const [key, value] of Object.entries(object)) { - object[key] = over(value) - } - } - return object - }) - - return over -} -const sortObject = sortObjectBy() -const sortURLObject = sortObjectBy(['type', 'url']) -const sortPeopleObject = sortObjectBy(['name', 'email', 'url']) -const sortDirectories = sortObjectBy([ - 'lib', - 'bin', - 'man', - 'doc', - 'example', - 'test', -]) -const overProperty = (property, over) => (object, ...args) => - hasOwnProperty(object, property) - ? Object.assign(object, { [property]: over(object[property], ...args) }) - : object -const sortGitHooks = sortObjectBy(gitHooks) - -// https://github.com/eslint/eslint/blob/acc0e47572a9390292b4e313b4a4bf360d236358/conf/config-schema.js -const eslintBaseConfigProperties = [ - // `files` and `excludedFiles` are only on `overrides[]` - // for easier sort `overrides[]`, - // add them to here, so we don't need sort `overrides[]` twice - 'files', - 'excludedFiles', - // baseConfig - 'env', - 'parser', - 'parserOptions', - 'settings', - 'plugins', - 'extends', - 'rules', - 'overrides', - 'globals', - 'processor', - 'noInlineConfig', - 'reportUnusedDisableDirectives', -] -const sortEslintConfig = onObject( - pipe([ - sortObjectBy(eslintBaseConfigProperties), - overProperty('env', sortObject), - overProperty('globals', sortObject), - overProperty( - 'overrides', - onArray((overrides) => overrides.map(sortEslintConfig)), - ), - overProperty('parserOptions', sortObject), - overProperty( - 'rules', - sortObjectBy( - (rule1, rule2) => - rule1.split('/').length - rule2.split('/').length || - rule1.localeCompare(rule2), - ), - ), - overProperty('settings', sortObject), - ]), -) -const sortVSCodeBadgeObject = sortObjectBy(['description', 'url', 'href']) - -const sortPrettierConfig = onObject( - pipe([ - // sort keys alphabetically, but put `overrides` at bottom - (config) => - sortObjectKeys(config, [ - ...Object.keys(config) - .filter((key) => key !== 'overrides') - .sort(), - 'overrides', - ]), - // if `config.overrides` exists - overProperty( - 'overrides', - // and `config.overrides` is an array - onArray((overrides) => - overrides.map( - pipe([ - // sort `config.overrides[]` alphabetically - sortObject, - // sort `config.overrides[].options` alphabetically - overProperty('options', sortObject), - ]), - ), - ), - ), - ]), -) - -// See https://docs.npmjs.com/misc/scripts -const defaultNpmScripts = new Set([ - 'install', - 'pack', - 'prepare', - 'publish', - 'restart', - 'shrinkwrap', - 'start', - 'stop', - 'test', - 'uninstall', - 'version', -]) - -const hasDevDependency = (dependency, packageJson) => { - return ( - 'devDependencies' in packageJson && - !!packageJson.devDependencies[dependency] - ) -} - -const sortScripts = onObject((scripts, packageJson) => { - const names = Object.keys(scripts) - const prefixable = new Set() - - const keys = names.map((name) => { - const omitted = name.replace(/^(?:pre|post)/, '') - if (defaultNpmScripts.has(omitted) || names.includes(omitted)) { - prefixable.add(omitted) - return omitted - } - return name - }) - - if (!hasDevDependency('npm-run-all', packageJson)) { - keys.sort() - } - - const order = keys.reduce( - (order, key) => - order.concat( - prefixable.has(key) ? [`pre${key}`, key, `post${key}`] : [key], - ), - [], - ) - - return sortObjectKeys(scripts, order) -}) - -// fields marked `vscode` are for `Visual Studio Code extension manifest` only -// https://code.visualstudio.com/api/references/extension-manifest -// Supported fields: -// publisher, displayName, categories, galleryBanner, preview, contributes, -// activationEvents, badges, markdown, qna, extensionPack, -// extensionDependencies, icon - -// field.key{string}: field name -// field.over{function}: sort field subKey -const fields = [ - { key: '$schema' }, - { key: 'name' }, - /* vscode */ { key: 'displayName' }, - { key: 'version' }, - { key: 'private' }, - { key: 'description' }, - /* vscode */ { key: 'categories', over: uniq }, - { key: 'keywords', over: uniq }, - { key: 'homepage' }, - { key: 'bugs', over: sortObjectBy(['url', 'email']) }, - { key: 'repository', over: sortURLObject }, - { key: 'funding', over: sortURLObject }, - { key: 'license', over: sortURLObject }, - /* vscode */ { key: 'qna' }, - { key: 'author', over: sortPeopleObject }, - { - key: 'maintainers', - over: onArray((maintainers) => maintainers.map(sortPeopleObject)), - }, - { - key: 'contributors', - over: onArray((contributors) => contributors.map(sortPeopleObject)), - }, - /* vscode */ { key: 'publisher' }, - { key: 'sideEffects' }, - { key: 'type' }, - { key: 'imports' }, - { key: 'exports' }, - { key: 'main' }, - { key: 'umd:main' }, - { key: 'jsdelivr' }, - { key: 'unpkg' }, - { key: 'module' }, - { key: 'source' }, - { key: 'jsnext:main' }, - { key: 'browser' }, - { key: 'types' }, - { key: 'typesVersions' }, - { key: 'typings' }, - { key: 'style' }, - { key: 'example' }, - { key: 'examplestyle' }, - { key: 'assets' }, - { key: 'bin', over: sortObject }, - { key: 'man' }, - { key: 'directories', over: sortDirectories }, - { key: 'files', over: uniq }, - { key: 'workspaces' }, - // node-pre-gyp https://www.npmjs.com/package/node-pre-gyp#1-add-new-entries-to-your-packagejson - { - key: 'binary', - over: sortObjectBy([ - 'module_name', - 'module_path', - 'remote_path', - 'package_name', - 'host', - ]), - }, - { key: 'scripts', over: sortScripts }, - { key: 'betterScripts', over: sortScripts }, - /* vscode */ { key: 'contributes', over: sortObject }, - /* vscode */ { key: 'activationEvents', over: uniq }, - { key: 'husky', over: overProperty('hooks', sortGitHooks) }, - { key: 'simple-git-hooks', over: sortGitHooks }, - { key: 'pre-commit' }, - { key: 'commitlint', over: sortObject }, - { key: 'lint-staged' }, - { key: 'config', over: sortObject }, - { key: 'nodemonConfig', over: sortObject }, - { key: 'browserify', over: sortObject }, - { key: 'babel', over: sortObject }, - { key: 'browserslist' }, - { key: 'xo', over: sortObject }, - { key: 'prettier', over: sortPrettierConfig }, - { key: 'eslintConfig', over: sortEslintConfig }, - { key: 'eslintIgnore' }, - { key: 'npmpkgjsonlint', over: sortObject }, - { key: 'npmPackageJsonLintConfig', over: sortObject }, - { key: 'npmpackagejsonlint', over: sortObject }, - { key: 'release', over: sortObject }, - { key: 'remarkConfig', over: sortObject }, - { key: 'stylelint' }, - { key: 'ava', over: sortObject }, - { key: 'jest', over: sortObject }, - { key: 'mocha', over: sortObject }, - { key: 'nyc', over: sortObject }, - { key: 'c8', over: sortObject }, - { key: 'tap', over: sortObject }, - { key: 'resolutions', over: sortObject }, - { key: 'dependencies', over: sortObject }, - { key: 'devDependencies', over: sortObject }, - { key: 'dependenciesMeta', over: sortObjectBy(undefined, true) }, - { key: 'peerDependencies', over: sortObject }, - // TODO: only sort depth = 2 - { key: 'peerDependenciesMeta', over: sortObjectBy(undefined, true) }, - { key: 'optionalDependencies', over: sortObject }, - { key: 'bundledDependencies', over: uniqAndSortArray }, - { key: 'bundleDependencies', over: uniqAndSortArray }, - /* vscode */ { key: 'extensionPack', over: uniqAndSortArray }, - /* vscode */ { key: 'extensionDependencies', over: uniqAndSortArray }, - { key: 'flat' }, - { key: 'engines', over: sortObject }, - { key: 'engineStrict', over: sortObject }, - { key: 'languageName' }, - { key: 'os' }, - { key: 'cpu' }, - { key: 'preferGlobal', over: sortObject }, - { key: 'publishConfig', over: sortObject }, - /* vscode */ { key: 'icon' }, - /* vscode */ { - key: 'badges', - over: onArray((badge) => badge.map(sortVSCodeBadgeObject)), - }, - /* vscode */ { key: 'galleryBanner', over: sortObject }, - /* vscode */ { key: 'preview' }, - /* vscode */ { key: 'markdown' }, -] - -const defaultSortOrder = fields.map(({ key }) => key) -const overFields = pipe( - fields.reduce((fns, { key, over }) => { - if (over) { - fns.push(overProperty(key, over)) - } - return fns - }, []), -) - -function editStringJSON(json, over) { - if (typeof json === 'string') { - const { indent } = detectIndent(json) - const endCharacters = json.slice(-1) === '\n' ? '\n' : '' - const newline = detectNewline(json) - json = JSON.parse(json) - - let result = JSON.stringify(over(json), null, indent) + endCharacters - if (newline === '\r\n') { - result = result.replace(/\n/g, newline) - } - return result - } - - return over(json) -} - -const isPrivateKey = (key) => key[0] === '_' -const partition = (array, predicate) => - array.reduce( - (result, value) => { - result[predicate(value) ? 0 : 1].push(value) - return result - }, - [[], []], - ) -function sortPackageJson(jsonIsh, options = {}) { - return editStringJSON( - jsonIsh, - onObject((json) => { - let sortOrder = options.sortOrder ? options.sortOrder : defaultSortOrder - - if (Array.isArray(sortOrder)) { - const keys = Object.keys(json) - const [privateKeys, publicKeys] = partition(keys, isPrivateKey) - sortOrder = [ - ...sortOrder, - ...defaultSortOrder, - ...publicKeys.sort(), - ...privateKeys.sort(), - ] - } - - return overFields(sortObjectKeys(json, sortOrder), json) - }), - ) -} - -module.exports = sortPackageJson -module.exports.sortPackageJson = sortPackageJson -module.exports.sortOrder = defaultSortOrder -module.exports.default = sortPackageJson - - -/***/ }), - -/***/ "../../node_modules/strip-ansi/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const ansiRegex = __webpack_require__("../../node_modules/ansi-regex/index.js"); - -module.exports = string => typeof string === 'string' ? string.replace(ansiRegex(), '') : string; - - -/***/ }), - -/***/ "../../node_modules/strip-bom/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = string => { - if (typeof string !== 'string') { - throw new TypeError(`Expected a string, got ${typeof string}`); - } - - // Catches EFBBBF (UTF-8 BOM) because the buffer-to-string - // conversion translates it to FEFF (UTF-16 BOM) - if (string.charCodeAt(0) === 0xFEFF) { - return string.slice(1); - } - - return string; -}; - - -/***/ }), - -/***/ "../../node_modules/strip-final-newline/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -module.exports = input => { - const LF = typeof input === 'string' ? '\n' : '\n'.charCodeAt(); - const CR = typeof input === 'string' ? '\r' : '\r'.charCodeAt(); - - if (input[input.length - 1] === LF) { - input = input.slice(0, input.length - 1); - } - - if (input[input.length - 1] === CR) { - input = input.slice(0, input.length - 1); - } - - return input; -}; - - -/***/ }), - -/***/ "../../node_modules/strong-log-transformer/index.js": -/***/ (function(module, exports, __webpack_require__) { - -// Copyright IBM Corp. 2014,2018. All Rights Reserved. -// Node module: strong-log-transformer -// This file is licensed under the Apache License 2.0. -// License text available at https://opensource.org/licenses/Apache-2.0 - -module.exports = __webpack_require__("../../node_modules/strong-log-transformer/lib/logger.js"); -module.exports.cli = __webpack_require__("../../node_modules/strong-log-transformer/lib/cli.js"); - - -/***/ }), - -/***/ "../../node_modules/strong-log-transformer/lib/cli.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -// Copyright IBM Corp. 2014,2018. All Rights Reserved. -// Node module: strong-log-transformer -// This file is licensed under the Apache License 2.0. -// License text available at https://opensource.org/licenses/Apache-2.0 - - - -var minimist = __webpack_require__("../../node_modules/minimist/index.js"); -var path = __webpack_require__("path"); - -var Logger = __webpack_require__("../../node_modules/strong-log-transformer/lib/logger.js"); -var pkg = __webpack_require__("../../node_modules/strong-log-transformer/package.json"); - -module.exports = cli; - -function cli(args) { - var opts = minimist(args.slice(2)); - var $0 = path.basename(args[1]); - var p = console.log.bind(console); - if (opts.v || opts.version) { - version($0, p); - } else if (opts.h || opts.help) { - usage($0, p); - } else if (args.length < 3) { - process.stdin.pipe(Logger()).pipe(process.stdout); - } else { - process.stdin.pipe(Logger(opts)).pipe(process.stdout); - } -} - -function version($0, p) { - p('%s v%s', pkg.name, pkg.version); -} - -function usage($0, p) { - var PADDING = ' '; - var opt, def; - p('Usage: %s [options]', $0); - p(''); - p('%s', pkg.description); - p(''); - p('OPTIONS:'); - for (opt in Logger.DEFAULTS) { - def = Logger.DEFAULTS[opt]; - if (typeof def === 'boolean') - boolOpt(opt, Logger.DEFAULTS[opt]); - else - stdOpt(opt, Logger.DEFAULTS[opt]); - } - p(''); - - function boolOpt(name, def) { - name = name + PADDING.slice(0, 20-name.length); - p(' --%s default: %s', name, def); - } - - function stdOpt(name, def) { - var value = name.toUpperCase() + - PADDING.slice(0, 19 - name.length*2); - p(' --%s %s default: %j', name, value, def); - } -} - - -/***/ }), - -/***/ "../../node_modules/strong-log-transformer/lib/logger.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -// Copyright IBM Corp. 2014,2018. All Rights Reserved. -// Node module: strong-log-transformer -// This file is licensed under the Apache License 2.0. -// License text available at https://opensource.org/licenses/Apache-2.0 - - - -var stream = __webpack_require__("stream"); -var util = __webpack_require__("util"); -var fs = __webpack_require__("fs"); - -var through = __webpack_require__("../../node_modules/through/index.js"); -var duplexer = __webpack_require__("../../node_modules/duplexer/index.js"); -var StringDecoder = __webpack_require__("string_decoder").StringDecoder; - -module.exports = Logger; - -Logger.DEFAULTS = { - format: 'text', - tag: '', - mergeMultiline: false, - timeStamp: false, -}; - -var formatters = { - text: textFormatter, - json: jsonFormatter, -} - -function Logger(options) { - var defaults = JSON.parse(JSON.stringify(Logger.DEFAULTS)); - options = util._extend(defaults, options || {}); - var catcher = deLiner(); - var emitter = catcher; - var transforms = [ - objectifier(), - ]; - - if (options.tag) { - transforms.push(staticTagger(options.tag)); - } - - if (options.mergeMultiline) { - transforms.push(lineMerger()); - } - - // TODO - // if (options.pidStamp) { - // transforms.push(pidStamper(options.pid)); - // } - - // TODO - // if (options.workerStamp) { - // transforms.push(workerStamper(options.worker)); - // } - - transforms.push(formatters[options.format](options)); - - // restore line endings that were removed by line splitting - transforms.push(reLiner()); - - for (var t in transforms) { - emitter = emitter.pipe(transforms[t]); - } - - return duplexer(catcher, emitter); -} - -function deLiner() { - var decoder = new StringDecoder('utf8'); - var last = ''; - - return new stream.Transform({ - transform(chunk, _enc, callback) { - last += decoder.write(chunk); - var list = last.split(/\r\n|[\n\v\f\r\x85\u2028\u2029]/g); - last = list.pop(); - for (var i = 0; i < list.length; i++) { - // swallow empty lines - if (list[i]) { - this.push(list[i]); - } - } - callback(); - }, - flush(callback) { - // incomplete UTF8 sequences become UTF8 replacement characters - last += decoder.end(); - if (last) { - this.push(last); - } - callback(); - }, - }); -} - -function reLiner() { - return through(appendNewline); - - function appendNewline(line) { - this.emit('data', line + '\n'); - } -} - -function objectifier() { - return through(objectify, null, {autoDestroy: false}); - - function objectify(line) { - this.emit('data', { - msg: line, - time: Date.now(), - }); - } -} - -function staticTagger(tag) { - return through(tagger); - - function tagger(logEvent) { - logEvent.tag = tag; - this.emit('data', logEvent); - } -} - -function textFormatter(options) { - return through(textify); - - function textify(logEvent) { - var line = util.format('%s%s', textifyTags(logEvent.tag), - logEvent.msg.toString()); - if (options.timeStamp) { - line = util.format('%s %s', new Date(logEvent.time).toISOString(), line); - } - this.emit('data', line.replace(/\n/g, '\\n')); - } - - function textifyTags(tags) { - var str = ''; - if (typeof tags === 'string') { - str = tags + ' '; - } else if (typeof tags === 'object') { - for (var t in tags) { - str += t + ':' + tags[t] + ' '; - } - } - return str; - } -} - -function jsonFormatter(options) { - return through(jsonify); - - function jsonify(logEvent) { - if (options.timeStamp) { - logEvent.time = new Date(logEvent.time).toISOString(); - } else { - delete logEvent.time; - } - logEvent.msg = logEvent.msg.toString(); - this.emit('data', JSON.stringify(logEvent)); - } -} - -function lineMerger(host) { - var previousLine = null; - var flushTimer = null; - var stream = through(lineMergerWrite, lineMergerEnd); - var flush = _flush.bind(stream); - - return stream; - - function lineMergerWrite(line) { - if (/^\s+/.test(line.msg)) { - if (previousLine) { - previousLine.msg += '\n' + line.msg; - } else { - previousLine = line; - } - } else { - flush(); - previousLine = line; - } - // rolling timeout - clearTimeout(flushTimer); - flushTimer = setTimeout(flush.bind(this), 10); - } - - function _flush() { - if (previousLine) { - this.emit('data', previousLine); - previousLine = null; - } - } - - function lineMergerEnd() { - flush.call(this); - this.emit('end'); - } -} - - -/***/ }), - -/***/ "../../node_modules/strong-log-transformer/package.json": -/***/ (function(module) { - -module.exports = JSON.parse("{\"name\":\"strong-log-transformer\",\"version\":\"2.1.0\",\"description\":\"Stream transformer that prefixes lines with timestamps and other things.\",\"author\":\"Ryan Graham \",\"license\":\"Apache-2.0\",\"repository\":{\"type\":\"git\",\"url\":\"git://github.com/strongloop/strong-log-transformer\"},\"keywords\":[\"logging\",\"streams\"],\"bugs\":{\"url\":\"https://github.com/strongloop/strong-log-transformer/issues\"},\"homepage\":\"https://github.com/strongloop/strong-log-transformer\",\"directories\":{\"test\":\"test\"},\"bin\":{\"sl-log-transformer\":\"bin/sl-log-transformer.js\"},\"main\":\"index.js\",\"scripts\":{\"test\":\"tap --100 test/test-*\"},\"dependencies\":{\"duplexer\":\"^0.1.1\",\"minimist\":\"^1.2.0\",\"through\":\"^2.3.4\"},\"devDependencies\":{\"tap\":\"^12.0.1\"},\"engines\":{\"node\":\">=4\"}}"); - -/***/ }), - -/***/ "../../node_modules/supports-color/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const os = __webpack_require__("os"); -const tty = __webpack_require__("tty"); -const hasFlag = __webpack_require__("../../node_modules/has-flag/index.js"); - -const {env} = process; - -let forceColor; -if (hasFlag('no-color') || - hasFlag('no-colors') || - hasFlag('color=false') || - hasFlag('color=never')) { - forceColor = 0; -} else if (hasFlag('color') || - hasFlag('colors') || - hasFlag('color=true') || - hasFlag('color=always')) { - forceColor = 1; -} - -if ('FORCE_COLOR' in env) { - if (env.FORCE_COLOR === 'true') { - forceColor = 1; - } else if (env.FORCE_COLOR === 'false') { - forceColor = 0; - } else { - forceColor = env.FORCE_COLOR.length === 0 ? 1 : Math.min(parseInt(env.FORCE_COLOR, 10), 3); - } -} - -function translateLevel(level) { - if (level === 0) { - return false; - } - - return { - level, - hasBasic: true, - has256: level >= 2, - has16m: level >= 3 - }; -} - -function supportsColor(haveStream, streamIsTTY) { - if (forceColor === 0) { - return 0; - } - - if (hasFlag('color=16m') || - hasFlag('color=full') || - hasFlag('color=truecolor')) { - return 3; - } - - if (hasFlag('color=256')) { - return 2; - } - - if (haveStream && !streamIsTTY && forceColor === undefined) { - return 0; - } - - const min = forceColor || 0; - - if (env.TERM === 'dumb') { - return min; - } - - if (process.platform === 'win32') { - // Windows 10 build 10586 is the first Windows release that supports 256 colors. - // Windows 10 build 14931 is the first release that supports 16m/TrueColor. - const osRelease = os.release().split('.'); - if ( - Number(osRelease[0]) >= 10 && - Number(osRelease[2]) >= 10586 - ) { - return Number(osRelease[2]) >= 14931 ? 3 : 2; - } - - return 1; - } - - if ('CI' in env) { - if (['TRAVIS', 'CIRCLECI', 'APPVEYOR', 'GITLAB_CI'].some(sign => sign in env) || env.CI_NAME === 'codeship') { - return 1; - } - - return min; - } - - if ('TEAMCITY_VERSION' in env) { - return /^(9\.(0*[1-9]\d*)\.|\d{2,}\.)/.test(env.TEAMCITY_VERSION) ? 1 : 0; - } - - if ('GITHUB_ACTIONS' in env) { - return 1; - } - - if (env.COLORTERM === 'truecolor') { - return 3; - } - - if ('TERM_PROGRAM' in env) { - const version = parseInt((env.TERM_PROGRAM_VERSION || '').split('.')[0], 10); - - switch (env.TERM_PROGRAM) { - case 'iTerm.app': - return version >= 3 ? 3 : 2; - case 'Apple_Terminal': - return 2; - // No default - } - } - - if (/-256(color)?$/i.test(env.TERM)) { - return 2; - } - - if (/^screen|^xterm|^vt100|^vt220|^rxvt|color|ansi|cygwin|linux/i.test(env.TERM)) { - return 1; - } - - if ('COLORTERM' in env) { - return 1; - } - - return min; -} - -function getSupportLevel(stream) { - const level = supportsColor(stream, stream && stream.isTTY); - return translateLevel(level); -} - -module.exports = { - supportsColor: getSupportLevel, - stdout: translateLevel(supportsColor(true, tty.isatty(1))), - stderr: translateLevel(supportsColor(true, tty.isatty(2))) -}; - - -/***/ }), - -/***/ "../../node_modules/through/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var Stream = __webpack_require__("stream") - -// through -// -// a stream that does nothing but re-emit the input. -// useful for aggregating a series of changing but not ending streams into one stream) - -exports = module.exports = through -through.through = through - -//create a readable writable stream. - -function through (write, end, opts) { - write = write || function (data) { this.queue(data) } - end = end || function () { this.queue(null) } - - var ended = false, destroyed = false, buffer = [], _ended = false - var stream = new Stream() - stream.readable = stream.writable = true - stream.paused = false - -// stream.autoPause = !(opts && opts.autoPause === false) - stream.autoDestroy = !(opts && opts.autoDestroy === false) - - stream.write = function (data) { - write.call(this, data) - return !stream.paused - } - - function drain() { - while(buffer.length && !stream.paused) { - var data = buffer.shift() - if(null === data) - return stream.emit('end') - else - stream.emit('data', data) - } - } - - stream.queue = stream.push = function (data) { -// console.error(ended) - if(_ended) return stream - if(data === null) _ended = true - buffer.push(data) - drain() - return stream - } - - //this will be registered as the first 'end' listener - //must call destroy next tick, to make sure we're after any - //stream piped from here. - //this is only a problem if end is not emitted synchronously. - //a nicer way to do this is to make sure this is the last listener for 'end' - - stream.on('end', function () { - stream.readable = false - if(!stream.writable && stream.autoDestroy) - process.nextTick(function () { - stream.destroy() - }) - }) - - function _end () { - stream.writable = false - end.call(stream) - if(!stream.readable && stream.autoDestroy) - stream.destroy() - } - - stream.end = function (data) { - if(ended) return - ended = true - if(arguments.length) stream.write(data) - _end() // will emit or queue - return stream - } - - stream.destroy = function () { - if(destroyed) return - destroyed = true - ended = true - buffer.length = 0 - stream.writable = stream.readable = false - stream.emit('close') - return stream - } - - stream.pause = function () { - if(stream.paused) return - stream.paused = true - return stream - } - - stream.resume = function () { - if(stream.paused) { - stream.paused = false - stream.emit('resume') - } - drain() - //may have become paused again, - //as drain emits 'data'. - if(!stream.paused) - stream.emit('drain') - return stream - } - return stream -} - - - -/***/ }), - -/***/ "../../node_modules/to-regex-range/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/*! - * to-regex-range - * - * Copyright (c) 2015-present, Jon Schlinkert. - * Released under the MIT License. - */ - - - -const isNumber = __webpack_require__("../../node_modules/to-regex-range/node_modules/is-number/index.js"); - -const toRegexRange = (min, max, options) => { - if (isNumber(min) === false) { - throw new TypeError('toRegexRange: expected the first argument to be a number'); - } - - if (max === void 0 || min === max) { - return String(min); - } - - if (isNumber(max) === false) { - throw new TypeError('toRegexRange: expected the second argument to be a number.'); - } - - let opts = { relaxZeros: true, ...options }; - if (typeof opts.strictZeros === 'boolean') { - opts.relaxZeros = opts.strictZeros === false; - } - - let relax = String(opts.relaxZeros); - let shorthand = String(opts.shorthand); - let capture = String(opts.capture); - let wrap = String(opts.wrap); - let cacheKey = min + ':' + max + '=' + relax + shorthand + capture + wrap; - - if (toRegexRange.cache.hasOwnProperty(cacheKey)) { - return toRegexRange.cache[cacheKey].result; - } - - let a = Math.min(min, max); - let b = Math.max(min, max); - - if (Math.abs(a - b) === 1) { - let result = min + '|' + max; - if (opts.capture) { - return `(${result})`; - } - if (opts.wrap === false) { - return result; - } - return `(?:${result})`; - } - - let isPadded = hasPadding(min) || hasPadding(max); - let state = { min, max, a, b }; - let positives = []; - let negatives = []; - - if (isPadded) { - state.isPadded = isPadded; - state.maxLen = String(state.max).length; - } - - if (a < 0) { - let newMin = b < 0 ? Math.abs(b) : 1; - negatives = splitToPatterns(newMin, Math.abs(a), state, opts); - a = state.a = 0; - } - - if (b >= 0) { - positives = splitToPatterns(a, b, state, opts); - } - - state.negatives = negatives; - state.positives = positives; - state.result = collatePatterns(negatives, positives, opts); - - if (opts.capture === true) { - state.result = `(${state.result})`; - } else if (opts.wrap !== false && (positives.length + negatives.length) > 1) { - state.result = `(?:${state.result})`; - } - - toRegexRange.cache[cacheKey] = state; - return state.result; -}; - -function collatePatterns(neg, pos, options) { - let onlyNegative = filterPatterns(neg, pos, '-', false, options) || []; - let onlyPositive = filterPatterns(pos, neg, '', false, options) || []; - let intersected = filterPatterns(neg, pos, '-?', true, options) || []; - let subpatterns = onlyNegative.concat(intersected).concat(onlyPositive); - return subpatterns.join('|'); -} - -function splitToRanges(min, max) { - let nines = 1; - let zeros = 1; - - let stop = countNines(min, nines); - let stops = new Set([max]); - - while (min <= stop && stop <= max) { - stops.add(stop); - nines += 1; - stop = countNines(min, nines); - } - - stop = countZeros(max + 1, zeros) - 1; - - while (min < stop && stop <= max) { - stops.add(stop); - zeros += 1; - stop = countZeros(max + 1, zeros) - 1; - } - - stops = [...stops]; - stops.sort(compare); - return stops; -} - -/** - * Convert a range to a regex pattern - * @param {Number} `start` - * @param {Number} `stop` - * @return {String} - */ - -function rangeToPattern(start, stop, options) { - if (start === stop) { - return { pattern: start, count: [], digits: 0 }; - } - - let zipped = zip(start, stop); - let digits = zipped.length; - let pattern = ''; - let count = 0; - - for (let i = 0; i < digits; i++) { - let [startDigit, stopDigit] = zipped[i]; - - if (startDigit === stopDigit) { - pattern += startDigit; - - } else if (startDigit !== '0' || stopDigit !== '9') { - pattern += toCharacterClass(startDigit, stopDigit, options); - - } else { - count++; - } - } - - if (count) { - pattern += options.shorthand === true ? '\\d' : '[0-9]'; - } - - return { pattern, count: [count], digits }; -} - -function splitToPatterns(min, max, tok, options) { - let ranges = splitToRanges(min, max); - let tokens = []; - let start = min; - let prev; - - for (let i = 0; i < ranges.length; i++) { - let max = ranges[i]; - let obj = rangeToPattern(String(start), String(max), options); - let zeros = ''; - - if (!tok.isPadded && prev && prev.pattern === obj.pattern) { - if (prev.count.length > 1) { - prev.count.pop(); - } - - prev.count.push(obj.count[0]); - prev.string = prev.pattern + toQuantifier(prev.count); - start = max + 1; - continue; - } - - if (tok.isPadded) { - zeros = padZeros(max, tok, options); - } - - obj.string = zeros + obj.pattern + toQuantifier(obj.count); - tokens.push(obj); - start = max + 1; - prev = obj; - } - - return tokens; -} - -function filterPatterns(arr, comparison, prefix, intersection, options) { - let result = []; - - for (let ele of arr) { - let { string } = ele; - - // only push if _both_ are negative... - if (!intersection && !contains(comparison, 'string', string)) { - result.push(prefix + string); - } - - // or _both_ are positive - if (intersection && contains(comparison, 'string', string)) { - result.push(prefix + string); - } - } - return result; -} - -/** - * Zip strings - */ - -function zip(a, b) { - let arr = []; - for (let i = 0; i < a.length; i++) arr.push([a[i], b[i]]); - return arr; -} - -function compare(a, b) { - return a > b ? 1 : b > a ? -1 : 0; -} - -function contains(arr, key, val) { - return arr.some(ele => ele[key] === val); -} - -function countNines(min, len) { - return Number(String(min).slice(0, -len) + '9'.repeat(len)); -} - -function countZeros(integer, zeros) { - return integer - (integer % Math.pow(10, zeros)); -} - -function toQuantifier(digits) { - let [start = 0, stop = ''] = digits; - if (stop || start > 1) { - return `{${start + (stop ? ',' + stop : '')}}`; - } - return ''; -} - -function toCharacterClass(a, b, options) { - return `[${a}${(b - a === 1) ? '' : '-'}${b}]`; -} - -function hasPadding(str) { - return /^-?(0+)\d/.test(str); -} - -function padZeros(value, tok, options) { - if (!tok.isPadded) { - return value; - } - - let diff = Math.abs(tok.maxLen - String(value).length); - let relax = options.relaxZeros !== false; - - switch (diff) { - case 0: - return ''; - case 1: - return relax ? '0?' : '0'; - case 2: - return relax ? '0{0,2}' : '00'; - default: { - return relax ? `0{0,${diff}}` : `0{${diff}}`; - } - } -} - -/** - * Cache - */ - -toRegexRange.cache = {}; -toRegexRange.clearCache = () => (toRegexRange.cache = {}); - -/** - * Expose `toRegexRange` - */ - -module.exports = toRegexRange; - - -/***/ }), - -/***/ "../../node_modules/to-regex-range/node_modules/is-number/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; -/*! - * is-number - * - * Copyright (c) 2014-present, Jon Schlinkert. - * Released under the MIT License. - */ - - - -module.exports = function(num) { - if (typeof num === 'number') { - return num - num === 0; - } - if (typeof num === 'string' && num.trim() !== '') { - return Number.isFinite ? Number.isFinite(+num) : isFinite(+num); - } - return false; -}; - - -/***/ }), - -/***/ "../../node_modules/validate-npm-package-license/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var parse = __webpack_require__("../../node_modules/validate-npm-package-license/node_modules/spdx-expression-parse/index.js"); -var correct = __webpack_require__("../../node_modules/validate-npm-package-license/node_modules/spdx-correct/index.js"); - -var genericWarning = ( - 'license should be ' + - 'a valid SPDX license expression (without "LicenseRef"), ' + - '"UNLICENSED", or ' + - '"SEE LICENSE IN "' -); - -var fileReferenceRE = /^SEE LICEN[CS]E IN (.+)$/; - -function startsWith(prefix, string) { - return string.slice(0, prefix.length) === prefix; -} - -function usesLicenseRef(ast) { - if (ast.hasOwnProperty('license')) { - var license = ast.license; - return ( - startsWith('LicenseRef', license) || - startsWith('DocumentRef', license) - ); - } else { - return ( - usesLicenseRef(ast.left) || - usesLicenseRef(ast.right) - ); - } -} - -module.exports = function(argument) { - var ast; - - try { - ast = parse(argument); - } catch (e) { - var match - if ( - argument === 'UNLICENSED' || - argument === 'UNLICENCED' - ) { - return { - validForOldPackages: true, - validForNewPackages: true, - unlicensed: true - }; - } else if (match = fileReferenceRE.exec(argument)) { - return { - validForOldPackages: true, - validForNewPackages: true, - inFile: match[1] - }; - } else { - var result = { - validForOldPackages: false, - validForNewPackages: false, - warnings: [genericWarning] - }; - var corrected = correct(argument); - if (corrected) { - result.warnings.push( - 'license is similar to the valid expression "' + corrected + '"' - ); - } - return result; - } - } - - if (usesLicenseRef(ast)) { - return { - validForNewPackages: false, - validForOldPackages: false, - spdx: true, - warnings: [genericWarning] - }; - } else { - return { - validForNewPackages: true, - validForOldPackages: true, - spdx: true - }; - } -}; - - -/***/ }), - -/***/ "../../node_modules/validate-npm-package-license/node_modules/spdx-correct/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var licenseIDs = __webpack_require__("../../node_modules/validate-npm-package-license/node_modules/spdx-license-ids/spdx-license-ids.json"); - -function valid(string) { - return licenseIDs.indexOf(string) > -1; -} - -// Common transpositions of license identifier acronyms -var transpositions = [ - ['APGL', 'AGPL'], - ['Gpl', 'GPL'], - ['GLP', 'GPL'], - ['APL', 'Apache'], - ['ISD', 'ISC'], - ['GLP', 'GPL'], - ['IST', 'ISC'], - ['Claude', 'Clause'], - [' or later', '+'], - [' International', ''], - ['GNU', 'GPL'], - ['GUN', 'GPL'], - ['+', ''], - ['GNU GPL', 'GPL'], - ['GNU/GPL', 'GPL'], - ['GNU GLP', 'GPL'], - ['GNU General Public License', 'GPL'], - ['Gnu public license', 'GPL'], - ['GNU Public License', 'GPL'], - ['GNU GENERAL PUBLIC LICENSE', 'GPL'], - ['MTI', 'MIT'], - ['Mozilla Public License', 'MPL'], - ['WTH', 'WTF'], - ['-License', ''] -]; - -var TRANSPOSED = 0; -var CORRECT = 1; - -// Simple corrections to nearly valid identifiers. -var transforms = [ - // e.g. 'mit' - function(argument) { - return argument.toUpperCase(); - }, - // e.g. 'MIT ' - function(argument) { - return argument.trim(); - }, - // e.g. 'M.I.T.' - function(argument) { - return argument.replace(/\./g, ''); - }, - // e.g. 'Apache- 2.0' - function(argument) { - return argument.replace(/\s+/g, ''); - }, - // e.g. 'CC BY 4.0'' - function(argument) { - return argument.replace(/\s+/g, '-'); - }, - // e.g. 'LGPLv2.1' - function(argument) { - return argument.replace('v', '-'); - }, - // e.g. 'Apache 2.0' - function(argument) { - return argument.replace(/,?\s*(\d)/, '-$1'); - }, - // e.g. 'GPL 2' - function(argument) { - return argument.replace(/,?\s*(\d)/, '-$1.0'); - }, - // e.g. 'Apache Version 2.0' - function(argument) { - return argument.replace(/,?\s*(V\.|v\.|V|v|Version|version)\s*(\d)/, '-$2'); - }, - // e.g. 'Apache Version 2' - function(argument) { - return argument.replace(/,?\s*(V\.|v\.|V|v|Version|version)\s*(\d)/, '-$2.0'); - }, - // e.g. 'ZLIB' - function(argument) { - return argument[0].toUpperCase() + argument.slice(1); - }, - // e.g. 'MPL/2.0' - function(argument) { - return argument.replace('/', '-'); - }, - // e.g. 'Apache 2' - function(argument) { - return argument - .replace(/\s*V\s*(\d)/, '-$1') - .replace(/(\d)$/, '$1.0'); - }, - // e.g. 'GPL-2.0-' - function(argument) { - return argument.slice(0, argument.length - 1); - }, - // e.g. 'GPL2' - function(argument) { - return argument.replace(/(\d)$/, '-$1.0'); - }, - // e.g. 'BSD 3' - function(argument) { - return argument.replace(/(-| )?(\d)$/, '-$2-Clause'); - }, - // e.g. 'BSD clause 3' - function(argument) { - return argument.replace(/(-| )clause(-| )(\d)/, '-$3-Clause'); - }, - // e.g. 'BY-NC-4.0' - function(argument) { - return 'CC-' + argument; - }, - // e.g. 'BY-NC' - function(argument) { - return 'CC-' + argument + '-4.0'; - }, - // e.g. 'Attribution-NonCommercial' - function(argument) { - return argument - .replace('Attribution', 'BY') - .replace('NonCommercial', 'NC') - .replace('NoDerivatives', 'ND') - .replace(/ (\d)/, '-$1') - .replace(/ ?International/, ''); - }, - // e.g. 'Attribution-NonCommercial' - function(argument) { - return 'CC-' + - argument - .replace('Attribution', 'BY') - .replace('NonCommercial', 'NC') - .replace('NoDerivatives', 'ND') - .replace(/ (\d)/, '-$1') - .replace(/ ?International/, '') + - '-4.0'; - } -]; - -// If all else fails, guess that strings containing certain substrings -// meant to identify certain licenses. -var lastResorts = [ - ['UNLI', 'Unlicense'], - ['WTF', 'WTFPL'], - ['2 CLAUSE', 'BSD-2-Clause'], - ['2-CLAUSE', 'BSD-2-Clause'], - ['3 CLAUSE', 'BSD-3-Clause'], - ['3-CLAUSE', 'BSD-3-Clause'], - ['AFFERO', 'AGPL-3.0'], - ['AGPL', 'AGPL-3.0'], - ['APACHE', 'Apache-2.0'], - ['ARTISTIC', 'Artistic-2.0'], - ['Affero', 'AGPL-3.0'], - ['BEER', 'Beerware'], - ['BOOST', 'BSL-1.0'], - ['BSD', 'BSD-2-Clause'], - ['ECLIPSE', 'EPL-1.0'], - ['FUCK', 'WTFPL'], - ['GNU', 'GPL-3.0'], - ['LGPL', 'LGPL-3.0'], - ['GPL', 'GPL-3.0'], - ['MIT', 'MIT'], - ['MPL', 'MPL-2.0'], - ['X11', 'X11'], - ['ZLIB', 'Zlib'] -]; - -var SUBSTRING = 0; -var IDENTIFIER = 1; - -var validTransformation = function(identifier) { - for (var i = 0; i < transforms.length; i++) { - var transformed = transforms[i](identifier); - if (transformed !== identifier && valid(transformed)) { - return transformed; - } - } - return null; -}; - -var validLastResort = function(identifier) { - var upperCased = identifier.toUpperCase(); - for (var i = 0; i < lastResorts.length; i++) { - var lastResort = lastResorts[i]; - if (upperCased.indexOf(lastResort[SUBSTRING]) > -1) { - return lastResort[IDENTIFIER]; - } - } - return null; -}; - -var anyCorrection = function(identifier, check) { - for (var i = 0; i < transpositions.length; i++) { - var transposition = transpositions[i]; - var transposed = transposition[TRANSPOSED]; - if (identifier.indexOf(transposed) > -1) { - var corrected = identifier.replace( - transposed, - transposition[CORRECT] - ); - var checked = check(corrected); - if (checked !== null) { - return checked; - } - } - } - return null; -}; - -module.exports = function(identifier) { - identifier = identifier.replace(/\+$/, ''); - if (valid(identifier)) { - return identifier; - } - var transformed = validTransformation(identifier); - if (transformed !== null) { - return transformed; - } - transformed = anyCorrection(identifier, function(argument) { - if (valid(argument)) { - return argument; - } - return validTransformation(argument); - }); - if (transformed !== null) { - return transformed; - } - transformed = validLastResort(identifier); - if (transformed !== null) { - return transformed; - } - transformed = anyCorrection(identifier, validLastResort); - if (transformed !== null) { - return transformed; - } - return null; -}; - - -/***/ }), - -/***/ "../../node_modules/validate-npm-package-license/node_modules/spdx-expression-parse/index.js": -/***/ (function(module, exports, __webpack_require__) { - -var parser = __webpack_require__("../../node_modules/validate-npm-package-license/node_modules/spdx-expression-parse/parser.js").parser - -module.exports = function (argument) { - return parser.parse(argument) -} - - -/***/ }), - -/***/ "../../node_modules/validate-npm-package-license/node_modules/spdx-expression-parse/parser.js": -/***/ (function(module, exports, __webpack_require__) { - -/* WEBPACK VAR INJECTION */(function(module) {/* parser generated by jison 0.4.17 */ -/* - Returns a Parser object of the following structure: - - Parser: { - yy: {} - } - - Parser.prototype: { - yy: {}, - trace: function(), - symbols_: {associative list: name ==> number}, - terminals_: {associative list: number ==> name}, - productions_: [...], - performAction: function anonymous(yytext, yyleng, yylineno, yy, yystate, $$, _$), - table: [...], - defaultActions: {...}, - parseError: function(str, hash), - parse: function(input), - - lexer: { - EOF: 1, - parseError: function(str, hash), - setInput: function(input), - input: function(), - unput: function(str), - more: function(), - less: function(n), - pastInput: function(), - upcomingInput: function(), - showPosition: function(), - test_match: function(regex_match_array, rule_index), - next: function(), - lex: function(), - begin: function(condition), - popState: function(), - _currentRules: function(), - topState: function(), - pushState: function(condition), - - options: { - ranges: boolean (optional: true ==> token location info will include a .range[] member) - flex: boolean (optional: true ==> flex-like lexing behaviour where the rules are tested exhaustively to find the longest match) - backtrack_lexer: boolean (optional: true ==> lexer regexes are tested in order and for each matching regex the action code is invoked; the lexer terminates the scan when a token is returned by the action code) - }, - - performAction: function(yy, yy_, $avoiding_name_collisions, YY_START), - rules: [...], - conditions: {associative list: name ==> set}, - } - } - - - token location info (@$, _$, etc.): { - first_line: n, - last_line: n, - first_column: n, - last_column: n, - range: [start_number, end_number] (where the numbers are indexes into the input string, regular zero-based) - } - - - the parseError function receives a 'hash' object with these members for lexer and parser errors: { - text: (matched text) - token: (the produced terminal token, if any) - line: (yylineno) - } - while parser (grammar) errors will also provide these members, i.e. parser errors deliver a superset of attributes: { - loc: (yylloc) - expected: (string describing the set of expected tokens) - recoverable: (boolean: TRUE when the parser has a error recovery rule available for this particular error) - } -*/ -var spdxparse = (function(){ -var o=function(k,v,o,l){for(o=o||{},l=k.length;l--;o[k[l]]=v);return o},$V0=[1,5],$V1=[1,6],$V2=[1,7],$V3=[1,4],$V4=[1,9],$V5=[1,10],$V6=[5,14,15,17],$V7=[5,12,14,15,17]; -var parser = {trace: function trace() { }, -yy: {}, -symbols_: {"error":2,"start":3,"expression":4,"EOS":5,"simpleExpression":6,"LICENSE":7,"PLUS":8,"LICENSEREF":9,"DOCUMENTREF":10,"COLON":11,"WITH":12,"EXCEPTION":13,"AND":14,"OR":15,"OPEN":16,"CLOSE":17,"$accept":0,"$end":1}, -terminals_: {2:"error",5:"EOS",7:"LICENSE",8:"PLUS",9:"LICENSEREF",10:"DOCUMENTREF",11:"COLON",12:"WITH",13:"EXCEPTION",14:"AND",15:"OR",16:"OPEN",17:"CLOSE"}, -productions_: [0,[3,2],[6,1],[6,2],[6,1],[6,3],[4,1],[4,3],[4,3],[4,3],[4,3]], -performAction: function anonymous(yytext, yyleng, yylineno, yy, yystate /* action[1] */, $$ /* vstack */, _$ /* lstack */) { -/* this == yyval */ - -var $0 = $$.length - 1; -switch (yystate) { -case 1: -return this.$ = $$[$0-1] -break; -case 2: case 4: case 5: -this.$ = {license: yytext} -break; -case 3: -this.$ = {license: $$[$0-1], plus: true} -break; -case 6: -this.$ = $$[$0] -break; -case 7: -this.$ = {exception: $$[$0]} -this.$.license = $$[$0-2].license -if ($$[$0-2].hasOwnProperty('plus')) { - this.$.plus = $$[$0-2].plus -} -break; -case 8: -this.$ = {conjunction: 'and', left: $$[$0-2], right: $$[$0]} -break; -case 9: -this.$ = {conjunction: 'or', left: $$[$0-2], right: $$[$0]} -break; -case 10: -this.$ = $$[$0-1] -break; -} -}, -table: [{3:1,4:2,6:3,7:$V0,9:$V1,10:$V2,16:$V3},{1:[3]},{5:[1,8],14:$V4,15:$V5},o($V6,[2,6],{12:[1,11]}),{4:12,6:3,7:$V0,9:$V1,10:$V2,16:$V3},o($V7,[2,2],{8:[1,13]}),o($V7,[2,4]),{11:[1,14]},{1:[2,1]},{4:15,6:3,7:$V0,9:$V1,10:$V2,16:$V3},{4:16,6:3,7:$V0,9:$V1,10:$V2,16:$V3},{13:[1,17]},{14:$V4,15:$V5,17:[1,18]},o($V7,[2,3]),{9:[1,19]},o($V6,[2,8]),o([5,15,17],[2,9],{14:$V4}),o($V6,[2,7]),o($V6,[2,10]),o($V7,[2,5])], -defaultActions: {8:[2,1]}, -parseError: function parseError(str, hash) { - if (hash.recoverable) { - this.trace(str); - } else { - function _parseError (msg, hash) { - this.message = msg; - this.hash = hash; - } - _parseError.prototype = Error; - - throw new _parseError(str, hash); - } -}, -parse: function parse(input) { - var self = this, stack = [0], tstack = [], vstack = [null], lstack = [], table = this.table, yytext = '', yylineno = 0, yyleng = 0, recovering = 0, TERROR = 2, EOF = 1; - var args = lstack.slice.call(arguments, 1); - var lexer = Object.create(this.lexer); - var sharedState = { yy: {} }; - for (var k in this.yy) { - if (Object.prototype.hasOwnProperty.call(this.yy, k)) { - sharedState.yy[k] = this.yy[k]; - } - } - lexer.setInput(input, sharedState.yy); - sharedState.yy.lexer = lexer; - sharedState.yy.parser = this; - if (typeof lexer.yylloc == 'undefined') { - lexer.yylloc = {}; - } - var yyloc = lexer.yylloc; - lstack.push(yyloc); - var ranges = lexer.options && lexer.options.ranges; - if (typeof sharedState.yy.parseError === 'function') { - this.parseError = sharedState.yy.parseError; - } else { - this.parseError = Object.getPrototypeOf(this).parseError; - } - function popStack(n) { - stack.length = stack.length - 2 * n; - vstack.length = vstack.length - n; - lstack.length = lstack.length - n; - } - _token_stack: - var lex = function () { - var token; - token = lexer.lex() || EOF; - if (typeof token !== 'number') { - token = self.symbols_[token] || token; - } - return token; - }; - var symbol, preErrorSymbol, state, action, a, r, yyval = {}, p, len, newState, expected; - while (true) { - state = stack[stack.length - 1]; - if (this.defaultActions[state]) { - action = this.defaultActions[state]; - } else { - if (symbol === null || typeof symbol == 'undefined') { - symbol = lex(); - } - action = table[state] && table[state][symbol]; - } - if (typeof action === 'undefined' || !action.length || !action[0]) { - var errStr = ''; - expected = []; - for (p in table[state]) { - if (this.terminals_[p] && p > TERROR) { - expected.push('\'' + this.terminals_[p] + '\''); - } - } - if (lexer.showPosition) { - errStr = 'Parse error on line ' + (yylineno + 1) + ':\n' + lexer.showPosition() + '\nExpecting ' + expected.join(', ') + ', got \'' + (this.terminals_[symbol] || symbol) + '\''; - } else { - errStr = 'Parse error on line ' + (yylineno + 1) + ': Unexpected ' + (symbol == EOF ? 'end of input' : '\'' + (this.terminals_[symbol] || symbol) + '\''); - } - this.parseError(errStr, { - text: lexer.match, - token: this.terminals_[symbol] || symbol, - line: lexer.yylineno, - loc: yyloc, - expected: expected - }); - } - if (action[0] instanceof Array && action.length > 1) { - throw new Error('Parse Error: multiple actions possible at state: ' + state + ', token: ' + symbol); - } - switch (action[0]) { - case 1: - stack.push(symbol); - vstack.push(lexer.yytext); - lstack.push(lexer.yylloc); - stack.push(action[1]); - symbol = null; - if (!preErrorSymbol) { - yyleng = lexer.yyleng; - yytext = lexer.yytext; - yylineno = lexer.yylineno; - yyloc = lexer.yylloc; - if (recovering > 0) { - recovering--; - } - } else { - symbol = preErrorSymbol; - preErrorSymbol = null; - } - break; - case 2: - len = this.productions_[action[1]][1]; - yyval.$ = vstack[vstack.length - len]; - yyval._$ = { - first_line: lstack[lstack.length - (len || 1)].first_line, - last_line: lstack[lstack.length - 1].last_line, - first_column: lstack[lstack.length - (len || 1)].first_column, - last_column: lstack[lstack.length - 1].last_column - }; - if (ranges) { - yyval._$.range = [ - lstack[lstack.length - (len || 1)].range[0], - lstack[lstack.length - 1].range[1] - ]; - } - r = this.performAction.apply(yyval, [ - yytext, - yyleng, - yylineno, - sharedState.yy, - action[1], - vstack, - lstack - ].concat(args)); - if (typeof r !== 'undefined') { - return r; - } - if (len) { - stack = stack.slice(0, -1 * len * 2); - vstack = vstack.slice(0, -1 * len); - lstack = lstack.slice(0, -1 * len); - } - stack.push(this.productions_[action[1]][0]); - vstack.push(yyval.$); - lstack.push(yyval._$); - newState = table[stack[stack.length - 2]][stack[stack.length - 1]]; - stack.push(newState); - break; - case 3: - return true; - } - } - return true; -}}; -/* generated by jison-lex 0.3.4 */ -var lexer = (function(){ -var lexer = ({ - -EOF:1, - -parseError:function parseError(str, hash) { - if (this.yy.parser) { - this.yy.parser.parseError(str, hash); - } else { - throw new Error(str); - } - }, - -// resets the lexer, sets new input -setInput:function (input, yy) { - this.yy = yy || this.yy || {}; - this._input = input; - this._more = this._backtrack = this.done = false; - this.yylineno = this.yyleng = 0; - this.yytext = this.matched = this.match = ''; - this.conditionStack = ['INITIAL']; - this.yylloc = { - first_line: 1, - first_column: 0, - last_line: 1, - last_column: 0 - }; - if (this.options.ranges) { - this.yylloc.range = [0,0]; - } - this.offset = 0; - return this; - }, - -// consumes and returns one char from the input -input:function () { - var ch = this._input[0]; - this.yytext += ch; - this.yyleng++; - this.offset++; - this.match += ch; - this.matched += ch; - var lines = ch.match(/(?:\r\n?|\n).*/g); - if (lines) { - this.yylineno++; - this.yylloc.last_line++; - } else { - this.yylloc.last_column++; - } - if (this.options.ranges) { - this.yylloc.range[1]++; - } - - this._input = this._input.slice(1); - return ch; - }, - -// unshifts one char (or a string) into the input -unput:function (ch) { - var len = ch.length; - var lines = ch.split(/(?:\r\n?|\n)/g); - - this._input = ch + this._input; - this.yytext = this.yytext.substr(0, this.yytext.length - len); - //this.yyleng -= len; - this.offset -= len; - var oldLines = this.match.split(/(?:\r\n?|\n)/g); - this.match = this.match.substr(0, this.match.length - 1); - this.matched = this.matched.substr(0, this.matched.length - 1); - - if (lines.length - 1) { - this.yylineno -= lines.length - 1; - } - var r = this.yylloc.range; - - this.yylloc = { - first_line: this.yylloc.first_line, - last_line: this.yylineno + 1, - first_column: this.yylloc.first_column, - last_column: lines ? - (lines.length === oldLines.length ? this.yylloc.first_column : 0) - + oldLines[oldLines.length - lines.length].length - lines[0].length : - this.yylloc.first_column - len - }; - - if (this.options.ranges) { - this.yylloc.range = [r[0], r[0] + this.yyleng - len]; - } - this.yyleng = this.yytext.length; - return this; - }, - -// When called from action, caches matched text and appends it on next action -more:function () { - this._more = true; - return this; - }, - -// When called from action, signals the lexer that this rule fails to match the input, so the next matching rule (regex) should be tested instead. -reject:function () { - if (this.options.backtrack_lexer) { - this._backtrack = true; - } else { - return this.parseError('Lexical error on line ' + (this.yylineno + 1) + '. You can only invoke reject() in the lexer when the lexer is of the backtracking persuasion (options.backtrack_lexer = true).\n' + this.showPosition(), { - text: "", - token: null, - line: this.yylineno - }); - - } - return this; - }, - -// retain first n characters of the match -less:function (n) { - this.unput(this.match.slice(n)); - }, - -// displays already matched input, i.e. for error messages -pastInput:function () { - var past = this.matched.substr(0, this.matched.length - this.match.length); - return (past.length > 20 ? '...':'') + past.substr(-20).replace(/\n/g, ""); - }, - -// displays upcoming input, i.e. for error messages -upcomingInput:function () { - var next = this.match; - if (next.length < 20) { - next += this._input.substr(0, 20-next.length); - } - return (next.substr(0,20) + (next.length > 20 ? '...' : '')).replace(/\n/g, ""); - }, - -// displays the character position where the lexing error occurred, i.e. for error messages -showPosition:function () { - var pre = this.pastInput(); - var c = new Array(pre.length + 1).join("-"); - return pre + this.upcomingInput() + "\n" + c + "^"; - }, - -// test the lexed token: return FALSE when not a match, otherwise return token -test_match:function (match, indexed_rule) { - var token, - lines, - backup; - - if (this.options.backtrack_lexer) { - // save context - backup = { - yylineno: this.yylineno, - yylloc: { - first_line: this.yylloc.first_line, - last_line: this.last_line, - first_column: this.yylloc.first_column, - last_column: this.yylloc.last_column - }, - yytext: this.yytext, - match: this.match, - matches: this.matches, - matched: this.matched, - yyleng: this.yyleng, - offset: this.offset, - _more: this._more, - _input: this._input, - yy: this.yy, - conditionStack: this.conditionStack.slice(0), - done: this.done - }; - if (this.options.ranges) { - backup.yylloc.range = this.yylloc.range.slice(0); - } - } - - lines = match[0].match(/(?:\r\n?|\n).*/g); - if (lines) { - this.yylineno += lines.length; - } - this.yylloc = { - first_line: this.yylloc.last_line, - last_line: this.yylineno + 1, - first_column: this.yylloc.last_column, - last_column: lines ? - lines[lines.length - 1].length - lines[lines.length - 1].match(/\r?\n?/)[0].length : - this.yylloc.last_column + match[0].length - }; - this.yytext += match[0]; - this.match += match[0]; - this.matches = match; - this.yyleng = this.yytext.length; - if (this.options.ranges) { - this.yylloc.range = [this.offset, this.offset += this.yyleng]; - } - this._more = false; - this._backtrack = false; - this._input = this._input.slice(match[0].length); - this.matched += match[0]; - token = this.performAction.call(this, this.yy, this, indexed_rule, this.conditionStack[this.conditionStack.length - 1]); - if (this.done && this._input) { - this.done = false; - } - if (token) { - return token; - } else if (this._backtrack) { - // recover context - for (var k in backup) { - this[k] = backup[k]; - } - return false; // rule action called reject() implying the next rule should be tested instead. - } - return false; - }, - -// return next match in input -next:function () { - if (this.done) { - return this.EOF; - } - if (!this._input) { - this.done = true; - } - - var token, - match, - tempMatch, - index; - if (!this._more) { - this.yytext = ''; - this.match = ''; - } - var rules = this._currentRules(); - for (var i = 0; i < rules.length; i++) { - tempMatch = this._input.match(this.rules[rules[i]]); - if (tempMatch && (!match || tempMatch[0].length > match[0].length)) { - match = tempMatch; - index = i; - if (this.options.backtrack_lexer) { - token = this.test_match(tempMatch, rules[i]); - if (token !== false) { - return token; - } else if (this._backtrack) { - match = false; - continue; // rule action called reject() implying a rule MISmatch. - } else { - // else: this is a lexer rule which consumes input without producing a token (e.g. whitespace) - return false; - } - } else if (!this.options.flex) { - break; - } - } - } - if (match) { - token = this.test_match(match, rules[index]); - if (token !== false) { - return token; - } - // else: this is a lexer rule which consumes input without producing a token (e.g. whitespace) - return false; - } - if (this._input === "") { - return this.EOF; - } else { - return this.parseError('Lexical error on line ' + (this.yylineno + 1) + '. Unrecognized text.\n' + this.showPosition(), { - text: "", - token: null, - line: this.yylineno - }); - } - }, - -// return next match that has a token -lex:function lex() { - var r = this.next(); - if (r) { - return r; - } else { - return this.lex(); - } - }, - -// activates a new lexer condition state (pushes the new lexer condition state onto the condition stack) -begin:function begin(condition) { - this.conditionStack.push(condition); - }, - -// pop the previously active lexer condition state off the condition stack -popState:function popState() { - var n = this.conditionStack.length - 1; - if (n > 0) { - return this.conditionStack.pop(); - } else { - return this.conditionStack[0]; - } - }, - -// produce the lexer rule set which is active for the currently active lexer condition state -_currentRules:function _currentRules() { - if (this.conditionStack.length && this.conditionStack[this.conditionStack.length - 1]) { - return this.conditions[this.conditionStack[this.conditionStack.length - 1]].rules; - } else { - return this.conditions["INITIAL"].rules; - } - }, - -// return the currently active lexer condition state; when an index argument is provided it produces the N-th previous condition state, if available -topState:function topState(n) { - n = this.conditionStack.length - 1 - Math.abs(n || 0); - if (n >= 0) { - return this.conditionStack[n]; - } else { - return "INITIAL"; - } - }, - -// alias for begin(condition) -pushState:function pushState(condition) { - this.begin(condition); - }, - -// return the number of states currently on the stack -stateStackSize:function stateStackSize() { - return this.conditionStack.length; - }, -options: {}, -performAction: function anonymous(yy,yy_,$avoiding_name_collisions,YY_START) { -var YYSTATE=YY_START; -switch($avoiding_name_collisions) { -case 0:return 5 -break; -case 1:/* skip whitespace */ -break; -case 2:return 8 -break; -case 3:return 16 -break; -case 4:return 17 -break; -case 5:return 11 -break; -case 6:return 10 -break; -case 7:return 9 -break; -case 8:return 14 -break; -case 9:return 15 -break; -case 10:return 12 -break; -case 11:return 7 -break; -case 12:return 7 -break; -case 13:return 7 -break; -case 14:return 7 -break; -case 15:return 7 -break; -case 16:return 7 -break; -case 17:return 7 -break; -case 18:return 7 -break; -case 19:return 7 -break; -case 20:return 7 -break; -case 21:return 7 -break; -case 22:return 7 -break; -case 23:return 7 -break; -case 24:return 13 -break; -case 25:return 13 -break; -case 26:return 13 -break; -case 27:return 13 -break; -case 28:return 13 -break; -case 29:return 13 -break; -case 30:return 13 -break; -case 31:return 13 -break; -case 32:return 7 -break; -case 33:return 13 -break; -case 34:return 7 -break; -case 35:return 13 -break; -case 36:return 7 -break; -case 37:return 13 -break; -case 38:return 13 -break; -case 39:return 7 -break; -case 40:return 13 -break; -case 41:return 13 -break; -case 42:return 13 -break; -case 43:return 13 -break; -case 44:return 13 -break; -case 45:return 7 -break; -case 46:return 13 -break; -case 47:return 7 -break; -case 48:return 7 -break; -case 49:return 7 -break; -case 50:return 7 -break; -case 51:return 7 -break; -case 52:return 7 -break; -case 53:return 7 -break; -case 54:return 7 -break; -case 55:return 7 -break; -case 56:return 7 -break; -case 57:return 7 -break; -case 58:return 7 -break; -case 59:return 7 -break; -case 60:return 7 -break; -case 61:return 7 -break; -case 62:return 7 -break; -case 63:return 13 -break; -case 64:return 7 -break; -case 65:return 7 -break; -case 66:return 13 -break; -case 67:return 7 -break; -case 68:return 7 -break; -case 69:return 7 -break; -case 70:return 7 -break; -case 71:return 7 -break; -case 72:return 7 -break; -case 73:return 13 -break; -case 74:return 7 -break; -case 75:return 13 -break; -case 76:return 7 -break; -case 77:return 7 -break; -case 78:return 7 -break; -case 79:return 7 -break; -case 80:return 7 -break; -case 81:return 7 -break; -case 82:return 7 -break; -case 83:return 7 -break; -case 84:return 7 -break; -case 85:return 7 -break; -case 86:return 7 -break; -case 87:return 7 -break; -case 88:return 7 -break; -case 89:return 7 -break; -case 90:return 7 -break; -case 91:return 7 -break; -case 92:return 7 -break; -case 93:return 7 -break; -case 94:return 7 -break; -case 95:return 7 -break; -case 96:return 7 -break; -case 97:return 7 -break; -case 98:return 7 -break; -case 99:return 7 -break; -case 100:return 7 -break; -case 101:return 7 -break; -case 102:return 7 -break; -case 103:return 7 -break; -case 104:return 7 -break; -case 105:return 7 -break; -case 106:return 7 -break; -case 107:return 7 -break; -case 108:return 7 -break; -case 109:return 7 -break; -case 110:return 7 -break; -case 111:return 7 -break; -case 112:return 7 -break; -case 113:return 7 -break; -case 114:return 7 -break; -case 115:return 7 -break; -case 116:return 7 -break; -case 117:return 7 -break; -case 118:return 7 -break; -case 119:return 7 -break; -case 120:return 7 -break; -case 121:return 7 -break; -case 122:return 7 -break; -case 123:return 7 -break; -case 124:return 7 -break; -case 125:return 7 -break; -case 126:return 7 -break; -case 127:return 7 -break; -case 128:return 7 -break; -case 129:return 7 -break; -case 130:return 7 -break; -case 131:return 7 -break; -case 132:return 7 -break; -case 133:return 7 -break; -case 134:return 7 -break; -case 135:return 7 -break; -case 136:return 7 -break; -case 137:return 7 -break; -case 138:return 7 -break; -case 139:return 7 -break; -case 140:return 7 -break; -case 141:return 7 -break; -case 142:return 7 -break; -case 143:return 7 -break; -case 144:return 7 -break; -case 145:return 7 -break; -case 146:return 7 -break; -case 147:return 7 -break; -case 148:return 7 -break; -case 149:return 7 -break; -case 150:return 7 -break; -case 151:return 7 -break; -case 152:return 7 -break; -case 153:return 7 -break; -case 154:return 7 -break; -case 155:return 7 -break; -case 156:return 7 -break; -case 157:return 7 -break; -case 158:return 7 -break; -case 159:return 7 -break; -case 160:return 7 -break; -case 161:return 7 -break; -case 162:return 7 -break; -case 163:return 7 -break; -case 164:return 7 -break; -case 165:return 7 -break; -case 166:return 7 -break; -case 167:return 7 -break; -case 168:return 7 -break; -case 169:return 7 -break; -case 170:return 7 -break; -case 171:return 7 -break; -case 172:return 7 -break; -case 173:return 7 -break; -case 174:return 7 -break; -case 175:return 7 -break; -case 176:return 7 -break; -case 177:return 7 -break; -case 178:return 7 -break; -case 179:return 7 -break; -case 180:return 7 -break; -case 181:return 7 -break; -case 182:return 7 -break; -case 183:return 7 -break; -case 184:return 7 -break; -case 185:return 7 -break; -case 186:return 7 -break; -case 187:return 7 -break; -case 188:return 7 -break; -case 189:return 7 -break; -case 190:return 7 -break; -case 191:return 7 -break; -case 192:return 7 -break; -case 193:return 7 -break; -case 194:return 7 -break; -case 195:return 7 -break; -case 196:return 7 -break; -case 197:return 7 -break; -case 198:return 7 -break; -case 199:return 7 -break; -case 200:return 7 -break; -case 201:return 7 -break; -case 202:return 7 -break; -case 203:return 7 -break; -case 204:return 7 -break; -case 205:return 7 -break; -case 206:return 7 -break; -case 207:return 7 -break; -case 208:return 7 -break; -case 209:return 7 -break; -case 210:return 7 -break; -case 211:return 7 -break; -case 212:return 7 -break; -case 213:return 7 -break; -case 214:return 7 -break; -case 215:return 7 -break; -case 216:return 7 -break; -case 217:return 7 -break; -case 218:return 7 -break; -case 219:return 7 -break; -case 220:return 7 -break; -case 221:return 7 -break; -case 222:return 7 -break; -case 223:return 7 -break; -case 224:return 7 -break; -case 225:return 7 -break; -case 226:return 7 -break; -case 227:return 7 -break; -case 228:return 7 -break; -case 229:return 7 -break; -case 230:return 7 -break; -case 231:return 7 -break; -case 232:return 7 -break; -case 233:return 7 -break; -case 234:return 7 -break; -case 235:return 7 -break; -case 236:return 7 -break; -case 237:return 7 -break; -case 238:return 7 -break; -case 239:return 7 -break; -case 240:return 7 -break; -case 241:return 7 -break; -case 242:return 7 -break; -case 243:return 7 -break; -case 244:return 7 -break; -case 245:return 7 -break; -case 246:return 7 -break; -case 247:return 7 -break; -case 248:return 7 -break; -case 249:return 7 -break; -case 250:return 7 -break; -case 251:return 7 -break; -case 252:return 7 -break; -case 253:return 7 -break; -case 254:return 7 -break; -case 255:return 7 -break; -case 256:return 7 -break; -case 257:return 7 -break; -case 258:return 7 -break; -case 259:return 7 -break; -case 260:return 7 -break; -case 261:return 7 -break; -case 262:return 7 -break; -case 263:return 7 -break; -case 264:return 7 -break; -case 265:return 7 -break; -case 266:return 7 -break; -case 267:return 7 -break; -case 268:return 7 -break; -case 269:return 7 -break; -case 270:return 7 -break; -case 271:return 7 -break; -case 272:return 7 -break; -case 273:return 7 -break; -case 274:return 7 -break; -case 275:return 7 -break; -case 276:return 7 -break; -case 277:return 7 -break; -case 278:return 7 -break; -case 279:return 7 -break; -case 280:return 7 -break; -case 281:return 7 -break; -case 282:return 7 -break; -case 283:return 7 -break; -case 284:return 7 -break; -case 285:return 7 -break; -case 286:return 7 -break; -case 287:return 7 -break; -case 288:return 7 -break; -case 289:return 7 -break; -case 290:return 7 -break; -case 291:return 7 -break; -case 292:return 7 -break; -case 293:return 7 -break; -case 294:return 7 -break; -case 295:return 7 -break; -case 296:return 7 -break; -case 297:return 7 -break; -case 298:return 7 -break; -case 299:return 7 -break; -case 300:return 7 -break; -case 301:return 7 -break; -case 302:return 7 -break; -case 303:return 7 -break; -case 304:return 7 -break; -case 305:return 7 -break; -case 306:return 7 -break; -case 307:return 7 -break; -case 308:return 7 -break; -case 309:return 7 -break; -case 310:return 7 -break; -case 311:return 7 -break; -case 312:return 7 -break; -case 313:return 7 -break; -case 314:return 7 -break; -case 315:return 7 -break; -case 316:return 7 -break; -case 317:return 7 -break; -case 318:return 7 -break; -case 319:return 7 -break; -case 320:return 7 -break; -case 321:return 7 -break; -case 322:return 7 -break; -case 323:return 7 -break; -case 324:return 7 -break; -case 325:return 7 -break; -case 326:return 7 -break; -case 327:return 7 -break; -case 328:return 7 -break; -case 329:return 7 -break; -case 330:return 7 -break; -case 331:return 7 -break; -case 332:return 7 -break; -case 333:return 7 -break; -case 334:return 7 -break; -case 335:return 7 -break; -case 336:return 7 -break; -case 337:return 7 -break; -case 338:return 7 -break; -case 339:return 7 -break; -case 340:return 7 -break; -case 341:return 7 -break; -case 342:return 7 -break; -case 343:return 7 -break; -case 344:return 7 -break; -case 345:return 7 -break; -case 346:return 7 -break; -case 347:return 7 -break; -case 348:return 7 -break; -case 349:return 7 -break; -case 350:return 7 -break; -case 351:return 7 -break; -case 352:return 7 -break; -case 353:return 7 -break; -case 354:return 7 -break; -case 355:return 7 -break; -case 356:return 7 -break; -case 357:return 7 -break; -case 358:return 7 -break; -case 359:return 7 -break; -case 360:return 7 -break; -case 361:return 7 -break; -case 362:return 7 -break; -case 363:return 7 -break; -case 364:return 7 -break; -} -}, -rules: [/^(?:$)/,/^(?:\s+)/,/^(?:\+)/,/^(?:\()/,/^(?:\))/,/^(?::)/,/^(?:DocumentRef-([0-9A-Za-z-+.]+))/,/^(?:LicenseRef-([0-9A-Za-z-+.]+))/,/^(?:AND)/,/^(?:OR)/,/^(?:WITH)/,/^(?:BSD-3-Clause-No-Nuclear-License-2014)/,/^(?:BSD-3-Clause-No-Nuclear-Warranty)/,/^(?:GPL-2\.0-with-classpath-exception)/,/^(?:GPL-3\.0-with-autoconf-exception)/,/^(?:GPL-2\.0-with-autoconf-exception)/,/^(?:BSD-3-Clause-No-Nuclear-License)/,/^(?:MPL-2\.0-no-copyleft-exception)/,/^(?:GPL-2\.0-with-bison-exception)/,/^(?:GPL-2\.0-with-font-exception)/,/^(?:GPL-2\.0-with-GCC-exception)/,/^(?:CNRI-Python-GPL-Compatible)/,/^(?:GPL-3\.0-with-GCC-exception)/,/^(?:BSD-3-Clause-Attribution)/,/^(?:Classpath-exception-2\.0)/,/^(?:WxWindows-exception-3\.1)/,/^(?:freertos-exception-2\.0)/,/^(?:Autoconf-exception-3\.0)/,/^(?:i2p-gpl-java-exception)/,/^(?:gnu-javamail-exception)/,/^(?:Nokia-Qt-exception-1\.1)/,/^(?:Autoconf-exception-2\.0)/,/^(?:BSD-2-Clause-FreeBSD)/,/^(?:u-boot-exception-2\.0)/,/^(?:zlib-acknowledgement)/,/^(?:Bison-exception-2\.2)/,/^(?:BSD-2-Clause-NetBSD)/,/^(?:CLISP-exception-2\.0)/,/^(?:eCos-exception-2\.0)/,/^(?:BSD-3-Clause-Clear)/,/^(?:Font-exception-2\.0)/,/^(?:FLTK-exception-2\.0)/,/^(?:GCC-exception-2\.0)/,/^(?:Qwt-exception-1\.0)/,/^(?:Libtool-exception)/,/^(?:BSD-3-Clause-LBNL)/,/^(?:GCC-exception-3\.1)/,/^(?:Artistic-1\.0-Perl)/,/^(?:Artistic-1\.0-cl8)/,/^(?:CC-BY-NC-SA-2\.5)/,/^(?:MIT-advertising)/,/^(?:BSD-Source-Code)/,/^(?:CC-BY-NC-SA-4\.0)/,/^(?:LiLiQ-Rplus-1\.1)/,/^(?:CC-BY-NC-SA-3\.0)/,/^(?:BSD-4-Clause-UC)/,/^(?:CC-BY-NC-SA-2\.0)/,/^(?:CC-BY-NC-SA-1\.0)/,/^(?:CC-BY-NC-ND-4\.0)/,/^(?:CC-BY-NC-ND-3\.0)/,/^(?:CC-BY-NC-ND-2\.5)/,/^(?:CC-BY-NC-ND-2\.0)/,/^(?:CC-BY-NC-ND-1\.0)/,/^(?:LZMA-exception)/,/^(?:BitTorrent-1\.1)/,/^(?:CrystalStacker)/,/^(?:FLTK-exception)/,/^(?:SugarCRM-1\.1\.3)/,/^(?:BSD-Protection)/,/^(?:BitTorrent-1\.0)/,/^(?:HaskellReport)/,/^(?:Interbase-1\.0)/,/^(?:StandardML-NJ)/,/^(?:mif-exception)/,/^(?:Frameworx-1\.0)/,/^(?:389-exception)/,/^(?:CC-BY-NC-2\.0)/,/^(?:CC-BY-NC-2\.5)/,/^(?:CC-BY-NC-3\.0)/,/^(?:CC-BY-NC-4\.0)/,/^(?:W3C-19980720)/,/^(?:CC-BY-SA-1\.0)/,/^(?:CC-BY-SA-2\.0)/,/^(?:CC-BY-SA-2\.5)/,/^(?:CC-BY-ND-2\.0)/,/^(?:CC-BY-SA-4\.0)/,/^(?:CC-BY-SA-3\.0)/,/^(?:Artistic-1\.0)/,/^(?:Artistic-2\.0)/,/^(?:CC-BY-ND-2\.5)/,/^(?:CC-BY-ND-3\.0)/,/^(?:CC-BY-ND-4\.0)/,/^(?:CC-BY-ND-1\.0)/,/^(?:BSD-4-Clause)/,/^(?:BSD-3-Clause)/,/^(?:BSD-2-Clause)/,/^(?:CC-BY-NC-1\.0)/,/^(?:bzip2-1\.0\.6)/,/^(?:Unicode-TOU)/,/^(?:CNRI-Jython)/,/^(?:ImageMagick)/,/^(?:Adobe-Glyph)/,/^(?:CUA-OPL-1\.0)/,/^(?:OLDAP-2\.2\.2)/,/^(?:LiLiQ-R-1\.1)/,/^(?:bzip2-1\.0\.5)/,/^(?:LiLiQ-P-1\.1)/,/^(?:OLDAP-2\.0\.1)/,/^(?:OLDAP-2\.2\.1)/,/^(?:CNRI-Python)/,/^(?:XFree86-1\.1)/,/^(?:OSET-PL-2\.1)/,/^(?:Apache-2\.0)/,/^(?:Watcom-1\.0)/,/^(?:PostgreSQL)/,/^(?:Python-2\.0)/,/^(?:RHeCos-1\.1)/,/^(?:EUDatagrid)/,/^(?:Spencer-99)/,/^(?:Intel-ACPI)/,/^(?:CECILL-1\.0)/,/^(?:CECILL-1\.1)/,/^(?:JasPer-2\.0)/,/^(?:CECILL-2\.0)/,/^(?:CECILL-2\.1)/,/^(?:gSOAP-1\.3b)/,/^(?:Spencer-94)/,/^(?:Apache-1\.1)/,/^(?:Spencer-86)/,/^(?:Apache-1\.0)/,/^(?:ClArtistic)/,/^(?:TORQUE-1\.1)/,/^(?:CATOSL-1\.1)/,/^(?:Adobe-2006)/,/^(?:Zimbra-1\.4)/,/^(?:Zimbra-1\.3)/,/^(?:Condor-1\.1)/,/^(?:CC-BY-3\.0)/,/^(?:CC-BY-2\.5)/,/^(?:OLDAP-2\.4)/,/^(?:SGI-B-1\.1)/,/^(?:SISSL-1\.2)/,/^(?:SGI-B-1\.0)/,/^(?:OLDAP-2\.3)/,/^(?:CC-BY-4\.0)/,/^(?:Crossword)/,/^(?:SimPL-2\.0)/,/^(?:OLDAP-2\.2)/,/^(?:OLDAP-2\.1)/,/^(?:ErlPL-1\.1)/,/^(?:LPPL-1\.3a)/,/^(?:LPPL-1\.3c)/,/^(?:OLDAP-2\.0)/,/^(?:Leptonica)/,/^(?:CPOL-1\.02)/,/^(?:OLDAP-1\.4)/,/^(?:OLDAP-1\.3)/,/^(?:CC-BY-2\.0)/,/^(?:Unlicense)/,/^(?:OLDAP-2\.8)/,/^(?:OLDAP-1\.2)/,/^(?:MakeIndex)/,/^(?:OLDAP-2\.7)/,/^(?:OLDAP-1\.1)/,/^(?:Sleepycat)/,/^(?:D-FSL-1\.0)/,/^(?:CC-BY-1\.0)/,/^(?:OLDAP-2\.6)/,/^(?:WXwindows)/,/^(?:NPOSL-3\.0)/,/^(?:FreeImage)/,/^(?:SGI-B-2\.0)/,/^(?:OLDAP-2\.5)/,/^(?:Beerware)/,/^(?:Newsletr)/,/^(?:NBPL-1\.0)/,/^(?:NASA-1\.3)/,/^(?:NLOD-1\.0)/,/^(?:AGPL-1\.0)/,/^(?:OCLC-2\.0)/,/^(?:ODbL-1\.0)/,/^(?:PDDL-1\.0)/,/^(?:Motosoto)/,/^(?:Afmparse)/,/^(?:ANTLR-PD)/,/^(?:LPL-1\.02)/,/^(?:Abstyles)/,/^(?:eCos-2\.0)/,/^(?:APSL-1\.0)/,/^(?:LPPL-1\.2)/,/^(?:LPPL-1\.1)/,/^(?:LPPL-1\.0)/,/^(?:APSL-1\.1)/,/^(?:APSL-2\.0)/,/^(?:Info-ZIP)/,/^(?:Zend-2\.0)/,/^(?:IBM-pibs)/,/^(?:LGPL-2\.0)/,/^(?:LGPL-3\.0)/,/^(?:LGPL-2\.1)/,/^(?:GFDL-1\.3)/,/^(?:PHP-3\.01)/,/^(?:GFDL-1\.2)/,/^(?:GFDL-1\.1)/,/^(?:AGPL-3\.0)/,/^(?:Giftware)/,/^(?:EUPL-1\.1)/,/^(?:RPSL-1\.0)/,/^(?:EUPL-1\.0)/,/^(?:MIT-enna)/,/^(?:CECILL-B)/,/^(?:diffmark)/,/^(?:CECILL-C)/,/^(?:CDDL-1\.0)/,/^(?:Sendmail)/,/^(?:CDDL-1\.1)/,/^(?:CPAL-1\.0)/,/^(?:APSL-1\.2)/,/^(?:NPL-1\.1)/,/^(?:AFL-1\.2)/,/^(?:Caldera)/,/^(?:AFL-2\.0)/,/^(?:FSFULLR)/,/^(?:AFL-2\.1)/,/^(?:VSL-1\.0)/,/^(?:VOSTROM)/,/^(?:UPL-1\.0)/,/^(?:Dotseqn)/,/^(?:CPL-1\.0)/,/^(?:dvipdfm)/,/^(?:EPL-1\.0)/,/^(?:OCCT-PL)/,/^(?:ECL-1\.0)/,/^(?:Latex2e)/,/^(?:ECL-2\.0)/,/^(?:GPL-1\.0)/,/^(?:GPL-2\.0)/,/^(?:GPL-3\.0)/,/^(?:AFL-3\.0)/,/^(?:LAL-1\.2)/,/^(?:LAL-1\.3)/,/^(?:EFL-1\.0)/,/^(?:EFL-2\.0)/,/^(?:gnuplot)/,/^(?:Aladdin)/,/^(?:LPL-1\.0)/,/^(?:libtiff)/,/^(?:Entessa)/,/^(?:AMDPLPA)/,/^(?:IPL-1\.0)/,/^(?:OPL-1\.0)/,/^(?:OSL-1\.0)/,/^(?:OSL-1\.1)/,/^(?:OSL-2\.0)/,/^(?:OSL-2\.1)/,/^(?:OSL-3\.0)/,/^(?:OpenSSL)/,/^(?:ZPL-2\.1)/,/^(?:PHP-3\.0)/,/^(?:ZPL-2\.0)/,/^(?:ZPL-1\.1)/,/^(?:CC0-1\.0)/,/^(?:SPL-1\.0)/,/^(?:psutils)/,/^(?:MPL-1\.0)/,/^(?:QPL-1\.0)/,/^(?:MPL-1\.1)/,/^(?:MPL-2\.0)/,/^(?:APL-1\.0)/,/^(?:RPL-1\.1)/,/^(?:RPL-1\.5)/,/^(?:MIT-CMU)/,/^(?:Multics)/,/^(?:Eurosym)/,/^(?:BSL-1\.0)/,/^(?:MIT-feh)/,/^(?:Saxpath)/,/^(?:Borceux)/,/^(?:OFL-1\.1)/,/^(?:OFL-1\.0)/,/^(?:AFL-1\.1)/,/^(?:YPL-1\.1)/,/^(?:YPL-1\.0)/,/^(?:NPL-1\.0)/,/^(?:iMatix)/,/^(?:mpich2)/,/^(?:APAFML)/,/^(?:Bahyph)/,/^(?:RSA-MD)/,/^(?:psfrag)/,/^(?:Plexus)/,/^(?:eGenix)/,/^(?:Glulxe)/,/^(?:SAX-PD)/,/^(?:Imlib2)/,/^(?:Wsuipa)/,/^(?:LGPLLR)/,/^(?:Libpng)/,/^(?:xinetd)/,/^(?:MITNFA)/,/^(?:NetCDF)/,/^(?:Naumen)/,/^(?:SMPPL)/,/^(?:Nunit)/,/^(?:FSFUL)/,/^(?:GL2PS)/,/^(?:SMLNJ)/,/^(?:Rdisc)/,/^(?:Noweb)/,/^(?:Nokia)/,/^(?:SISSL)/,/^(?:Qhull)/,/^(?:Intel)/,/^(?:Glide)/,/^(?:Xerox)/,/^(?:AMPAS)/,/^(?:WTFPL)/,/^(?:MS-PL)/,/^(?:XSkat)/,/^(?:MS-RL)/,/^(?:MirOS)/,/^(?:RSCPL)/,/^(?:TMate)/,/^(?:OGTSL)/,/^(?:FSFAP)/,/^(?:NCSA)/,/^(?:Zlib)/,/^(?:SCEA)/,/^(?:SNIA)/,/^(?:NGPL)/,/^(?:NOSL)/,/^(?:ADSL)/,/^(?:MTLL)/,/^(?:NLPL)/,/^(?:Ruby)/,/^(?:JSON)/,/^(?:Barr)/,/^(?:0BSD)/,/^(?:Xnet)/,/^(?:Cube)/,/^(?:curl)/,/^(?:DSDP)/,/^(?:Fair)/,/^(?:HPND)/,/^(?:TOSL)/,/^(?:IJG)/,/^(?:SWL)/,/^(?:Vim)/,/^(?:FTL)/,/^(?:ICU)/,/^(?:OML)/,/^(?:NRL)/,/^(?:DOC)/,/^(?:TCL)/,/^(?:W3C)/,/^(?:NTP)/,/^(?:IPA)/,/^(?:ISC)/,/^(?:X11)/,/^(?:AAL)/,/^(?:AML)/,/^(?:xpp)/,/^(?:Zed)/,/^(?:MIT)/,/^(?:Mup)/], -conditions: {"INITIAL":{"rules":[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,165,166,167,168,169,170,171,172,173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255,256,257,258,259,260,261,262,263,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,281,282,283,284,285,286,287,288,289,290,291,292,293,294,295,296,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,317,318,319,320,321,322,323,324,325,326,327,328,329,330,331,332,333,334,335,336,337,338,339,340,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364],"inclusive":true}} -}); -return lexer; -})(); -parser.lexer = lexer; -function Parser () { - this.yy = {}; -} -Parser.prototype = parser;parser.Parser = Parser; -return new Parser; -})(); - - -if (true) { -exports.parser = spdxparse; -exports.Parser = spdxparse.Parser; -exports.parse = function () { return spdxparse.parse.apply(spdxparse, arguments); }; -exports.main = function commonjsMain(args) { - if (!args[1]) { - console.log('Usage: '+args[0]+' FILE'); - process.exit(1); - } - var source = __webpack_require__("fs").readFileSync(__webpack_require__("path").normalize(args[1]), "utf8"); - return exports.parser.parse(source); -}; -if ( true && __webpack_require__.c[__webpack_require__.s] === module) { - exports.main(process.argv.slice(1)); -} -} - -/* WEBPACK VAR INJECTION */}.call(this, __webpack_require__("../../node_modules/webpack/buildin/module.js")(module))) - -/***/ }), - -/***/ "../../node_modules/validate-npm-package-license/node_modules/spdx-license-ids/spdx-license-ids.json": -/***/ (function(module) { - -module.exports = JSON.parse("[\"Glide\",\"Abstyles\",\"AFL-1.1\",\"AFL-1.2\",\"AFL-2.0\",\"AFL-2.1\",\"AFL-3.0\",\"AMPAS\",\"APL-1.0\",\"Adobe-Glyph\",\"APAFML\",\"Adobe-2006\",\"AGPL-1.0\",\"Afmparse\",\"Aladdin\",\"ADSL\",\"AMDPLPA\",\"ANTLR-PD\",\"Apache-1.0\",\"Apache-1.1\",\"Apache-2.0\",\"AML\",\"APSL-1.0\",\"APSL-1.1\",\"APSL-1.2\",\"APSL-2.0\",\"Artistic-1.0\",\"Artistic-1.0-Perl\",\"Artistic-1.0-cl8\",\"Artistic-2.0\",\"AAL\",\"Bahyph\",\"Barr\",\"Beerware\",\"BitTorrent-1.0\",\"BitTorrent-1.1\",\"BSL-1.0\",\"Borceux\",\"BSD-2-Clause\",\"BSD-2-Clause-FreeBSD\",\"BSD-2-Clause-NetBSD\",\"BSD-3-Clause\",\"BSD-3-Clause-Clear\",\"BSD-4-Clause\",\"BSD-Protection\",\"BSD-Source-Code\",\"BSD-3-Clause-Attribution\",\"0BSD\",\"BSD-4-Clause-UC\",\"bzip2-1.0.5\",\"bzip2-1.0.6\",\"Caldera\",\"CECILL-1.0\",\"CECILL-1.1\",\"CECILL-2.0\",\"CECILL-2.1\",\"CECILL-B\",\"CECILL-C\",\"ClArtistic\",\"MIT-CMU\",\"CNRI-Jython\",\"CNRI-Python\",\"CNRI-Python-GPL-Compatible\",\"CPOL-1.02\",\"CDDL-1.0\",\"CDDL-1.1\",\"CPAL-1.0\",\"CPL-1.0\",\"CATOSL-1.1\",\"Condor-1.1\",\"CC-BY-1.0\",\"CC-BY-2.0\",\"CC-BY-2.5\",\"CC-BY-3.0\",\"CC-BY-4.0\",\"CC-BY-ND-1.0\",\"CC-BY-ND-2.0\",\"CC-BY-ND-2.5\",\"CC-BY-ND-3.0\",\"CC-BY-ND-4.0\",\"CC-BY-NC-1.0\",\"CC-BY-NC-2.0\",\"CC-BY-NC-2.5\",\"CC-BY-NC-3.0\",\"CC-BY-NC-4.0\",\"CC-BY-NC-ND-1.0\",\"CC-BY-NC-ND-2.0\",\"CC-BY-NC-ND-2.5\",\"CC-BY-NC-ND-3.0\",\"CC-BY-NC-ND-4.0\",\"CC-BY-NC-SA-1.0\",\"CC-BY-NC-SA-2.0\",\"CC-BY-NC-SA-2.5\",\"CC-BY-NC-SA-3.0\",\"CC-BY-NC-SA-4.0\",\"CC-BY-SA-1.0\",\"CC-BY-SA-2.0\",\"CC-BY-SA-2.5\",\"CC-BY-SA-3.0\",\"CC-BY-SA-4.0\",\"CC0-1.0\",\"Crossword\",\"CrystalStacker\",\"CUA-OPL-1.0\",\"Cube\",\"curl\",\"D-FSL-1.0\",\"diffmark\",\"WTFPL\",\"DOC\",\"Dotseqn\",\"DSDP\",\"dvipdfm\",\"EPL-1.0\",\"ECL-1.0\",\"ECL-2.0\",\"eGenix\",\"EFL-1.0\",\"EFL-2.0\",\"MIT-advertising\",\"MIT-enna\",\"Entessa\",\"ErlPL-1.1\",\"EUDatagrid\",\"EUPL-1.0\",\"EUPL-1.1\",\"Eurosym\",\"Fair\",\"MIT-feh\",\"Frameworx-1.0\",\"FreeImage\",\"FTL\",\"FSFAP\",\"FSFUL\",\"FSFULLR\",\"Giftware\",\"GL2PS\",\"Glulxe\",\"AGPL-3.0\",\"GFDL-1.1\",\"GFDL-1.2\",\"GFDL-1.3\",\"GPL-1.0\",\"GPL-2.0\",\"GPL-3.0\",\"LGPL-2.1\",\"LGPL-3.0\",\"LGPL-2.0\",\"gnuplot\",\"gSOAP-1.3b\",\"HaskellReport\",\"HPND\",\"IBM-pibs\",\"IPL-1.0\",\"ICU\",\"ImageMagick\",\"iMatix\",\"Imlib2\",\"IJG\",\"Info-ZIP\",\"Intel-ACPI\",\"Intel\",\"Interbase-1.0\",\"IPA\",\"ISC\",\"JasPer-2.0\",\"JSON\",\"LPPL-1.0\",\"LPPL-1.1\",\"LPPL-1.2\",\"LPPL-1.3a\",\"LPPL-1.3c\",\"Latex2e\",\"BSD-3-Clause-LBNL\",\"Leptonica\",\"LGPLLR\",\"Libpng\",\"libtiff\",\"LAL-1.2\",\"LAL-1.3\",\"LiLiQ-P-1.1\",\"LiLiQ-Rplus-1.1\",\"LiLiQ-R-1.1\",\"LPL-1.02\",\"LPL-1.0\",\"MakeIndex\",\"MTLL\",\"MS-PL\",\"MS-RL\",\"MirOS\",\"MITNFA\",\"MIT\",\"Motosoto\",\"MPL-1.0\",\"MPL-1.1\",\"MPL-2.0\",\"MPL-2.0-no-copyleft-exception\",\"mpich2\",\"Multics\",\"Mup\",\"NASA-1.3\",\"Naumen\",\"NBPL-1.0\",\"NetCDF\",\"NGPL\",\"NOSL\",\"NPL-1.0\",\"NPL-1.1\",\"Newsletr\",\"NLPL\",\"Nokia\",\"NPOSL-3.0\",\"NLOD-1.0\",\"Noweb\",\"NRL\",\"NTP\",\"Nunit\",\"OCLC-2.0\",\"ODbL-1.0\",\"PDDL-1.0\",\"OCCT-PL\",\"OGTSL\",\"OLDAP-2.2.2\",\"OLDAP-1.1\",\"OLDAP-1.2\",\"OLDAP-1.3\",\"OLDAP-1.4\",\"OLDAP-2.0\",\"OLDAP-2.0.1\",\"OLDAP-2.1\",\"OLDAP-2.2\",\"OLDAP-2.2.1\",\"OLDAP-2.3\",\"OLDAP-2.4\",\"OLDAP-2.5\",\"OLDAP-2.6\",\"OLDAP-2.7\",\"OLDAP-2.8\",\"OML\",\"OPL-1.0\",\"OSL-1.0\",\"OSL-1.1\",\"OSL-2.0\",\"OSL-2.1\",\"OSL-3.0\",\"OpenSSL\",\"OSET-PL-2.1\",\"PHP-3.0\",\"PHP-3.01\",\"Plexus\",\"PostgreSQL\",\"psfrag\",\"psutils\",\"Python-2.0\",\"QPL-1.0\",\"Qhull\",\"Rdisc\",\"RPSL-1.0\",\"RPL-1.1\",\"RPL-1.5\",\"RHeCos-1.1\",\"RSCPL\",\"RSA-MD\",\"Ruby\",\"SAX-PD\",\"Saxpath\",\"SCEA\",\"SWL\",\"SMPPL\",\"Sendmail\",\"SGI-B-1.0\",\"SGI-B-1.1\",\"SGI-B-2.0\",\"OFL-1.0\",\"OFL-1.1\",\"SimPL-2.0\",\"Sleepycat\",\"SNIA\",\"Spencer-86\",\"Spencer-94\",\"Spencer-99\",\"SMLNJ\",\"SugarCRM-1.1.3\",\"SISSL\",\"SISSL-1.2\",\"SPL-1.0\",\"Watcom-1.0\",\"TCL\",\"Unlicense\",\"TMate\",\"TORQUE-1.1\",\"TOSL\",\"Unicode-TOU\",\"UPL-1.0\",\"NCSA\",\"Vim\",\"VOSTROM\",\"VSL-1.0\",\"W3C-19980720\",\"W3C\",\"Wsuipa\",\"Xnet\",\"X11\",\"Xerox\",\"XFree86-1.1\",\"xinetd\",\"xpp\",\"XSkat\",\"YPL-1.0\",\"YPL-1.1\",\"Zed\",\"Zend-2.0\",\"Zimbra-1.3\",\"Zimbra-1.4\",\"Zlib\",\"zlib-acknowledgement\",\"ZPL-1.1\",\"ZPL-2.0\",\"ZPL-2.1\",\"BSD-3-Clause-No-Nuclear-License\",\"BSD-3-Clause-No-Nuclear-Warranty\",\"BSD-3-Clause-No-Nuclear-License-2014\",\"eCos-2.0\",\"GPL-2.0-with-autoconf-exception\",\"GPL-2.0-with-bison-exception\",\"GPL-2.0-with-classpath-exception\",\"GPL-2.0-with-font-exception\",\"GPL-2.0-with-GCC-exception\",\"GPL-3.0-with-autoconf-exception\",\"GPL-3.0-with-GCC-exception\",\"StandardML-NJ\",\"WXwindows\"]"); - -/***/ }), - -/***/ "../../node_modules/wcwidth/combining.js": -/***/ (function(module, exports) { - -module.exports = [ - [ 0x0300, 0x036F ], [ 0x0483, 0x0486 ], [ 0x0488, 0x0489 ], - [ 0x0591, 0x05BD ], [ 0x05BF, 0x05BF ], [ 0x05C1, 0x05C2 ], - [ 0x05C4, 0x05C5 ], [ 0x05C7, 0x05C7 ], [ 0x0600, 0x0603 ], - [ 0x0610, 0x0615 ], [ 0x064B, 0x065E ], [ 0x0670, 0x0670 ], - [ 0x06D6, 0x06E4 ], [ 0x06E7, 0x06E8 ], [ 0x06EA, 0x06ED ], - [ 0x070F, 0x070F ], [ 0x0711, 0x0711 ], [ 0x0730, 0x074A ], - [ 0x07A6, 0x07B0 ], [ 0x07EB, 0x07F3 ], [ 0x0901, 0x0902 ], - [ 0x093C, 0x093C ], [ 0x0941, 0x0948 ], [ 0x094D, 0x094D ], - [ 0x0951, 0x0954 ], [ 0x0962, 0x0963 ], [ 0x0981, 0x0981 ], - [ 0x09BC, 0x09BC ], [ 0x09C1, 0x09C4 ], [ 0x09CD, 0x09CD ], - [ 0x09E2, 0x09E3 ], [ 0x0A01, 0x0A02 ], [ 0x0A3C, 0x0A3C ], - [ 0x0A41, 0x0A42 ], [ 0x0A47, 0x0A48 ], [ 0x0A4B, 0x0A4D ], - [ 0x0A70, 0x0A71 ], [ 0x0A81, 0x0A82 ], [ 0x0ABC, 0x0ABC ], - [ 0x0AC1, 0x0AC5 ], [ 0x0AC7, 0x0AC8 ], [ 0x0ACD, 0x0ACD ], - [ 0x0AE2, 0x0AE3 ], [ 0x0B01, 0x0B01 ], [ 0x0B3C, 0x0B3C ], - [ 0x0B3F, 0x0B3F ], [ 0x0B41, 0x0B43 ], [ 0x0B4D, 0x0B4D ], - [ 0x0B56, 0x0B56 ], [ 0x0B82, 0x0B82 ], [ 0x0BC0, 0x0BC0 ], - [ 0x0BCD, 0x0BCD ], [ 0x0C3E, 0x0C40 ], [ 0x0C46, 0x0C48 ], - [ 0x0C4A, 0x0C4D ], [ 0x0C55, 0x0C56 ], [ 0x0CBC, 0x0CBC ], - [ 0x0CBF, 0x0CBF ], [ 0x0CC6, 0x0CC6 ], [ 0x0CCC, 0x0CCD ], - [ 0x0CE2, 0x0CE3 ], [ 0x0D41, 0x0D43 ], [ 0x0D4D, 0x0D4D ], - [ 0x0DCA, 0x0DCA ], [ 0x0DD2, 0x0DD4 ], [ 0x0DD6, 0x0DD6 ], - [ 0x0E31, 0x0E31 ], [ 0x0E34, 0x0E3A ], [ 0x0E47, 0x0E4E ], - [ 0x0EB1, 0x0EB1 ], [ 0x0EB4, 0x0EB9 ], [ 0x0EBB, 0x0EBC ], - [ 0x0EC8, 0x0ECD ], [ 0x0F18, 0x0F19 ], [ 0x0F35, 0x0F35 ], - [ 0x0F37, 0x0F37 ], [ 0x0F39, 0x0F39 ], [ 0x0F71, 0x0F7E ], - [ 0x0F80, 0x0F84 ], [ 0x0F86, 0x0F87 ], [ 0x0F90, 0x0F97 ], - [ 0x0F99, 0x0FBC ], [ 0x0FC6, 0x0FC6 ], [ 0x102D, 0x1030 ], - [ 0x1032, 0x1032 ], [ 0x1036, 0x1037 ], [ 0x1039, 0x1039 ], - [ 0x1058, 0x1059 ], [ 0x1160, 0x11FF ], [ 0x135F, 0x135F ], - [ 0x1712, 0x1714 ], [ 0x1732, 0x1734 ], [ 0x1752, 0x1753 ], - [ 0x1772, 0x1773 ], [ 0x17B4, 0x17B5 ], [ 0x17B7, 0x17BD ], - [ 0x17C6, 0x17C6 ], [ 0x17C9, 0x17D3 ], [ 0x17DD, 0x17DD ], - [ 0x180B, 0x180D ], [ 0x18A9, 0x18A9 ], [ 0x1920, 0x1922 ], - [ 0x1927, 0x1928 ], [ 0x1932, 0x1932 ], [ 0x1939, 0x193B ], - [ 0x1A17, 0x1A18 ], [ 0x1B00, 0x1B03 ], [ 0x1B34, 0x1B34 ], - [ 0x1B36, 0x1B3A ], [ 0x1B3C, 0x1B3C ], [ 0x1B42, 0x1B42 ], - [ 0x1B6B, 0x1B73 ], [ 0x1DC0, 0x1DCA ], [ 0x1DFE, 0x1DFF ], - [ 0x200B, 0x200F ], [ 0x202A, 0x202E ], [ 0x2060, 0x2063 ], - [ 0x206A, 0x206F ], [ 0x20D0, 0x20EF ], [ 0x302A, 0x302F ], - [ 0x3099, 0x309A ], [ 0xA806, 0xA806 ], [ 0xA80B, 0xA80B ], - [ 0xA825, 0xA826 ], [ 0xFB1E, 0xFB1E ], [ 0xFE00, 0xFE0F ], - [ 0xFE20, 0xFE23 ], [ 0xFEFF, 0xFEFF ], [ 0xFFF9, 0xFFFB ], - [ 0x10A01, 0x10A03 ], [ 0x10A05, 0x10A06 ], [ 0x10A0C, 0x10A0F ], - [ 0x10A38, 0x10A3A ], [ 0x10A3F, 0x10A3F ], [ 0x1D167, 0x1D169 ], - [ 0x1D173, 0x1D182 ], [ 0x1D185, 0x1D18B ], [ 0x1D1AA, 0x1D1AD ], - [ 0x1D242, 0x1D244 ], [ 0xE0001, 0xE0001 ], [ 0xE0020, 0xE007F ], - [ 0xE0100, 0xE01EF ] -] - - -/***/ }), - -/***/ "../../node_modules/wcwidth/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -var defaults = __webpack_require__("../../node_modules/defaults/index.js") -var combining = __webpack_require__("../../node_modules/wcwidth/combining.js") - -var DEFAULTS = { - nul: 0, - control: 0 -} - -module.exports = function wcwidth(str) { - return wcswidth(str, DEFAULTS) -} - -module.exports.config = function(opts) { - opts = defaults(opts || {}, DEFAULTS) - return function wcwidth(str) { - return wcswidth(str, opts) - } -} - -/* - * The following functions define the column width of an ISO 10646 - * character as follows: - * - The null character (U+0000) has a column width of 0. - * - Other C0/C1 control characters and DEL will lead to a return value - * of -1. - * - Non-spacing and enclosing combining characters (general category - * code Mn or Me in the - * Unicode database) have a column width of 0. - * - SOFT HYPHEN (U+00AD) has a column width of 1. - * - Other format characters (general category code Cf in the Unicode - * database) and ZERO WIDTH - * SPACE (U+200B) have a column width of 0. - * - Hangul Jamo medial vowels and final consonants (U+1160-U+11FF) - * have a column width of 0. - * - Spacing characters in the East Asian Wide (W) or East Asian - * Full-width (F) category as - * defined in Unicode Technical Report #11 have a column width of 2. - * - All remaining characters (including all printable ISO 8859-1 and - * WGL4 characters, Unicode control characters, etc.) have a column - * width of 1. - * This implementation assumes that characters are encoded in ISO 10646. -*/ - -function wcswidth(str, opts) { - if (typeof str !== 'string') return wcwidth(str, opts) - - var s = 0 - for (var i = 0; i < str.length; i++) { - var n = wcwidth(str.charCodeAt(i), opts) - if (n < 0) return -1 - s += n - } - - return s -} - -function wcwidth(ucs, opts) { - // test for 8-bit control characters - if (ucs === 0) return opts.nul - if (ucs < 32 || (ucs >= 0x7f && ucs < 0xa0)) return opts.control - - // binary search in table of non-spacing characters - if (bisearch(ucs)) return 0 - - // if we arrive here, ucs is not a combining or C0/C1 control character - return 1 + - (ucs >= 0x1100 && - (ucs <= 0x115f || // Hangul Jamo init. consonants - ucs == 0x2329 || ucs == 0x232a || - (ucs >= 0x2e80 && ucs <= 0xa4cf && - ucs != 0x303f) || // CJK ... Yi - (ucs >= 0xac00 && ucs <= 0xd7a3) || // Hangul Syllables - (ucs >= 0xf900 && ucs <= 0xfaff) || // CJK Compatibility Ideographs - (ucs >= 0xfe10 && ucs <= 0xfe19) || // Vertical forms - (ucs >= 0xfe30 && ucs <= 0xfe6f) || // CJK Compatibility Forms - (ucs >= 0xff00 && ucs <= 0xff60) || // Fullwidth Forms - (ucs >= 0xffe0 && ucs <= 0xffe6) || - (ucs >= 0x20000 && ucs <= 0x2fffd) || - (ucs >= 0x30000 && ucs <= 0x3fffd))); -} - -function bisearch(ucs) { - var min = 0 - var max = combining.length - 1 - var mid - - if (ucs < combining[0][0] || ucs > combining[max][1]) return false - - while (max >= min) { - mid = Math.floor((min + max) / 2) - if (ucs > combining[mid][1]) min = mid + 1 - else if (ucs < combining[mid][0]) max = mid - 1 - else return true - } - - return false -} - - -/***/ }), - -/***/ "../../node_modules/webpack/buildin/module.js": -/***/ (function(module, exports) { - -module.exports = function(module) { - if (!module.webpackPolyfill) { - module.deprecate = function() {}; - module.paths = []; - // module.parent = undefined by default - if (!module.children) module.children = []; - Object.defineProperty(module, "loaded", { - enumerable: true, - get: function() { - return module.l; - } - }); - Object.defineProperty(module, "id", { - enumerable: true, - get: function() { - return module.i; - } - }); - module.webpackPolyfill = 1; - } - return module; -}; - - -/***/ }), - -/***/ "../../node_modules/which/which.js": -/***/ (function(module, exports, __webpack_require__) { - -const isWindows = process.platform === 'win32' || - process.env.OSTYPE === 'cygwin' || - process.env.OSTYPE === 'msys' - -const path = __webpack_require__("path") -const COLON = isWindows ? ';' : ':' -const isexe = __webpack_require__("../../node_modules/isexe/index.js") - -const getNotFoundError = (cmd) => - Object.assign(new Error(`not found: ${cmd}`), { code: 'ENOENT' }) - -const getPathInfo = (cmd, opt) => { - const colon = opt.colon || COLON - - // If it has a slash, then we don't bother searching the pathenv. - // just check the file itself, and that's it. - const pathEnv = cmd.match(/\//) || isWindows && cmd.match(/\\/) ? [''] - : ( - [ - // windows always checks the cwd first - ...(isWindows ? [process.cwd()] : []), - ...(opt.path || process.env.PATH || - /* istanbul ignore next: very unusual */ '').split(colon), - ] - ) - const pathExtExe = isWindows - ? opt.pathExt || process.env.PATHEXT || '.EXE;.CMD;.BAT;.COM' - : '' - const pathExt = isWindows ? pathExtExe.split(colon) : [''] - - if (isWindows) { - if (cmd.indexOf('.') !== -1 && pathExt[0] !== '') - pathExt.unshift('') - } - - return { - pathEnv, - pathExt, - pathExtExe, - } -} - -const which = (cmd, opt, cb) => { - if (typeof opt === 'function') { - cb = opt - opt = {} - } - if (!opt) - opt = {} - - const { pathEnv, pathExt, pathExtExe } = getPathInfo(cmd, opt) - const found = [] - - const step = i => new Promise((resolve, reject) => { - if (i === pathEnv.length) - return opt.all && found.length ? resolve(found) - : reject(getNotFoundError(cmd)) - - const ppRaw = pathEnv[i] - const pathPart = /^".*"$/.test(ppRaw) ? ppRaw.slice(1, -1) : ppRaw - - const pCmd = path.join(pathPart, cmd) - const p = !pathPart && /^\.[\\\/]/.test(cmd) ? cmd.slice(0, 2) + pCmd - : pCmd - - resolve(subStep(p, i, 0)) - }) - - const subStep = (p, i, ii) => new Promise((resolve, reject) => { - if (ii === pathExt.length) - return resolve(step(i + 1)) - const ext = pathExt[ii] - isexe(p + ext, { pathExt: pathExtExe }, (er, is) => { - if (!er && is) { - if (opt.all) - found.push(p + ext) - else - return resolve(p + ext) - } - return resolve(subStep(p, i, ii + 1)) - }) - }) - - return cb ? step(0).then(res => cb(null, res), cb) : step(0) -} - -const whichSync = (cmd, opt) => { - opt = opt || {} - - const { pathEnv, pathExt, pathExtExe } = getPathInfo(cmd, opt) - const found = [] - - for (let i = 0; i < pathEnv.length; i ++) { - const ppRaw = pathEnv[i] - const pathPart = /^".*"$/.test(ppRaw) ? ppRaw.slice(1, -1) : ppRaw - - const pCmd = path.join(pathPart, cmd) - const p = !pathPart && /^\.[\\\/]/.test(cmd) ? cmd.slice(0, 2) + pCmd - : pCmd - - for (let j = 0; j < pathExt.length; j ++) { - const cur = p + pathExt[j] - try { - const is = isexe.sync(cur, { pathExt: pathExtExe }) - if (is) { - if (opt.all) - found.push(cur) - else - return cur - } - } catch (ex) {} - } - } - - if (opt.all && found.length) - return found - - if (opt.nothrow) - return null - - throw getNotFoundError(cmd) -} - -module.exports = which -which.sync = whichSync - - -/***/ }), - -/***/ "../../node_modules/wrappy/wrappy.js": -/***/ (function(module, exports) { - -// Returns a wrapper function that returns a wrapped callback -// The wrapper function should do some stuff, and return a -// presumably different callback function. -// This makes sure that own properties are retained, so that -// decorations and such are not lost along the way. -module.exports = wrappy -function wrappy (fn, cb) { - if (fn && cb) return wrappy(fn)(cb) - - if (typeof fn !== 'function') - throw new TypeError('need wrapper function') - - Object.keys(fn).forEach(function (k) { - wrapper[k] = fn[k] - }) - - return wrapper - - function wrapper() { - var args = new Array(arguments.length) - for (var i = 0; i < args.length; i++) { - args[i] = arguments[i] - } - var ret = fn.apply(this, args) - var cb = args[args.length-1] - if (typeof ret === 'function' && ret !== cb) { - Object.keys(cb).forEach(function (k) { - ret[k] = cb[k] - }) - } - return ret - } -} - - -/***/ }), - -/***/ "../../node_modules/write-json-file/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); -const fs = __webpack_require__("../../node_modules/graceful-fs/graceful-fs.js"); -const writeFileAtomic = __webpack_require__("../../node_modules/write-json-file/node_modules/write-file-atomic/index.js"); -const sortKeys = __webpack_require__("../../node_modules/sort-keys/index.js"); -const makeDir = __webpack_require__("../../node_modules/write-json-file/node_modules/make-dir/index.js"); -const pify = __webpack_require__("../../node_modules/write-json-file/node_modules/pify/index.js"); -const detectIndent = __webpack_require__("../../node_modules/write-json-file/node_modules/detect-indent/index.js"); - -const init = (fn, filePath, data, options) => { - if (!filePath) { - throw new TypeError('Expected a filepath'); - } - - if (data === undefined) { - throw new TypeError('Expected data to stringify'); - } - - options = Object.assign({ - indent: '\t', - sortKeys: false - }, options); - - if (options.sortKeys) { - data = sortKeys(data, { - deep: true, - compare: typeof options.sortKeys === 'function' ? options.sortKeys : undefined - }); - } - - return fn(filePath, data, options); -}; - -const readFile = filePath => pify(fs.readFile)(filePath, 'utf8').catch(() => {}); - -const main = (filePath, data, options) => { - return (options.detectIndent ? readFile(filePath) : Promise.resolve()) - .then(string => { - const indent = string ? detectIndent(string).indent : options.indent; - const json = JSON.stringify(data, options.replacer, indent); - - return pify(writeFileAtomic)(filePath, `${json}\n`, {mode: options.mode}); - }); -}; - -const mainSync = (filePath, data, options) => { - let {indent} = options; - - if (options.detectIndent) { - try { - const file = fs.readFileSync(filePath, 'utf8'); - indent = detectIndent(file).indent; - } catch (error) { - if (error.code !== 'ENOENT') { - throw error; - } - } - } - - const json = JSON.stringify(data, options.replacer, indent); - - return writeFileAtomic.sync(filePath, `${json}\n`, {mode: options.mode}); -}; - -const writeJsonFile = (filePath, data, options) => { - return makeDir(path.dirname(filePath), {fs}) - .then(() => init(main, filePath, data, options)); -}; - -module.exports = writeJsonFile; -// TODO: Remove this for the next major release -module.exports.default = writeJsonFile; -module.exports.sync = (filePath, data, options) => { - makeDir.sync(path.dirname(filePath), {fs}); - init(mainSync, filePath, data, options); -}; - - -/***/ }), - -/***/ "../../node_modules/write-json-file/node_modules/detect-indent/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -// detect either spaces or tabs but not both to properly handle tabs -// for indentation and spaces for alignment -const INDENT_RE = /^(?:( )+|\t+)/; - -function getMostUsed(indents) { - let result = 0; - let maxUsed = 0; - let maxWeight = 0; - - for (const entry of indents) { - // TODO: use destructuring when targeting Node.js 6 - const key = entry[0]; - const val = entry[1]; - - const u = val[0]; - const w = val[1]; - - if (u > maxUsed || (u === maxUsed && w > maxWeight)) { - maxUsed = u; - maxWeight = w; - result = Number(key); - } - } - - return result; -} - -module.exports = str => { - if (typeof str !== 'string') { - throw new TypeError('Expected a string'); - } - - // used to see if tabs or spaces are the most used - let tabs = 0; - let spaces = 0; - - // remember the size of previous line's indentation - let prev = 0; - - // remember how many indents/unindents as occurred for a given size - // and how much lines follow a given indentation - // - // indents = { - // 3: [1, 0], - // 4: [1, 5], - // 5: [1, 0], - // 12: [1, 0], - // } - const indents = new Map(); - - // pointer to the array of last used indent - let current; - - // whether the last action was an indent (opposed to an unindent) - let isIndent; - - for (const line of str.split(/\n/g)) { - if (!line) { - // ignore empty lines - continue; - } - - let indent; - const matches = line.match(INDENT_RE); - - if (matches) { - indent = matches[0].length; - - if (matches[1]) { - spaces++; - } else { - tabs++; - } - } else { - indent = 0; - } - - const diff = indent - prev; - prev = indent; - - if (diff) { - // an indent or unindent has been detected - - isIndent = diff > 0; - - current = indents.get(isIndent ? diff : -diff); - - if (current) { - current[0]++; - } else { - current = [1, 0]; - indents.set(diff, current); - } - } else if (current) { - // if the last action was an indent, increment the weight - current[1] += Number(isIndent); - } - } - - const amount = getMostUsed(indents); - - let type; - let indent; - if (!amount) { - type = null; - indent = ''; - } else if (spaces >= tabs) { - type = 'space'; - indent = ' '.repeat(amount); - } else { - type = 'tab'; - indent = '\t'.repeat(amount); - } - - return { - amount, - type, - indent - }; -}; - - -/***/ }), - -/***/ "../../node_modules/write-json-file/node_modules/make-dir/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const fs = __webpack_require__("fs"); -const path = __webpack_require__("path"); -const pify = __webpack_require__("../../node_modules/write-json-file/node_modules/pify/index.js"); -const semver = __webpack_require__("../../node_modules/write-json-file/node_modules/semver/semver.js"); - -const defaults = { - mode: 0o777 & (~process.umask()), - fs -}; - -const useNativeRecursiveOption = semver.satisfies(process.version, '>=10.12.0'); - -// https://github.com/nodejs/node/issues/8987 -// https://github.com/libuv/libuv/pull/1088 -const checkPath = pth => { - if (process.platform === 'win32') { - const pathHasInvalidWinCharacters = /[<>:"|?*]/.test(pth.replace(path.parse(pth).root, '')); - - if (pathHasInvalidWinCharacters) { - const error = new Error(`Path contains invalid characters: ${pth}`); - error.code = 'EINVAL'; - throw error; - } - } -}; - -const permissionError = pth => { - // This replicates the exception of `fs.mkdir` with native the - // `recusive` option when run on an invalid drive under Windows. - const error = new Error(`operation not permitted, mkdir '${pth}'`); - error.code = 'EPERM'; - error.errno = -4048; - error.path = pth; - error.syscall = 'mkdir'; - return error; -}; - -const makeDir = (input, options) => Promise.resolve().then(() => { - checkPath(input); - options = Object.assign({}, defaults, options); - - // TODO: Use util.promisify when targeting Node.js 8 - const mkdir = pify(options.fs.mkdir); - const stat = pify(options.fs.stat); - - if (useNativeRecursiveOption && options.fs.mkdir === fs.mkdir) { - const pth = path.resolve(input); - - return mkdir(pth, { - mode: options.mode, - recursive: true - }).then(() => pth); - } - - const make = pth => { - return mkdir(pth, options.mode) - .then(() => pth) - .catch(error => { - if (error.code === 'EPERM') { - throw error; - } - - if (error.code === 'ENOENT') { - if (path.dirname(pth) === pth) { - throw permissionError(pth); - } - - if (error.message.includes('null bytes')) { - throw error; - } - - return make(path.dirname(pth)).then(() => make(pth)); - } - - return stat(pth) - .then(stats => stats.isDirectory() ? pth : Promise.reject()) - .catch(() => { - throw error; - }); - }); - }; - - return make(path.resolve(input)); -}); - -module.exports = makeDir; -module.exports.default = makeDir; - -module.exports.sync = (input, options) => { - checkPath(input); - options = Object.assign({}, defaults, options); - - if (useNativeRecursiveOption && options.fs.mkdirSync === fs.mkdirSync) { - const pth = path.resolve(input); - - fs.mkdirSync(pth, { - mode: options.mode, - recursive: true - }); - - return pth; - } - - const make = pth => { - try { - options.fs.mkdirSync(pth, options.mode); - } catch (error) { - if (error.code === 'EPERM') { - throw error; - } - - if (error.code === 'ENOENT') { - if (path.dirname(pth) === pth) { - throw permissionError(pth); - } - - if (error.message.includes('null bytes')) { - throw error; - } - - make(path.dirname(pth)); - return make(pth); - } - - try { - if (!options.fs.statSync(pth).isDirectory()) { - throw new Error('The path is not a directory'); - } - } catch (_) { - throw error; - } - } - - return pth; - }; - - return make(path.resolve(input)); -}; - - -/***/ }), - -/***/ "../../node_modules/write-json-file/node_modules/pify/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - - -const processFn = (fn, options) => function (...args) { - const P = options.promiseModule; - - return new P((resolve, reject) => { - if (options.multiArgs) { - args.push((...result) => { - if (options.errorFirst) { - if (result[0]) { - reject(result); - } else { - result.shift(); - resolve(result); - } - } else { - resolve(result); - } - }); - } else if (options.errorFirst) { - args.push((error, result) => { - if (error) { - reject(error); - } else { - resolve(result); - } - }); - } else { - args.push(resolve); - } - - fn.apply(this, args); - }); -}; - -module.exports = (input, options) => { - options = Object.assign({ - exclude: [/.+(Sync|Stream)$/], - errorFirst: true, - promiseModule: Promise - }, options); - - const objType = typeof input; - if (!(input !== null && (objType === 'object' || objType === 'function'))) { - throw new TypeError(`Expected \`input\` to be a \`Function\` or \`Object\`, got \`${input === null ? 'null' : objType}\``); - } - - const filter = key => { - const match = pattern => typeof pattern === 'string' ? key === pattern : pattern.test(key); - return options.include ? options.include.some(match) : !options.exclude.some(match); - }; - - let ret; - if (objType === 'function') { - ret = function (...args) { - return options.excludeMain ? input(...args) : processFn(input, options).apply(this, args); - }; - } else { - ret = Object.create(Object.getPrototypeOf(input)); - } - - for (const key in input) { // eslint-disable-line guard-for-in - const property = input[key]; - ret[key] = typeof property === 'function' && filter(key) ? processFn(property, options) : property; - } - - return ret; -}; - - -/***/ }), - -/***/ "../../node_modules/write-json-file/node_modules/semver/semver.js": -/***/ (function(module, exports) { - -exports = module.exports = SemVer - -var debug -/* istanbul ignore next */ -if (typeof process === 'object' && - process.env && - process.env.NODE_DEBUG && - /\bsemver\b/i.test(process.env.NODE_DEBUG)) { - debug = function () { - var args = Array.prototype.slice.call(arguments, 0) - args.unshift('SEMVER') - console.log.apply(console, args) - } -} else { - debug = function () {} -} - -// Note: this is the semver.org version of the spec that it implements -// Not necessarily the package version of this code. -exports.SEMVER_SPEC_VERSION = '2.0.0' - -var MAX_LENGTH = 256 -var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || - /* istanbul ignore next */ 9007199254740991 - -// Max safe segment length for coercion. -var MAX_SAFE_COMPONENT_LENGTH = 16 - -// The actual regexps go on exports.re -var re = exports.re = [] -var src = exports.src = [] -var R = 0 - -// The following Regular Expressions can be used for tokenizing, -// validating, and parsing SemVer version strings. - -// ## Numeric Identifier -// A single `0`, or a non-zero digit followed by zero or more digits. - -var NUMERICIDENTIFIER = R++ -src[NUMERICIDENTIFIER] = '0|[1-9]\\d*' -var NUMERICIDENTIFIERLOOSE = R++ -src[NUMERICIDENTIFIERLOOSE] = '[0-9]+' - -// ## Non-numeric Identifier -// Zero or more digits, followed by a letter or hyphen, and then zero or -// more letters, digits, or hyphens. - -var NONNUMERICIDENTIFIER = R++ -src[NONNUMERICIDENTIFIER] = '\\d*[a-zA-Z-][a-zA-Z0-9-]*' - -// ## Main Version -// Three dot-separated numeric identifiers. - -var MAINVERSION = R++ -src[MAINVERSION] = '(' + src[NUMERICIDENTIFIER] + ')\\.' + - '(' + src[NUMERICIDENTIFIER] + ')\\.' + - '(' + src[NUMERICIDENTIFIER] + ')' - -var MAINVERSIONLOOSE = R++ -src[MAINVERSIONLOOSE] = '(' + src[NUMERICIDENTIFIERLOOSE] + ')\\.' + - '(' + src[NUMERICIDENTIFIERLOOSE] + ')\\.' + - '(' + src[NUMERICIDENTIFIERLOOSE] + ')' - -// ## Pre-release Version Identifier -// A numeric identifier, or a non-numeric identifier. - -var PRERELEASEIDENTIFIER = R++ -src[PRERELEASEIDENTIFIER] = '(?:' + src[NUMERICIDENTIFIER] + - '|' + src[NONNUMERICIDENTIFIER] + ')' - -var PRERELEASEIDENTIFIERLOOSE = R++ -src[PRERELEASEIDENTIFIERLOOSE] = '(?:' + src[NUMERICIDENTIFIERLOOSE] + - '|' + src[NONNUMERICIDENTIFIER] + ')' - -// ## Pre-release Version -// Hyphen, followed by one or more dot-separated pre-release version -// identifiers. - -var PRERELEASE = R++ -src[PRERELEASE] = '(?:-(' + src[PRERELEASEIDENTIFIER] + - '(?:\\.' + src[PRERELEASEIDENTIFIER] + ')*))' - -var PRERELEASELOOSE = R++ -src[PRERELEASELOOSE] = '(?:-?(' + src[PRERELEASEIDENTIFIERLOOSE] + - '(?:\\.' + src[PRERELEASEIDENTIFIERLOOSE] + ')*))' - -// ## Build Metadata Identifier -// Any combination of digits, letters, or hyphens. - -var BUILDIDENTIFIER = R++ -src[BUILDIDENTIFIER] = '[0-9A-Za-z-]+' - -// ## Build Metadata -// Plus sign, followed by one or more period-separated build metadata -// identifiers. - -var BUILD = R++ -src[BUILD] = '(?:\\+(' + src[BUILDIDENTIFIER] + - '(?:\\.' + src[BUILDIDENTIFIER] + ')*))' - -// ## Full Version String -// A main version, followed optionally by a pre-release version and -// build metadata. - -// Note that the only major, minor, patch, and pre-release sections of -// the version string are capturing groups. The build metadata is not a -// capturing group, because it should not ever be used in version -// comparison. - -var FULL = R++ -var FULLPLAIN = 'v?' + src[MAINVERSION] + - src[PRERELEASE] + '?' + - src[BUILD] + '?' - -src[FULL] = '^' + FULLPLAIN + '$' - -// like full, but allows v1.2.3 and =1.2.3, which people do sometimes. -// also, 1.0.0alpha1 (prerelease without the hyphen) which is pretty -// common in the npm registry. -var LOOSEPLAIN = '[v=\\s]*' + src[MAINVERSIONLOOSE] + - src[PRERELEASELOOSE] + '?' + - src[BUILD] + '?' - -var LOOSE = R++ -src[LOOSE] = '^' + LOOSEPLAIN + '$' - -var GTLT = R++ -src[GTLT] = '((?:<|>)?=?)' - -// Something like "2.*" or "1.2.x". -// Note that "x.x" is a valid xRange identifer, meaning "any version" -// Only the first item is strictly required. -var XRANGEIDENTIFIERLOOSE = R++ -src[XRANGEIDENTIFIERLOOSE] = src[NUMERICIDENTIFIERLOOSE] + '|x|X|\\*' -var XRANGEIDENTIFIER = R++ -src[XRANGEIDENTIFIER] = src[NUMERICIDENTIFIER] + '|x|X|\\*' - -var XRANGEPLAIN = R++ -src[XRANGEPLAIN] = '[v=\\s]*(' + src[XRANGEIDENTIFIER] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIER] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIER] + ')' + - '(?:' + src[PRERELEASE] + ')?' + - src[BUILD] + '?' + - ')?)?' - -var XRANGEPLAINLOOSE = R++ -src[XRANGEPLAINLOOSE] = '[v=\\s]*(' + src[XRANGEIDENTIFIERLOOSE] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIERLOOSE] + ')' + - '(?:\\.(' + src[XRANGEIDENTIFIERLOOSE] + ')' + - '(?:' + src[PRERELEASELOOSE] + ')?' + - src[BUILD] + '?' + - ')?)?' - -var XRANGE = R++ -src[XRANGE] = '^' + src[GTLT] + '\\s*' + src[XRANGEPLAIN] + '$' -var XRANGELOOSE = R++ -src[XRANGELOOSE] = '^' + src[GTLT] + '\\s*' + src[XRANGEPLAINLOOSE] + '$' - -// Coercion. -// Extract anything that could conceivably be a part of a valid semver -var COERCE = R++ -src[COERCE] = '(?:^|[^\\d])' + - '(\\d{1,' + MAX_SAFE_COMPONENT_LENGTH + '})' + - '(?:\\.(\\d{1,' + MAX_SAFE_COMPONENT_LENGTH + '}))?' + - '(?:\\.(\\d{1,' + MAX_SAFE_COMPONENT_LENGTH + '}))?' + - '(?:$|[^\\d])' - -// Tilde ranges. -// Meaning is "reasonably at or greater than" -var LONETILDE = R++ -src[LONETILDE] = '(?:~>?)' - -var TILDETRIM = R++ -src[TILDETRIM] = '(\\s*)' + src[LONETILDE] + '\\s+' -re[TILDETRIM] = new RegExp(src[TILDETRIM], 'g') -var tildeTrimReplace = '$1~' - -var TILDE = R++ -src[TILDE] = '^' + src[LONETILDE] + src[XRANGEPLAIN] + '$' -var TILDELOOSE = R++ -src[TILDELOOSE] = '^' + src[LONETILDE] + src[XRANGEPLAINLOOSE] + '$' - -// Caret ranges. -// Meaning is "at least and backwards compatible with" -var LONECARET = R++ -src[LONECARET] = '(?:\\^)' - -var CARETTRIM = R++ -src[CARETTRIM] = '(\\s*)' + src[LONECARET] + '\\s+' -re[CARETTRIM] = new RegExp(src[CARETTRIM], 'g') -var caretTrimReplace = '$1^' - -var CARET = R++ -src[CARET] = '^' + src[LONECARET] + src[XRANGEPLAIN] + '$' -var CARETLOOSE = R++ -src[CARETLOOSE] = '^' + src[LONECARET] + src[XRANGEPLAINLOOSE] + '$' - -// A simple gt/lt/eq thing, or just "" to indicate "any version" -var COMPARATORLOOSE = R++ -src[COMPARATORLOOSE] = '^' + src[GTLT] + '\\s*(' + LOOSEPLAIN + ')$|^$' -var COMPARATOR = R++ -src[COMPARATOR] = '^' + src[GTLT] + '\\s*(' + FULLPLAIN + ')$|^$' - -// An expression to strip any whitespace between the gtlt and the thing -// it modifies, so that `> 1.2.3` ==> `>1.2.3` -var COMPARATORTRIM = R++ -src[COMPARATORTRIM] = '(\\s*)' + src[GTLT] + - '\\s*(' + LOOSEPLAIN + '|' + src[XRANGEPLAIN] + ')' - -// this one has to use the /g flag -re[COMPARATORTRIM] = new RegExp(src[COMPARATORTRIM], 'g') -var comparatorTrimReplace = '$1$2$3' - -// Something like `1.2.3 - 1.2.4` -// Note that these all use the loose form, because they'll be -// checked against either the strict or loose comparator form -// later. -var HYPHENRANGE = R++ -src[HYPHENRANGE] = '^\\s*(' + src[XRANGEPLAIN] + ')' + - '\\s+-\\s+' + - '(' + src[XRANGEPLAIN] + ')' + - '\\s*$' - -var HYPHENRANGELOOSE = R++ -src[HYPHENRANGELOOSE] = '^\\s*(' + src[XRANGEPLAINLOOSE] + ')' + - '\\s+-\\s+' + - '(' + src[XRANGEPLAINLOOSE] + ')' + - '\\s*$' - -// Star ranges basically just allow anything at all. -var STAR = R++ -src[STAR] = '(<|>)?=?\\s*\\*' - -// Compile to actual regexp objects. -// All are flag-free, unless they were created above with a flag. -for (var i = 0; i < R; i++) { - debug(i, src[i]) - if (!re[i]) { - re[i] = new RegExp(src[i]) - } -} - -exports.parse = parse -function parse (version, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - if (version instanceof SemVer) { - return version - } - - if (typeof version !== 'string') { - return null - } - - if (version.length > MAX_LENGTH) { - return null - } - - var r = options.loose ? re[LOOSE] : re[FULL] - if (!r.test(version)) { - return null - } - - try { - return new SemVer(version, options) - } catch (er) { - return null - } -} - -exports.valid = valid -function valid (version, options) { - var v = parse(version, options) - return v ? v.version : null -} - -exports.clean = clean -function clean (version, options) { - var s = parse(version.trim().replace(/^[=v]+/, ''), options) - return s ? s.version : null -} - -exports.SemVer = SemVer - -function SemVer (version, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - if (version instanceof SemVer) { - if (version.loose === options.loose) { - return version - } else { - version = version.version - } - } else if (typeof version !== 'string') { - throw new TypeError('Invalid Version: ' + version) - } - - if (version.length > MAX_LENGTH) { - throw new TypeError('version is longer than ' + MAX_LENGTH + ' characters') - } - - if (!(this instanceof SemVer)) { - return new SemVer(version, options) - } - - debug('SemVer', version, options) - this.options = options - this.loose = !!options.loose - - var m = version.trim().match(options.loose ? re[LOOSE] : re[FULL]) - - if (!m) { - throw new TypeError('Invalid Version: ' + version) - } - - this.raw = version - - // these are actually numbers - this.major = +m[1] - this.minor = +m[2] - this.patch = +m[3] - - if (this.major > MAX_SAFE_INTEGER || this.major < 0) { - throw new TypeError('Invalid major version') - } - - if (this.minor > MAX_SAFE_INTEGER || this.minor < 0) { - throw new TypeError('Invalid minor version') - } - - if (this.patch > MAX_SAFE_INTEGER || this.patch < 0) { - throw new TypeError('Invalid patch version') - } - - // numberify any prerelease numeric ids - if (!m[4]) { - this.prerelease = [] - } else { - this.prerelease = m[4].split('.').map(function (id) { - if (/^[0-9]+$/.test(id)) { - var num = +id - if (num >= 0 && num < MAX_SAFE_INTEGER) { - return num - } - } - return id - }) - } - - this.build = m[5] ? m[5].split('.') : [] - this.format() -} - -SemVer.prototype.format = function () { - this.version = this.major + '.' + this.minor + '.' + this.patch - if (this.prerelease.length) { - this.version += '-' + this.prerelease.join('.') - } - return this.version -} - -SemVer.prototype.toString = function () { - return this.version -} - -SemVer.prototype.compare = function (other) { - debug('SemVer.compare', this.version, this.options, other) - if (!(other instanceof SemVer)) { - other = new SemVer(other, this.options) - } - - return this.compareMain(other) || this.comparePre(other) -} - -SemVer.prototype.compareMain = function (other) { - if (!(other instanceof SemVer)) { - other = new SemVer(other, this.options) - } - - return compareIdentifiers(this.major, other.major) || - compareIdentifiers(this.minor, other.minor) || - compareIdentifiers(this.patch, other.patch) -} - -SemVer.prototype.comparePre = function (other) { - if (!(other instanceof SemVer)) { - other = new SemVer(other, this.options) - } - - // NOT having a prerelease is > having one - if (this.prerelease.length && !other.prerelease.length) { - return -1 - } else if (!this.prerelease.length && other.prerelease.length) { - return 1 - } else if (!this.prerelease.length && !other.prerelease.length) { - return 0 - } - - var i = 0 - do { - var a = this.prerelease[i] - var b = other.prerelease[i] - debug('prerelease compare', i, a, b) - if (a === undefined && b === undefined) { - return 0 - } else if (b === undefined) { - return 1 - } else if (a === undefined) { - return -1 - } else if (a === b) { - continue - } else { - return compareIdentifiers(a, b) - } - } while (++i) -} - -// preminor will bump the version up to the next minor release, and immediately -// down to pre-release. premajor and prepatch work the same way. -SemVer.prototype.inc = function (release, identifier) { - switch (release) { - case 'premajor': - this.prerelease.length = 0 - this.patch = 0 - this.minor = 0 - this.major++ - this.inc('pre', identifier) - break - case 'preminor': - this.prerelease.length = 0 - this.patch = 0 - this.minor++ - this.inc('pre', identifier) - break - case 'prepatch': - // If this is already a prerelease, it will bump to the next version - // drop any prereleases that might already exist, since they are not - // relevant at this point. - this.prerelease.length = 0 - this.inc('patch', identifier) - this.inc('pre', identifier) - break - // If the input is a non-prerelease version, this acts the same as - // prepatch. - case 'prerelease': - if (this.prerelease.length === 0) { - this.inc('patch', identifier) - } - this.inc('pre', identifier) - break - - case 'major': - // If this is a pre-major version, bump up to the same major version. - // Otherwise increment major. - // 1.0.0-5 bumps to 1.0.0 - // 1.1.0 bumps to 2.0.0 - if (this.minor !== 0 || - this.patch !== 0 || - this.prerelease.length === 0) { - this.major++ - } - this.minor = 0 - this.patch = 0 - this.prerelease = [] - break - case 'minor': - // If this is a pre-minor version, bump up to the same minor version. - // Otherwise increment minor. - // 1.2.0-5 bumps to 1.2.0 - // 1.2.1 bumps to 1.3.0 - if (this.patch !== 0 || this.prerelease.length === 0) { - this.minor++ - } - this.patch = 0 - this.prerelease = [] - break - case 'patch': - // If this is not a pre-release version, it will increment the patch. - // If it is a pre-release it will bump up to the same patch version. - // 1.2.0-5 patches to 1.2.0 - // 1.2.0 patches to 1.2.1 - if (this.prerelease.length === 0) { - this.patch++ - } - this.prerelease = [] - break - // This probably shouldn't be used publicly. - // 1.0.0 "pre" would become 1.0.0-0 which is the wrong direction. - case 'pre': - if (this.prerelease.length === 0) { - this.prerelease = [0] - } else { - var i = this.prerelease.length - while (--i >= 0) { - if (typeof this.prerelease[i] === 'number') { - this.prerelease[i]++ - i = -2 - } - } - if (i === -1) { - // didn't increment anything - this.prerelease.push(0) - } - } - if (identifier) { - // 1.2.0-beta.1 bumps to 1.2.0-beta.2, - // 1.2.0-beta.fooblz or 1.2.0-beta bumps to 1.2.0-beta.0 - if (this.prerelease[0] === identifier) { - if (isNaN(this.prerelease[1])) { - this.prerelease = [identifier, 0] - } - } else { - this.prerelease = [identifier, 0] - } - } - break - - default: - throw new Error('invalid increment argument: ' + release) - } - this.format() - this.raw = this.version - return this -} - -exports.inc = inc -function inc (version, release, loose, identifier) { - if (typeof (loose) === 'string') { - identifier = loose - loose = undefined - } - - try { - return new SemVer(version, loose).inc(release, identifier).version - } catch (er) { - return null - } -} - -exports.diff = diff -function diff (version1, version2) { - if (eq(version1, version2)) { - return null - } else { - var v1 = parse(version1) - var v2 = parse(version2) - var prefix = '' - if (v1.prerelease.length || v2.prerelease.length) { - prefix = 'pre' - var defaultResult = 'prerelease' - } - for (var key in v1) { - if (key === 'major' || key === 'minor' || key === 'patch') { - if (v1[key] !== v2[key]) { - return prefix + key - } - } - } - return defaultResult // may be undefined - } -} - -exports.compareIdentifiers = compareIdentifiers - -var numeric = /^[0-9]+$/ -function compareIdentifiers (a, b) { - var anum = numeric.test(a) - var bnum = numeric.test(b) - - if (anum && bnum) { - a = +a - b = +b - } - - return a === b ? 0 - : (anum && !bnum) ? -1 - : (bnum && !anum) ? 1 - : a < b ? -1 - : 1 -} - -exports.rcompareIdentifiers = rcompareIdentifiers -function rcompareIdentifiers (a, b) { - return compareIdentifiers(b, a) -} - -exports.major = major -function major (a, loose) { - return new SemVer(a, loose).major -} - -exports.minor = minor -function minor (a, loose) { - return new SemVer(a, loose).minor -} - -exports.patch = patch -function patch (a, loose) { - return new SemVer(a, loose).patch -} - -exports.compare = compare -function compare (a, b, loose) { - return new SemVer(a, loose).compare(new SemVer(b, loose)) -} - -exports.compareLoose = compareLoose -function compareLoose (a, b) { - return compare(a, b, true) -} - -exports.rcompare = rcompare -function rcompare (a, b, loose) { - return compare(b, a, loose) -} - -exports.sort = sort -function sort (list, loose) { - return list.sort(function (a, b) { - return exports.compare(a, b, loose) - }) -} - -exports.rsort = rsort -function rsort (list, loose) { - return list.sort(function (a, b) { - return exports.rcompare(a, b, loose) - }) -} - -exports.gt = gt -function gt (a, b, loose) { - return compare(a, b, loose) > 0 -} - -exports.lt = lt -function lt (a, b, loose) { - return compare(a, b, loose) < 0 -} - -exports.eq = eq -function eq (a, b, loose) { - return compare(a, b, loose) === 0 -} - -exports.neq = neq -function neq (a, b, loose) { - return compare(a, b, loose) !== 0 -} - -exports.gte = gte -function gte (a, b, loose) { - return compare(a, b, loose) >= 0 -} - -exports.lte = lte -function lte (a, b, loose) { - return compare(a, b, loose) <= 0 -} - -exports.cmp = cmp -function cmp (a, op, b, loose) { - switch (op) { - case '===': - if (typeof a === 'object') - a = a.version - if (typeof b === 'object') - b = b.version - return a === b - - case '!==': - if (typeof a === 'object') - a = a.version - if (typeof b === 'object') - b = b.version - return a !== b - - case '': - case '=': - case '==': - return eq(a, b, loose) - - case '!=': - return neq(a, b, loose) - - case '>': - return gt(a, b, loose) - - case '>=': - return gte(a, b, loose) - - case '<': - return lt(a, b, loose) - - case '<=': - return lte(a, b, loose) - - default: - throw new TypeError('Invalid operator: ' + op) - } -} - -exports.Comparator = Comparator -function Comparator (comp, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - if (comp instanceof Comparator) { - if (comp.loose === !!options.loose) { - return comp - } else { - comp = comp.value - } - } - - if (!(this instanceof Comparator)) { - return new Comparator(comp, options) - } - - debug('comparator', comp, options) - this.options = options - this.loose = !!options.loose - this.parse(comp) - - if (this.semver === ANY) { - this.value = '' - } else { - this.value = this.operator + this.semver.version - } - - debug('comp', this) -} - -var ANY = {} -Comparator.prototype.parse = function (comp) { - var r = this.options.loose ? re[COMPARATORLOOSE] : re[COMPARATOR] - var m = comp.match(r) - - if (!m) { - throw new TypeError('Invalid comparator: ' + comp) - } - - this.operator = m[1] - if (this.operator === '=') { - this.operator = '' - } - - // if it literally is just '>' or '' then allow anything. - if (!m[2]) { - this.semver = ANY - } else { - this.semver = new SemVer(m[2], this.options.loose) - } -} - -Comparator.prototype.toString = function () { - return this.value -} - -Comparator.prototype.test = function (version) { - debug('Comparator.test', version, this.options.loose) - - if (this.semver === ANY) { - return true - } - - if (typeof version === 'string') { - version = new SemVer(version, this.options) - } - - return cmp(version, this.operator, this.semver, this.options) -} - -Comparator.prototype.intersects = function (comp, options) { - if (!(comp instanceof Comparator)) { - throw new TypeError('a Comparator is required') - } - - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - var rangeTmp - - if (this.operator === '') { - rangeTmp = new Range(comp.value, options) - return satisfies(this.value, rangeTmp, options) - } else if (comp.operator === '') { - rangeTmp = new Range(this.value, options) - return satisfies(comp.semver, rangeTmp, options) - } - - var sameDirectionIncreasing = - (this.operator === '>=' || this.operator === '>') && - (comp.operator === '>=' || comp.operator === '>') - var sameDirectionDecreasing = - (this.operator === '<=' || this.operator === '<') && - (comp.operator === '<=' || comp.operator === '<') - var sameSemVer = this.semver.version === comp.semver.version - var differentDirectionsInclusive = - (this.operator === '>=' || this.operator === '<=') && - (comp.operator === '>=' || comp.operator === '<=') - var oppositeDirectionsLessThan = - cmp(this.semver, '<', comp.semver, options) && - ((this.operator === '>=' || this.operator === '>') && - (comp.operator === '<=' || comp.operator === '<')) - var oppositeDirectionsGreaterThan = - cmp(this.semver, '>', comp.semver, options) && - ((this.operator === '<=' || this.operator === '<') && - (comp.operator === '>=' || comp.operator === '>')) - - return sameDirectionIncreasing || sameDirectionDecreasing || - (sameSemVer && differentDirectionsInclusive) || - oppositeDirectionsLessThan || oppositeDirectionsGreaterThan -} - -exports.Range = Range -function Range (range, options) { - if (!options || typeof options !== 'object') { - options = { - loose: !!options, - includePrerelease: false - } - } - - if (range instanceof Range) { - if (range.loose === !!options.loose && - range.includePrerelease === !!options.includePrerelease) { - return range - } else { - return new Range(range.raw, options) - } - } - - if (range instanceof Comparator) { - return new Range(range.value, options) - } - - if (!(this instanceof Range)) { - return new Range(range, options) - } - - this.options = options - this.loose = !!options.loose - this.includePrerelease = !!options.includePrerelease - - // First, split based on boolean or || - this.raw = range - this.set = range.split(/\s*\|\|\s*/).map(function (range) { - return this.parseRange(range.trim()) - }, this).filter(function (c) { - // throw out any that are not relevant for whatever reason - return c.length - }) - - if (!this.set.length) { - throw new TypeError('Invalid SemVer Range: ' + range) - } - - this.format() -} - -Range.prototype.format = function () { - this.range = this.set.map(function (comps) { - return comps.join(' ').trim() - }).join('||').trim() - return this.range -} - -Range.prototype.toString = function () { - return this.range -} - -Range.prototype.parseRange = function (range) { - var loose = this.options.loose - range = range.trim() - // `1.2.3 - 1.2.4` => `>=1.2.3 <=1.2.4` - var hr = loose ? re[HYPHENRANGELOOSE] : re[HYPHENRANGE] - range = range.replace(hr, hyphenReplace) - debug('hyphen replace', range) - // `> 1.2.3 < 1.2.5` => `>1.2.3 <1.2.5` - range = range.replace(re[COMPARATORTRIM], comparatorTrimReplace) - debug('comparator trim', range, re[COMPARATORTRIM]) - - // `~ 1.2.3` => `~1.2.3` - range = range.replace(re[TILDETRIM], tildeTrimReplace) - - // `^ 1.2.3` => `^1.2.3` - range = range.replace(re[CARETTRIM], caretTrimReplace) - - // normalize spaces - range = range.split(/\s+/).join(' ') - - // At this point, the range is completely trimmed and - // ready to be split into comparators. - - var compRe = loose ? re[COMPARATORLOOSE] : re[COMPARATOR] - var set = range.split(' ').map(function (comp) { - return parseComparator(comp, this.options) - }, this).join(' ').split(/\s+/) - if (this.options.loose) { - // in loose mode, throw out any that are not valid comparators - set = set.filter(function (comp) { - return !!comp.match(compRe) - }) - } - set = set.map(function (comp) { - return new Comparator(comp, this.options) - }, this) - - return set -} - -Range.prototype.intersects = function (range, options) { - if (!(range instanceof Range)) { - throw new TypeError('a Range is required') - } - - return this.set.some(function (thisComparators) { - return thisComparators.every(function (thisComparator) { - return range.set.some(function (rangeComparators) { - return rangeComparators.every(function (rangeComparator) { - return thisComparator.intersects(rangeComparator, options) - }) - }) - }) - }) -} - -// Mostly just for testing and legacy API reasons -exports.toComparators = toComparators -function toComparators (range, options) { - return new Range(range, options).set.map(function (comp) { - return comp.map(function (c) { - return c.value - }).join(' ').trim().split(' ') - }) -} - -// comprised of xranges, tildes, stars, and gtlt's at this point. -// already replaced the hyphen ranges -// turn into a set of JUST comparators. -function parseComparator (comp, options) { - debug('comp', comp, options) - comp = replaceCarets(comp, options) - debug('caret', comp) - comp = replaceTildes(comp, options) - debug('tildes', comp) - comp = replaceXRanges(comp, options) - debug('xrange', comp) - comp = replaceStars(comp, options) - debug('stars', comp) - return comp -} - -function isX (id) { - return !id || id.toLowerCase() === 'x' || id === '*' -} - -// ~, ~> --> * (any, kinda silly) -// ~2, ~2.x, ~2.x.x, ~>2, ~>2.x ~>2.x.x --> >=2.0.0 <3.0.0 -// ~2.0, ~2.0.x, ~>2.0, ~>2.0.x --> >=2.0.0 <2.1.0 -// ~1.2, ~1.2.x, ~>1.2, ~>1.2.x --> >=1.2.0 <1.3.0 -// ~1.2.3, ~>1.2.3 --> >=1.2.3 <1.3.0 -// ~1.2.0, ~>1.2.0 --> >=1.2.0 <1.3.0 -function replaceTildes (comp, options) { - return comp.trim().split(/\s+/).map(function (comp) { - return replaceTilde(comp, options) - }).join(' ') -} - -function replaceTilde (comp, options) { - var r = options.loose ? re[TILDELOOSE] : re[TILDE] - return comp.replace(r, function (_, M, m, p, pr) { - debug('tilde', comp, _, M, m, p, pr) - var ret - - if (isX(M)) { - ret = '' - } else if (isX(m)) { - ret = '>=' + M + '.0.0 <' + (+M + 1) + '.0.0' - } else if (isX(p)) { - // ~1.2 == >=1.2.0 <1.3.0 - ret = '>=' + M + '.' + m + '.0 <' + M + '.' + (+m + 1) + '.0' - } else if (pr) { - debug('replaceTilde pr', pr) - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + M + '.' + (+m + 1) + '.0' - } else { - // ~1.2.3 == >=1.2.3 <1.3.0 - ret = '>=' + M + '.' + m + '.' + p + - ' <' + M + '.' + (+m + 1) + '.0' - } - - debug('tilde return', ret) - return ret - }) -} - -// ^ --> * (any, kinda silly) -// ^2, ^2.x, ^2.x.x --> >=2.0.0 <3.0.0 -// ^2.0, ^2.0.x --> >=2.0.0 <3.0.0 -// ^1.2, ^1.2.x --> >=1.2.0 <2.0.0 -// ^1.2.3 --> >=1.2.3 <2.0.0 -// ^1.2.0 --> >=1.2.0 <2.0.0 -function replaceCarets (comp, options) { - return comp.trim().split(/\s+/).map(function (comp) { - return replaceCaret(comp, options) - }).join(' ') -} - -function replaceCaret (comp, options) { - debug('caret', comp, options) - var r = options.loose ? re[CARETLOOSE] : re[CARET] - return comp.replace(r, function (_, M, m, p, pr) { - debug('caret', comp, _, M, m, p, pr) - var ret - - if (isX(M)) { - ret = '' - } else if (isX(m)) { - ret = '>=' + M + '.0.0 <' + (+M + 1) + '.0.0' - } else if (isX(p)) { - if (M === '0') { - ret = '>=' + M + '.' + m + '.0 <' + M + '.' + (+m + 1) + '.0' - } else { - ret = '>=' + M + '.' + m + '.0 <' + (+M + 1) + '.0.0' - } - } else if (pr) { - debug('replaceCaret pr', pr) - if (M === '0') { - if (m === '0') { - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + M + '.' + m + '.' + (+p + 1) - } else { - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + M + '.' + (+m + 1) + '.0' - } - } else { - ret = '>=' + M + '.' + m + '.' + p + '-' + pr + - ' <' + (+M + 1) + '.0.0' - } - } else { - debug('no pr') - if (M === '0') { - if (m === '0') { - ret = '>=' + M + '.' + m + '.' + p + - ' <' + M + '.' + m + '.' + (+p + 1) - } else { - ret = '>=' + M + '.' + m + '.' + p + - ' <' + M + '.' + (+m + 1) + '.0' - } - } else { - ret = '>=' + M + '.' + m + '.' + p + - ' <' + (+M + 1) + '.0.0' - } - } - - debug('caret return', ret) - return ret - }) -} - -function replaceXRanges (comp, options) { - debug('replaceXRanges', comp, options) - return comp.split(/\s+/).map(function (comp) { - return replaceXRange(comp, options) - }).join(' ') -} - -function replaceXRange (comp, options) { - comp = comp.trim() - var r = options.loose ? re[XRANGELOOSE] : re[XRANGE] - return comp.replace(r, function (ret, gtlt, M, m, p, pr) { - debug('xRange', comp, ret, gtlt, M, m, p, pr) - var xM = isX(M) - var xm = xM || isX(m) - var xp = xm || isX(p) - var anyX = xp - - if (gtlt === '=' && anyX) { - gtlt = '' - } - - if (xM) { - if (gtlt === '>' || gtlt === '<') { - // nothing is allowed - ret = '<0.0.0' - } else { - // nothing is forbidden - ret = '*' - } - } else if (gtlt && anyX) { - // we know patch is an x, because we have any x at all. - // replace X with 0 - if (xm) { - m = 0 - } - p = 0 - - if (gtlt === '>') { - // >1 => >=2.0.0 - // >1.2 => >=1.3.0 - // >1.2.3 => >= 1.2.4 - gtlt = '>=' - if (xm) { - M = +M + 1 - m = 0 - p = 0 - } else { - m = +m + 1 - p = 0 - } - } else if (gtlt === '<=') { - // <=0.7.x is actually <0.8.0, since any 0.7.x should - // pass. Similarly, <=7.x is actually <8.0.0, etc. - gtlt = '<' - if (xm) { - M = +M + 1 - } else { - m = +m + 1 - } - } - - ret = gtlt + M + '.' + m + '.' + p - } else if (xm) { - ret = '>=' + M + '.0.0 <' + (+M + 1) + '.0.0' - } else if (xp) { - ret = '>=' + M + '.' + m + '.0 <' + M + '.' + (+m + 1) + '.0' - } - - debug('xRange return', ret) - - return ret - }) -} - -// Because * is AND-ed with everything else in the comparator, -// and '' means "any version", just remove the *s entirely. -function replaceStars (comp, options) { - debug('replaceStars', comp, options) - // Looseness is ignored here. star is always as loose as it gets! - return comp.trim().replace(re[STAR], '') -} - -// This function is passed to string.replace(re[HYPHENRANGE]) -// M, m, patch, prerelease, build -// 1.2 - 3.4.5 => >=1.2.0 <=3.4.5 -// 1.2.3 - 3.4 => >=1.2.0 <3.5.0 Any 3.4.x will do -// 1.2 - 3.4 => >=1.2.0 <3.5.0 -function hyphenReplace ($0, - from, fM, fm, fp, fpr, fb, - to, tM, tm, tp, tpr, tb) { - if (isX(fM)) { - from = '' - } else if (isX(fm)) { - from = '>=' + fM + '.0.0' - } else if (isX(fp)) { - from = '>=' + fM + '.' + fm + '.0' - } else { - from = '>=' + from - } - - if (isX(tM)) { - to = '' - } else if (isX(tm)) { - to = '<' + (+tM + 1) + '.0.0' - } else if (isX(tp)) { - to = '<' + tM + '.' + (+tm + 1) + '.0' - } else if (tpr) { - to = '<=' + tM + '.' + tm + '.' + tp + '-' + tpr - } else { - to = '<=' + to - } - - return (from + ' ' + to).trim() -} - -// if ANY of the sets match ALL of its comparators, then pass -Range.prototype.test = function (version) { - if (!version) { - return false - } - - if (typeof version === 'string') { - version = new SemVer(version, this.options) - } - - for (var i = 0; i < this.set.length; i++) { - if (testSet(this.set[i], version, this.options)) { - return true - } - } - return false -} - -function testSet (set, version, options) { - for (var i = 0; i < set.length; i++) { - if (!set[i].test(version)) { - return false - } - } - - if (version.prerelease.length && !options.includePrerelease) { - // Find the set of versions that are allowed to have prereleases - // For example, ^1.2.3-pr.1 desugars to >=1.2.3-pr.1 <2.0.0 - // That should allow `1.2.3-pr.2` to pass. - // However, `1.2.4-alpha.notready` should NOT be allowed, - // even though it's within the range set by the comparators. - for (i = 0; i < set.length; i++) { - debug(set[i].semver) - if (set[i].semver === ANY) { - continue - } - - if (set[i].semver.prerelease.length > 0) { - var allowed = set[i].semver - if (allowed.major === version.major && - allowed.minor === version.minor && - allowed.patch === version.patch) { - return true - } - } - } - - // Version has a -pre, but it's not one of the ones we like. - return false - } - - return true -} - -exports.satisfies = satisfies -function satisfies (version, range, options) { - try { - range = new Range(range, options) - } catch (er) { - return false - } - return range.test(version) -} - -exports.maxSatisfying = maxSatisfying -function maxSatisfying (versions, range, options) { - var max = null - var maxSV = null - try { - var rangeObj = new Range(range, options) - } catch (er) { - return null - } - versions.forEach(function (v) { - if (rangeObj.test(v)) { - // satisfies(v, range, options) - if (!max || maxSV.compare(v) === -1) { - // compare(max, v, true) - max = v - maxSV = new SemVer(max, options) - } - } - }) - return max -} - -exports.minSatisfying = minSatisfying -function minSatisfying (versions, range, options) { - var min = null - var minSV = null - try { - var rangeObj = new Range(range, options) - } catch (er) { - return null - } - versions.forEach(function (v) { - if (rangeObj.test(v)) { - // satisfies(v, range, options) - if (!min || minSV.compare(v) === 1) { - // compare(min, v, true) - min = v - minSV = new SemVer(min, options) - } - } - }) - return min -} - -exports.minVersion = minVersion -function minVersion (range, loose) { - range = new Range(range, loose) - - var minver = new SemVer('0.0.0') - if (range.test(minver)) { - return minver - } - - minver = new SemVer('0.0.0-0') - if (range.test(minver)) { - return minver - } - - minver = null - for (var i = 0; i < range.set.length; ++i) { - var comparators = range.set[i] - - comparators.forEach(function (comparator) { - // Clone to avoid manipulating the comparator's semver object. - var compver = new SemVer(comparator.semver.version) - switch (comparator.operator) { - case '>': - if (compver.prerelease.length === 0) { - compver.patch++ - } else { - compver.prerelease.push(0) - } - compver.raw = compver.format() - /* fallthrough */ - case '': - case '>=': - if (!minver || gt(minver, compver)) { - minver = compver - } - break - case '<': - case '<=': - /* Ignore maximum versions */ - break - /* istanbul ignore next */ - default: - throw new Error('Unexpected operation: ' + comparator.operator) - } - }) - } - - if (minver && range.test(minver)) { - return minver - } - - return null -} - -exports.validRange = validRange -function validRange (range, options) { - try { - // Return '*' instead of '' so that truthiness works. - // This will throw if it's invalid anyway - return new Range(range, options).range || '*' - } catch (er) { - return null - } -} - -// Determine if version is less than all the versions possible in the range -exports.ltr = ltr -function ltr (version, range, options) { - return outside(version, range, '<', options) -} - -// Determine if version is greater than all the versions possible in the range. -exports.gtr = gtr -function gtr (version, range, options) { - return outside(version, range, '>', options) -} - -exports.outside = outside -function outside (version, range, hilo, options) { - version = new SemVer(version, options) - range = new Range(range, options) - - var gtfn, ltefn, ltfn, comp, ecomp - switch (hilo) { - case '>': - gtfn = gt - ltefn = lte - ltfn = lt - comp = '>' - ecomp = '>=' - break - case '<': - gtfn = lt - ltefn = gte - ltfn = gt - comp = '<' - ecomp = '<=' - break - default: - throw new TypeError('Must provide a hilo val of "<" or ">"') - } - - // If it satisifes the range it is not outside - if (satisfies(version, range, options)) { - return false - } - - // From now on, variable terms are as if we're in "gtr" mode. - // but note that everything is flipped for the "ltr" function. - - for (var i = 0; i < range.set.length; ++i) { - var comparators = range.set[i] - - var high = null - var low = null - - comparators.forEach(function (comparator) { - if (comparator.semver === ANY) { - comparator = new Comparator('>=0.0.0') - } - high = high || comparator - low = low || comparator - if (gtfn(comparator.semver, high.semver, options)) { - high = comparator - } else if (ltfn(comparator.semver, low.semver, options)) { - low = comparator - } - }) - - // If the edge version comparator has a operator then our version - // isn't outside it - if (high.operator === comp || high.operator === ecomp) { - return false - } - - // If the lowest version comparator has an operator and our version - // is less than it then it isn't higher than the range - if ((!low.operator || low.operator === comp) && - ltefn(version, low.semver)) { - return false - } else if (low.operator === ecomp && ltfn(version, low.semver)) { - return false - } - } - return true -} - -exports.prerelease = prerelease -function prerelease (version, options) { - var parsed = parse(version, options) - return (parsed && parsed.prerelease.length) ? parsed.prerelease : null -} - -exports.intersects = intersects -function intersects (r1, r2, options) { - r1 = new Range(r1, options) - r2 = new Range(r2, options) - return r1.intersects(r2) -} - -exports.coerce = coerce -function coerce (version) { - if (version instanceof SemVer) { - return version - } - - if (typeof version !== 'string') { - return null - } - - var match = version.match(re[COERCE]) - - if (match == null) { - return null - } - - return parse(match[1] + - '.' + (match[2] || '0') + - '.' + (match[3] || '0')) -} - - -/***/ }), - -/***/ "../../node_modules/write-json-file/node_modules/write-file-atomic/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -module.exports = writeFile -module.exports.sync = writeFileSync -module.exports._getTmpname = getTmpname // for testing -module.exports._cleanupOnExit = cleanupOnExit - -var fs = __webpack_require__("../../node_modules/graceful-fs/graceful-fs.js") -var MurmurHash3 = __webpack_require__("../../node_modules/imurmurhash/imurmurhash.js") -var onExit = __webpack_require__("../../node_modules/signal-exit/index.js") -var path = __webpack_require__("path") -var activeFiles = {} - -// if we run inside of a worker_thread, `process.pid` is not unique -/* istanbul ignore next */ -var threadId = (function getId () { - try { - var workerThreads = __webpack_require__("worker_threads") - - /// if we are in main thread, this is set to `0` - return workerThreads.threadId - } catch (e) { - // worker_threads are not available, fallback to 0 - return 0 - } -})() - -var invocations = 0 -function getTmpname (filename) { - return filename + '.' + - MurmurHash3(__filename) - .hash(String(process.pid)) - .hash(String(threadId)) - .hash(String(++invocations)) - .result() -} - -function cleanupOnExit (tmpfile) { - return function () { - try { - fs.unlinkSync(typeof tmpfile === 'function' ? tmpfile() : tmpfile) - } catch (_) {} - } -} - -function writeFile (filename, data, options, callback) { - if (options) { - if (options instanceof Function) { - callback = options - options = {} - } else if (typeof options === 'string') { - options = { encoding: options } - } - } else { - options = {} - } - - var Promise = options.Promise || global.Promise - var truename - var fd - var tmpfile - /* istanbul ignore next -- The closure only gets called when onExit triggers */ - var removeOnExitHandler = onExit(cleanupOnExit(() => tmpfile)) - var absoluteName = path.resolve(filename) - - new Promise(function serializeSameFile (resolve) { - // make a queue if it doesn't already exist - if (!activeFiles[absoluteName]) activeFiles[absoluteName] = [] - - activeFiles[absoluteName].push(resolve) // add this job to the queue - if (activeFiles[absoluteName].length === 1) resolve() // kick off the first one - }).then(function getRealPath () { - return new Promise(function (resolve) { - fs.realpath(filename, function (_, realname) { - truename = realname || filename - tmpfile = getTmpname(truename) - resolve() - }) - }) - }).then(function stat () { - return new Promise(function stat (resolve) { - if (options.mode && options.chown) resolve() - else { - // Either mode or chown is not explicitly set - // Default behavior is to copy it from original file - fs.stat(truename, function (err, stats) { - if (err || !stats) resolve() - else { - options = Object.assign({}, options) - - if (options.mode == null) { - options.mode = stats.mode - } - if (options.chown == null && process.getuid) { - options.chown = { uid: stats.uid, gid: stats.gid } - } - resolve() - } - }) - } - }) - }).then(function thenWriteFile () { - return new Promise(function (resolve, reject) { - fs.open(tmpfile, 'w', options.mode, function (err, _fd) { - fd = _fd - if (err) reject(err) - else resolve() - }) - }) - }).then(function write () { - return new Promise(function (resolve, reject) { - if (Buffer.isBuffer(data)) { - fs.write(fd, data, 0, data.length, 0, function (err) { - if (err) reject(err) - else resolve() - }) - } else if (data != null) { - fs.write(fd, String(data), 0, String(options.encoding || 'utf8'), function (err) { - if (err) reject(err) - else resolve() - }) - } else resolve() - }) - }).then(function syncAndClose () { - return new Promise(function (resolve, reject) { - if (options.fsync !== false) { - fs.fsync(fd, function (err) { - if (err) fs.close(fd, () => reject(err)) - else fs.close(fd, resolve) - }) - } else { - fs.close(fd, resolve) - } - }) - }).then(function chown () { - fd = null - if (options.chown) { - return new Promise(function (resolve, reject) { - fs.chown(tmpfile, options.chown.uid, options.chown.gid, function (err) { - if (err) reject(err) - else resolve() - }) - }) - } - }).then(function chmod () { - if (options.mode) { - return new Promise(function (resolve, reject) { - fs.chmod(tmpfile, options.mode, function (err) { - if (err) reject(err) - else resolve() - }) - }) - } - }).then(function rename () { - return new Promise(function (resolve, reject) { - fs.rename(tmpfile, truename, function (err) { - if (err) reject(err) - else resolve() - }) - }) - }).then(function success () { - removeOnExitHandler() - callback() - }, function fail (err) { - return new Promise(resolve => { - return fd ? fs.close(fd, resolve) : resolve() - }).then(() => { - removeOnExitHandler() - fs.unlink(tmpfile, function () { - callback(err) - }) - }) - }).then(function checkQueue () { - activeFiles[absoluteName].shift() // remove the element added by serializeSameFile - if (activeFiles[absoluteName].length > 0) { - activeFiles[absoluteName][0]() // start next job if one is pending - } else delete activeFiles[absoluteName] - }) -} - -function writeFileSync (filename, data, options) { - if (typeof options === 'string') options = { encoding: options } - else if (!options) options = {} - try { - filename = fs.realpathSync(filename) - } catch (ex) { - // it's ok, it'll happen on a not yet existing file - } - var tmpfile = getTmpname(filename) - - if (!options.mode || !options.chown) { - // Either mode or chown is not explicitly set - // Default behavior is to copy it from original file - try { - var stats = fs.statSync(filename) - options = Object.assign({}, options) - if (!options.mode) { - options.mode = stats.mode - } - if (!options.chown && process.getuid) { - options.chown = { uid: stats.uid, gid: stats.gid } - } - } catch (ex) { - // ignore stat errors - } - } - - var fd - var cleanup = cleanupOnExit(tmpfile) - var removeOnExitHandler = onExit(cleanup) - - try { - fd = fs.openSync(tmpfile, 'w', options.mode) - if (Buffer.isBuffer(data)) { - fs.writeSync(fd, data, 0, data.length, 0) - } else if (data != null) { - fs.writeSync(fd, String(data), 0, String(options.encoding || 'utf8')) - } - if (options.fsync !== false) { - fs.fsyncSync(fd) - } - fs.closeSync(fd) - if (options.chown) fs.chownSync(tmpfile, options.chown.uid, options.chown.gid) - if (options.mode) fs.chmodSync(tmpfile, options.mode) - fs.renameSync(tmpfile, filename) - removeOnExitHandler() - } catch (err) { - if (fd) { - try { - fs.closeSync(fd) - } catch (ex) { - // ignore close errors at this stage, error may have closed fd already. - } - } - removeOnExitHandler() - cleanup() - throw err - } -} - - -/***/ }), - -/***/ "../../node_modules/write-pkg/index.js": -/***/ (function(module, exports, __webpack_require__) { - -"use strict"; - -const path = __webpack_require__("path"); -const writeJsonFile = __webpack_require__("../../node_modules/write-json-file/index.js"); -const sortKeys = __webpack_require__("../../node_modules/sort-keys/index.js"); - -const dependencyKeys = new Set([ - 'dependencies', - 'devDependencies', - 'optionalDependencies', - 'peerDependencies' -]); - -function normalize(packageJson) { - const result = {}; - - for (const key of Object.keys(packageJson)) { - if (!dependencyKeys.has(key)) { - result[key] = packageJson[key]; - } else if (Object.keys(packageJson[key]).length !== 0) { - result[key] = sortKeys(packageJson[key]); - } - } - - return result; -} - -module.exports = async (filePath, data, options) => { - if (typeof filePath !== 'string') { - options = data; - data = filePath; - filePath = '.'; - } - - options = { - normalize: true, - ...options, - detectIndent: true - }; - - filePath = path.basename(filePath) === 'package.json' ? filePath : path.join(filePath, 'package.json'); - - data = options.normalize ? normalize(data) : data; - - return writeJsonFile(filePath, data, options); -}; - -module.exports.sync = (filePath, data, options) => { - if (typeof filePath !== 'string') { - options = data; - data = filePath; - filePath = '.'; - } - - options = { - normalize: true, - ...options, - detectIndent: true - }; - - filePath = path.basename(filePath) === 'package.json' ? filePath : path.join(filePath, 'package.json'); - - data = options.normalize ? normalize(data) : data; - - writeJsonFile.sync(filePath, data, options); -}; - - -/***/ }), - -/***/ "./src/cli.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return run; }); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/dedent/dist/dedent.js"); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(dedent__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var getopts__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/getopts/index.js"); -/* harmony import */ var getopts__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(getopts__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var _kbn_tooling_log__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/index.js"); -/* harmony import */ var _kbn_tooling_log__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(_kbn_tooling_log__WEBPACK_IMPORTED_MODULE_3__); -/* harmony import */ var _commands__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/commands/index.ts"); -/* harmony import */ var _run__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/run.ts"); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/utils/log.ts"); -/* - * 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. - */ - - - - - - - - -function help() { - _utils_log__WEBPACK_IMPORTED_MODULE_6__[/* log */ "a"].info(dedent__WEBPACK_IMPORTED_MODULE_0___default.a` - usage: kbn [] - - By default commands are run for Kibana itself, all packages in the 'packages/' - folder and for all plugins in './plugins' and '../kibana-extra'. - - Available commands: - - ${Object.values(_commands__WEBPACK_IMPORTED_MODULE_4__[/* commands */ "a"]).map(command => `${command.name} - ${command.description}`).join('\n ')} - - Global options: - - -e, --exclude Exclude specified project. Can be specified multiple times to exclude multiple projects, e.g. '-e kibana -e @kbn/pm'. - -i, --include Include only specified projects. If left unspecified, it defaults to including all projects. - --oss Do not include the x-pack when running command. - --skip-kibana-plugins Filter all plugins in ./plugins and ../kibana-extra when running command. - --no-cache Disable the kbn packages bootstrap cache - --no-validate Disable the bootstrap yarn.lock validation - --force-install Forces yarn install to run on bootstrap - --offline Run in offline mode - --verbose Set log level to verbose - --debug Set log level to debug - --quiet Set log level to error - --silent Disable log output - - "run" options: - --skip-missing Ignore packages which don't have the requested script - ` + '\n'); -} - -async function run(argv) { - _utils_log__WEBPACK_IMPORTED_MODULE_6__[/* log */ "a"].setLogLevel(Object(_kbn_tooling_log__WEBPACK_IMPORTED_MODULE_3__["pickLevelFromFlags"])(getopts__WEBPACK_IMPORTED_MODULE_1___default()(argv, { - boolean: ['verbose', 'debug', 'quiet', 'silent', 'skip-missing'] - }))); // We can simplify this setup (and remove this extra handling) once Yarn - // starts forwarding the `--` directly to this script, see - // https://github.com/yarnpkg/yarn/blob/b2d3e1a8fe45ef376b716d597cc79b38702a9320/src/cli/index.js#L174-L182 - - if (argv.includes('--')) { - _utils_log__WEBPACK_IMPORTED_MODULE_6__[/* log */ "a"].error(`Using "--" is not allowed, as it doesn't work with 'yarn kbn'.`); - process.exit(1); - } - - const options = getopts__WEBPACK_IMPORTED_MODULE_1___default()(argv, { - alias: { - e: 'exclude', - h: 'help', - i: 'include' - }, - default: { - cache: true, - 'force-install': false, - offline: false, - validate: true - }, - boolean: ['cache', 'force-install', 'offline', 'validate'] - }); - const args = options._; - - if (options.help || args.length === 0) { - help(); - return; - } // This `rootPath` is relative to `./dist/` as that's the location of the - // built version of this tool. - - - const rootPath = Object(path__WEBPACK_IMPORTED_MODULE_2__["resolve"])(__dirname, '../../../'); - const commandName = args[0]; - const extraArgs = args.slice(1); - const commandOptions = { - options, - extraArgs, - rootPath - }; - const command = _commands__WEBPACK_IMPORTED_MODULE_4__[/* commands */ "a"][commandName]; - - if (command === undefined) { - _utils_log__WEBPACK_IMPORTED_MODULE_6__[/* log */ "a"].error(`[${commandName}] is not a valid command, see 'kbn --help'`); - process.exit(1); - } - - await Object(_run__WEBPACK_IMPORTED_MODULE_5__[/* runCommand */ "a"])(command, commandOptions); -} - -/***/ }), - -/***/ "./src/commands/bootstrap.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return BootstrapCommand; }); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/@kbn/ci-stats-reporter/target_node/index.js"); -/* harmony import */ var _kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/@kbn/bazel-runner/target_node/index.js"); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/log.ts"); -/* harmony import */ var _utils_child_process__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/child_process.ts"); -/* harmony import */ var _utils_link_project_executables__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/link_project_executables.ts"); -/* harmony import */ var _utils_yarn_lock__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/utils/yarn_lock.ts"); -/* harmony import */ var _utils_validate_dependencies__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("./src/utils/validate_dependencies.ts"); -/* harmony import */ var _utils_bazel__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("./src/utils/bazel/index.ts"); -/* harmony import */ var _utils_bazel_setup_remote_cache__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__("./src/utils/bazel/setup_remote_cache.ts"); -function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; } - -function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; } - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -/* - * 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. - */ - - - - - - - - - - -const BootstrapCommand = { - description: 'Install dependencies and crosslink projects', - name: 'bootstrap', - reportTiming: { - group: 'scripts/kbn bootstrap', - id: 'total' - }, - - async run(projects, projectGraph, { - options, - kbn, - rootPath - }) { - var _projects$get; - - const kibanaProjectPath = ((_projects$get = projects.get('kibana')) === null || _projects$get === void 0 ? void 0 : _projects$get.path) || ''; - const offline = (options === null || options === void 0 ? void 0 : options.offline) === true; - const reporter = _kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_1__["CiStatsReporter"].fromEnv(_utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"]); - const timings = []; - - const time = async (id, body) => { - const start = Date.now(); - - try { - return await body(); - } finally { - timings.push({ - id, - ms: Date.now() - start - }); - } - }; // Force install is set in case a flag is passed into yarn kbn bootstrap or - // our custom logic have determined there is a chance node_modules have been manually deleted and as such bazel - // tracking mechanism is no longer valid - - - const forceInstall = !!options && options['force-install'] === true || (await Object(_utils_bazel__WEBPACK_IMPORTED_MODULE_8__[/* haveNodeModulesBeenManuallyDeleted */ "c"])(kibanaProjectPath)); // Install bazel machinery tools if needed - - await Object(_utils_bazel__WEBPACK_IMPORTED_MODULE_8__[/* installBazelTools */ "d"])(rootPath); // Setup remote cache settings in .bazelrc.cache if needed - - await Object(_utils_bazel_setup_remote_cache__WEBPACK_IMPORTED_MODULE_9__[/* setupRemoteCache */ "a"])(rootPath); // Bootstrap process for Bazel packages - // Bazel is now managing dependencies so yarn install - // will happen as part of this - // - // NOTE: Bazel projects will be introduced incrementally - // And should begin from the ones with none dependencies forward. - // That way non bazel projects could depend on bazel projects but not the other way around - // That is only intended during the migration process while non Bazel projects are not removed at all. - // - - if (forceInstall) { - await time('force install dependencies', async () => { - await Object(_utils_bazel__WEBPACK_IMPORTED_MODULE_8__[/* removeYarnIntegrityFileIfExists */ "f"])(path__WEBPACK_IMPORTED_MODULE_0___default.a.resolve(kibanaProjectPath, 'node_modules')); - await Object(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_2__["runBazel"])({ - bazelArgs: ['clean', '--expunge'], - log: _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"] - }); - await Object(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_2__["runBazel"])({ - bazelArgs: ['run', '@nodejs//:yarn'], - offline, - log: _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"], - execaOpts: { - env: { - SASS_BINARY_SITE: 'https://us-central1-elastic-kibana-184716.cloudfunctions.net/kibana-ci-proxy-cache/node-sass', - RE2_DOWNLOAD_MIRROR: 'https://us-central1-elastic-kibana-184716.cloudfunctions.net/kibana-ci-proxy-cache/node-re2' - } - } - }); - }); - } // build packages - - - await time('build packages', async () => { - await Object(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_2__["runBazel"])({ - bazelArgs: ['build', '//packages:build', '--show_result=1'], - log: _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"], - offline - }); - }); - const yarnLock = await time('read yarn.lock', async () => await Object(_utils_yarn_lock__WEBPACK_IMPORTED_MODULE_6__[/* readYarnLock */ "a"])(kbn)); - - if (options.validate) { - await time('validate dependencies', async () => { - await Object(_utils_validate_dependencies__WEBPACK_IMPORTED_MODULE_7__[/* validateDependencies */ "a"])(kbn, yarnLock); - }); - } // Assure all kbn projects with bin defined scripts - // copy those scripts into the top level node_modules folder - // - // NOTE: We don't probably need this anymore, is actually not being used - - - await time('link project executables', async () => { - await Object(_utils_link_project_executables__WEBPACK_IMPORTED_MODULE_5__[/* linkProjectExecutables */ "a"])(projects, projectGraph); - }); - await time('update vscode config', async () => { - // Update vscode settings - await Object(_utils_child_process__WEBPACK_IMPORTED_MODULE_4__[/* spawnStreaming */ "b"])(process.execPath, ['scripts/update_vscode_config'], { - cwd: kbn.getAbsolute(), - env: process.env - }, { - prefix: '[vscode]', - debug: false - }); - }); // send timings - - await reporter.timings({ - upstreamBranch: kbn.kibanaProject.json.branch, - // prevent loading @kbn/utils by passing null - kibanaUuid: kbn.getUuid() || null, - timings: timings.map(t => _objectSpread({ - group: 'scripts/kbn bootstrap' - }, t)) - }); - } - -}; - -/***/ }), - -/***/ "./src/commands/build.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return BuildCommand; }); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/@kbn/bazel-runner/target_node/index.js"); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/log.ts"); -/* - * 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. - */ - - -const BuildCommand = { - description: 'Runs a build in the Bazel built packages', - name: 'build', - reportTiming: { - group: 'scripts/kbn build', - id: 'total' - }, - - async run(projects, projectGraph, { - options - }) { - // Call bazel with the target to build all available packages - await Object(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0__["runBazel"])({ - bazelArgs: ['build', '//packages:build', '--show_result=1'], - log: _utils_log__WEBPACK_IMPORTED_MODULE_1__[/* log */ "a"], - offline: (options === null || options === void 0 ? void 0 : options.offline) === true - }); - } - -}; - -/***/ }), - -/***/ "./src/commands/clean.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return CleanCommand; }); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/dedent/dist/dedent.js"); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(dedent__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var del__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/del/index.js"); -/* harmony import */ var del__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(del__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var ora__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/ora/index.js"); -/* harmony import */ var ora__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(ora__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_3__); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/@kbn/bazel-runner/target_node/index.js"); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4__); -/* harmony import */ var _utils_bazel__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/bazel/index.ts"); -/* harmony import */ var _utils_fs__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/utils/fs.ts"); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("./src/utils/log.ts"); -/* - * 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. - */ - - - - - - - - -const CleanCommand = { - description: 'Deletes output directories and resets internal caches.', - name: 'clean', - reportTiming: { - group: 'scripts/kbn clean', - id: 'total' - }, - - async run(projects, projectGraph, { - kbn - }) { - _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].warning(dedent__WEBPACK_IMPORTED_MODULE_0___default.a` - This command is only necessary for the circumstance where you need to recover a consistent - state when problems arise. If you need to run this command often, please let us know by - filling out this form: https://ela.st/yarn-kbn-clean. - Please not it might not solve problems with node_modules. To solve problems around node_modules - you might need to run 'yarn kbn reset'. - `); - const toDelete = []; - - for (const project of projects.values()) { - if (await Object(_utils_fs__WEBPACK_IMPORTED_MODULE_6__[/* isDirectory */ "c"])(project.targetLocation)) { - toDelete.push({ - cwd: project.path, - pattern: Object(path__WEBPACK_IMPORTED_MODULE_3__["relative"])(project.path, project.targetLocation) - }); - } - - const { - extraPatterns - } = project.getCleanConfig(); - - if (extraPatterns) { - toDelete.push({ - cwd: project.path, - pattern: extraPatterns - }); - } - } // Runs Bazel soft clean - - - if (await Object(_utils_bazel__WEBPACK_IMPORTED_MODULE_5__[/* isBazelBinAvailable */ "e"])(kbn.getAbsolute())) { - await Object(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4__["runBazel"])({ - bazelArgs: ['clean'], - log: _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"] - }); - _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].success('Soft cleaned bazel'); - } - - if (toDelete.length === 0) { - _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].success('Nothing to delete'); - } else { - /** - * In order to avoid patterns like `/build` in packages from accidentally - * impacting files outside the package we use `process.chdir()` to change - * the cwd to the package and execute `del()` without the `force` option - * so it will check that each file being deleted is within the package. - * - * `del()` does support a `cwd` option, but it's only for resolving the - * patterns and does not impact the cwd check. - */ - const originalCwd = process.cwd(); - - try { - for (const { - pattern, - cwd - } of toDelete) { - process.chdir(cwd); - const promise = del__WEBPACK_IMPORTED_MODULE_1___default()(pattern); - - if (_utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].wouldLogLevel('info')) { - ora__WEBPACK_IMPORTED_MODULE_2___default.a.promise(promise, Object(path__WEBPACK_IMPORTED_MODULE_3__["relative"])(originalCwd, Object(path__WEBPACK_IMPORTED_MODULE_3__["join"])(cwd, String(pattern)))); - } - - await promise; - } - } finally { - process.chdir(originalCwd); - } - } - } - -}; - -/***/ }), - -/***/ "./src/commands/index.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return commands; }); -/* harmony import */ var _bootstrap__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("./src/commands/bootstrap.ts"); -/* harmony import */ var _build__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/commands/build.ts"); -/* harmony import */ var _clean__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("./src/commands/clean.ts"); -/* harmony import */ var _reset__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/commands/reset.ts"); -/* harmony import */ var _run__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/commands/run.ts"); -/* harmony import */ var _watch__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/commands/watch.ts"); -/* - * 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. - */ - - - - - - -const commands = { - bootstrap: _bootstrap__WEBPACK_IMPORTED_MODULE_0__[/* BootstrapCommand */ "a"], - build: _build__WEBPACK_IMPORTED_MODULE_1__[/* BuildCommand */ "a"], - clean: _clean__WEBPACK_IMPORTED_MODULE_2__[/* CleanCommand */ "a"], - reset: _reset__WEBPACK_IMPORTED_MODULE_3__[/* ResetCommand */ "a"], - run: _run__WEBPACK_IMPORTED_MODULE_4__[/* RunCommand */ "a"], - watch: _watch__WEBPACK_IMPORTED_MODULE_5__[/* WatchCommand */ "a"] -}; - -/***/ }), - -/***/ "./src/commands/reset.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return ResetCommand; }); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/dedent/dist/dedent.js"); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(dedent__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var del__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/del/index.js"); -/* harmony import */ var del__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(del__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var ora__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/ora/index.js"); -/* harmony import */ var ora__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(ora__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_3__); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("../../node_modules/@kbn/bazel-runner/target_node/index.js"); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4__); -/* harmony import */ var _utils_bazel__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/bazel/index.ts"); -/* harmony import */ var _utils_fs__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/utils/fs.ts"); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("./src/utils/log.ts"); -/* - * 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. - */ - - - - - - - - -const ResetCommand = { - description: 'Deletes node_modules and output directories, resets internal and disk caches, and stops Bazel server', - name: 'reset', - reportTiming: { - group: 'scripts/kbn reset', - id: 'total' - }, - - async run(projects, projectGraph, { - kbn - }) { - _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].warning(dedent__WEBPACK_IMPORTED_MODULE_0___default.a` - In most cases, 'yarn kbn clean' is all that should be needed to recover a consistent state when - problems arise. However for the rare cases where something get corrupt on node_modules you might need this command. - If you think you need to use this command very often (which is not normal), please let us know. - `); - const toDelete = []; - - for (const project of projects.values()) { - if (await Object(_utils_fs__WEBPACK_IMPORTED_MODULE_6__[/* isDirectory */ "c"])(project.nodeModulesLocation)) { - toDelete.push({ - cwd: project.path, - pattern: Object(path__WEBPACK_IMPORTED_MODULE_3__["relative"])(project.path, project.nodeModulesLocation) - }); - } - - if (await Object(_utils_fs__WEBPACK_IMPORTED_MODULE_6__[/* isDirectory */ "c"])(project.targetLocation)) { - toDelete.push({ - cwd: project.path, - pattern: Object(path__WEBPACK_IMPORTED_MODULE_3__["relative"])(project.path, project.targetLocation) - }); - } - - const { - extraPatterns - } = project.getCleanConfig(); - - if (extraPatterns) { - toDelete.push({ - cwd: project.path, - pattern: extraPatterns - }); - } - } // Runs Bazel hard clean and deletes Bazel Cache Folders - - - if (await Object(_utils_bazel__WEBPACK_IMPORTED_MODULE_5__[/* isBazelBinAvailable */ "e"])(kbn.getAbsolute())) { - // Hard cleaning bazel - await Object(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_4__["runBazel"])({ - bazelArgs: ['clean', '--expunge'], - log: _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"] - }); - _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].success('Hard cleaned bazel'); // Deletes Bazel Cache Folders - - await del__WEBPACK_IMPORTED_MODULE_1___default()([await Object(_utils_bazel__WEBPACK_IMPORTED_MODULE_5__[/* getBazelDiskCacheFolder */ "a"])(), await Object(_utils_bazel__WEBPACK_IMPORTED_MODULE_5__[/* getBazelRepositoryCacheFolder */ "b"])()], { - force: true - }); - _utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].success('Removed disk caches'); - } - - if (toDelete.length === 0) { - return; - } - /** - * In order to avoid patterns like `/build` in packages from accidentally - * impacting files outside the package we use `process.chdir()` to change - * the cwd to the package and execute `del()` without the `force` option - * so it will check that each file being deleted is within the package. - * - * `del()` does support a `cwd` option, but it's only for resolving the - * patterns and does not impact the cwd check. - */ - - - const originalCwd = process.cwd(); - - try { - for (const { - pattern, - cwd - } of toDelete) { - process.chdir(cwd); - const promise = del__WEBPACK_IMPORTED_MODULE_1___default()(pattern); - - if (_utils_log__WEBPACK_IMPORTED_MODULE_7__[/* log */ "a"].wouldLogLevel('info')) { - ora__WEBPACK_IMPORTED_MODULE_2___default.a.promise(promise, Object(path__WEBPACK_IMPORTED_MODULE_3__["relative"])(originalCwd, Object(path__WEBPACK_IMPORTED_MODULE_3__["join"])(cwd, String(pattern)))); - } - - await promise; - } - } finally { - process.chdir(originalCwd); - } - } - -}; - -/***/ }), - -/***/ "./src/commands/run.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return RunCommand; }); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/dedent/dist/dedent.js"); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(dedent__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _utils_errors__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/errors.ts"); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("./src/utils/log.ts"); -/* harmony import */ var _utils_parallelize__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/parallelize.ts"); -/* harmony import */ var _utils_projects__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/projects.ts"); -/* - * 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. - */ - - - - - -const RunCommand = { - description: 'Run script defined in package.json in each package that contains that script (only works on packages not using Bazel yet)', - name: 'run', - reportTiming: { - group: 'scripts/kbn run', - id: 'total' - }, - - async run(projects, projectGraph, { - extraArgs, - options - }) { - _utils_log__WEBPACK_IMPORTED_MODULE_2__[/* log */ "a"].warning(dedent__WEBPACK_IMPORTED_MODULE_0___default.a` - We are migrating packages into the Bazel build system and we will no longer support running npm scripts on - packages using 'yarn kbn run' on Bazel built packages. If the package you are trying to act on contains a - BUILD.bazel file please just use 'yarn kbn build' to build it or 'yarn kbn watch' to watch it - `); - const batchedProjects = Object(_utils_projects__WEBPACK_IMPORTED_MODULE_4__[/* topologicallyBatchProjects */ "d"])(projects, projectGraph); - - if (extraArgs.length === 0) { - throw new _utils_errors__WEBPACK_IMPORTED_MODULE_1__[/* CliError */ "a"]('No script specified'); - } - - const scriptName = extraArgs[0]; - const scriptArgs = extraArgs.slice(1); - await Object(_utils_parallelize__WEBPACK_IMPORTED_MODULE_3__[/* parallelizeBatches */ "a"])(batchedProjects, async project => { - if (!project.hasScript(scriptName)) { - if (!!options['skip-missing']) { - return; - } - - throw new _utils_errors__WEBPACK_IMPORTED_MODULE_1__[/* CliError */ "a"](`[${project.name}] no "${scriptName}" script defined. To skip packages without the "${scriptName}" script pass --skip-missing`); - } - - _utils_log__WEBPACK_IMPORTED_MODULE_2__[/* log */ "a"].info(`[${project.name}] running "${scriptName}" script`); - await project.runScriptStreaming(scriptName, { - args: scriptArgs - }); - _utils_log__WEBPACK_IMPORTED_MODULE_2__[/* log */ "a"].success(`[${project.name}] complete`); - }); - } - -}; - -/***/ }), - -/***/ "./src/commands/watch.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return WatchCommand; }); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/@kbn/bazel-runner/target_node/index.js"); -/* harmony import */ var _kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/log.ts"); -/* - * 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. - */ - - -const WatchCommand = { - description: 'Runs a build in the Bazel built packages and keeps watching them for changes', - name: 'watch', - reportTiming: { - group: 'scripts/kbn watch', - id: 'total' - }, - - async run(projects, projectGraph, { - options - }) { - const runOffline = (options === null || options === void 0 ? void 0 : options.offline) === true; // Call bazel with the target to build all available packages and run it through iBazel to watch it for changes - // - // Note: --run_output=false arg will disable the iBazel notifications about gazelle and buildozer when running it - // Can also be solved by adding a root `.bazel_fix_commands.json` but its not needed at the moment - - await Object(_kbn_bazel_runner__WEBPACK_IMPORTED_MODULE_0__["runIBazel"])({ - bazelArgs: ['--run_output=false', 'build', '//packages:build', '--show_result=1'], - log: _utils_log__WEBPACK_IMPORTED_MODULE_1__[/* log */ "a"], - offline: runOffline - }); - } - -}; - -/***/ }), - -/***/ "./src/config.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return getProjectPaths; }); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_0__); -/* - * 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. - */ - - -/** - * Returns all the paths where plugins are located - */ -function getProjectPaths({ - rootPath, - ossOnly, - skipKibanaPlugins -}) { - const projectPaths = [rootPath, Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'packages/*')]; // This is needed in order to install the dependencies for the declared - // plugin functional used in the selenium functional tests. - // As we are now using the webpack dll for the client vendors dependencies - // when we run the plugin functional tests against the distributable - // dependencies used by such plugins like @eui, react and react-dom can't - // be loaded from the dll as the context is different from the one declared - // into the webpack dll reference plugin. - // In anyway, have a plugin declaring their own dependencies is the - // correct and the expect behavior. - - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'test/plugin_functional/plugins/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'test/interpreter_functional/plugins/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'test/server_integration/__fixtures__/plugins/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'examples/*')); - - if (!ossOnly) { - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'x-pack')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'x-pack/plugins/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'x-pack/legacy/plugins/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'x-pack/test/functional_with_es_ssl/fixtures/plugins/*')); - } - - if (!skipKibanaPlugins) { - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, '../kibana-extra/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, '../kibana-extra/*/packages/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, '../kibana-extra/*/plugins/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'plugins/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'plugins/*/packages/*')); - projectPaths.push(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootPath, 'plugins/*/plugins/*')); - } - - return projectPaths; -} - -/***/ }), - -/***/ "./src/index.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -__webpack_require__.r(__webpack_exports__); -/* harmony import */ var _cli__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("./src/cli.ts"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "run", function() { return _cli__WEBPACK_IMPORTED_MODULE_0__["a"]; }); - -/* harmony import */ var _utils_projects__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/projects.ts"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "getProjects", function() { return _utils_projects__WEBPACK_IMPORTED_MODULE_1__["b"]; }); - -/* harmony import */ var _utils_project__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("./src/utils/project.ts"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "Project", function() { return _utils_project__WEBPACK_IMPORTED_MODULE_2__["a"]; }); - -/* harmony import */ var _config__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/config.ts"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "getProjectPaths", function() { return _config__WEBPACK_IMPORTED_MODULE_3__["a"]; }); - -/* - * 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. - */ - - - - - -/***/ }), - -/***/ "./src/run.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return runCommand; }); -/* harmony import */ var _kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/@kbn/ci-stats-reporter/target_node/index.js"); -/* harmony import */ var _kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _kbn_plugin_discovery__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/@kbn/plugin-discovery/target_node/index.js"); -/* harmony import */ var _kbn_plugin_discovery__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_kbn_plugin_discovery__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var _utils_errors__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("./src/utils/errors.ts"); -/* harmony import */ var _utils_log__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/log.ts"); -/* harmony import */ var _utils_projects__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/projects.ts"); -/* harmony import */ var _utils_projects_tree__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/projects_tree.ts"); -/* harmony import */ var _utils_regenerate_package_json__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/utils/regenerate_package_json.ts"); -/* harmony import */ var _utils_regenerate_synthetic_package_map__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("./src/utils/regenerate_synthetic_package_map.ts"); -/* harmony import */ var _utils_regenerate_base_tsconfig__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__("./src/utils/regenerate_base_tsconfig.ts"); -/* harmony import */ var _utils_kibana__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__("./src/utils/kibana.ts"); -function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; } - -function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; } - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -/* - * 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. - */ - - - - - - - - - - -process.env.CI_STATS_NESTED_TIMING = 'true'; -async function runCommand(command, config) { - const runStartTime = Date.now(); - let kbn; - const timings = []; - - async function time(id, block) { - const start = Date.now(); - let success = true; - - try { - return await block(); - } catch (error) { - success = false; - throw error; - } finally { - timings.push({ - id, - ms: Date.now() - start, - meta: { - success - } - }); - } - } - - async function reportTimes(timingConfig, error) { - if (!kbn) { - // things are too broken to report remotely - return; - } - - const reporter = _kbn_ci_stats_reporter__WEBPACK_IMPORTED_MODULE_0__["CiStatsReporter"].fromEnv(_utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"]); - - try { - await reporter.timings({ - upstreamBranch: kbn.kibanaProject.json.branch, - // prevent loading @kbn/utils by passing null - kibanaUuid: kbn.getUuid() || null, - timings: [...timings.map(t => _objectSpread(_objectSpread({}, timingConfig), t)), { - group: timingConfig.group, - id: timingConfig.id, - ms: Date.now() - runStartTime, - meta: { - success: !error - } - }] - }); - } catch (e) { - // prevent hiding bootstrap errors - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].error('failed to report timings:'); - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].error(e); - } - } - - try { - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].debug(`Running [${command.name}] command from [${config.rootPath}]`); - await time('regenerate package.json, synthetic-package map and tsconfig', async () => { - const plugins = Object(_kbn_plugin_discovery__WEBPACK_IMPORTED_MODULE_1__["simpleKibanaPlatformPluginDiscovery"])(Object(_kbn_plugin_discovery__WEBPACK_IMPORTED_MODULE_1__["getPluginSearchPaths"])({ - rootDir: config.rootPath, - oss: false, - examples: true, - testPlugins: true - }), []); - await Promise.all([Object(_utils_regenerate_package_json__WEBPACK_IMPORTED_MODULE_6__[/* regeneratePackageJson */ "a"])(config.rootPath), Object(_utils_regenerate_synthetic_package_map__WEBPACK_IMPORTED_MODULE_7__[/* regenerateSyntheticPackageMap */ "a"])(plugins, config.rootPath), Object(_utils_regenerate_base_tsconfig__WEBPACK_IMPORTED_MODULE_8__[/* regenerateBaseTsconfig */ "a"])(plugins, config.rootPath)]); - }); - kbn = await time('load Kibana project', async () => await _utils_kibana__WEBPACK_IMPORTED_MODULE_9__[/* Kibana */ "a"].loadFrom(config.rootPath)); - const projects = kbn.getFilteredProjects({ - skipKibanaPlugins: Boolean(config.options['skip-kibana-plugins']), - ossOnly: Boolean(config.options.oss), - exclude: toArray(config.options.exclude), - include: toArray(config.options.include) - }); - - if (projects.size === 0) { - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].error(`There are no projects found. Double check project name(s) in '-i/--include' and '-e/--exclude' filters.`); - return process.exit(1); - } - - const projectGraph = Object(_utils_projects__WEBPACK_IMPORTED_MODULE_4__[/* buildProjectGraph */ "a"])(projects); - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].debug(`Found ${projects.size.toString()} projects`); - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].debug(Object(_utils_projects_tree__WEBPACK_IMPORTED_MODULE_5__[/* renderProjectsTree */ "a"])(config.rootPath, projects)); - await command.run(projects, projectGraph, _objectSpread(_objectSpread({}, config), {}, { - kbn - })); - - if (command.reportTiming) { - await reportTimes(command.reportTiming); - } - } catch (error) { - if (command.reportTiming) { - await reportTimes(command.reportTiming, error); - } - - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].error(`[${command.name}] failed:`); - - if (error instanceof _utils_errors__WEBPACK_IMPORTED_MODULE_2__[/* CliError */ "a"]) { - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].error(error.message); - const metaOutput = Object.entries(error.meta).map(([key, value]) => `${key}: ${value}`).join('\n'); - - if (metaOutput) { - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].info('Additional debugging info:\n'); - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].indent(2); - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].info(metaOutput); - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].indent(-2); - } - } else { - _utils_log__WEBPACK_IMPORTED_MODULE_3__[/* log */ "a"].error(error); - } - - process.exit(1); - } -} - -function toArray(value) { - if (value == null) { - return []; - } - - return Array.isArray(value) ? value : [value]; -} - -/***/ }), - -/***/ "./src/utils/bazel/get_cache_folders.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return getBazelDiskCacheFolder; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return getBazelRepositoryCacheFolder; }); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _child_process__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/child_process.ts"); -/* - * 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. - */ - - - -async function rawRunBazelInfoRepoCache() { - const { - stdout: bazelRepositoryCachePath - } = await Object(_child_process__WEBPACK_IMPORTED_MODULE_1__[/* spawn */ "a"])('bazel', ['info', 'repository_cache'], { - stdio: 'pipe' - }); - return bazelRepositoryCachePath; -} - -async function getBazelDiskCacheFolder() { - return Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(Object(path__WEBPACK_IMPORTED_MODULE_0__["dirname"])(await rawRunBazelInfoRepoCache()), 'disk-cache'); -} -async function getBazelRepositoryCacheFolder() { - return await rawRunBazelInfoRepoCache(); -} - -/***/ }), - -/***/ "./src/utils/bazel/index.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony import */ var _get_cache_folders__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("./src/utils/bazel/get_cache_folders.ts"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "a", function() { return _get_cache_folders__WEBPACK_IMPORTED_MODULE_0__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "b", function() { return _get_cache_folders__WEBPACK_IMPORTED_MODULE_0__["b"]; }); - -/* harmony import */ var _install_tools__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/bazel/install_tools.ts"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "d", function() { return _install_tools__WEBPACK_IMPORTED_MODULE_1__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "e", function() { return _install_tools__WEBPACK_IMPORTED_MODULE_1__["b"]; }); - -/* harmony import */ var _yarn__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("./src/utils/bazel/yarn.ts"); -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "c", function() { return _yarn__WEBPACK_IMPORTED_MODULE_2__["a"]; }); - -/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, "f", function() { return _yarn__WEBPACK_IMPORTED_MODULE_2__["b"]; }); - -/* - * 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. - */ - - - - -/***/ }), - -/***/ "./src/utils/bazel/install_tools.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return isBazelBinAvailable; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return installBazelTools; }); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/dedent/dist/dedent.js"); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(dedent__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var _child_process__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("./src/utils/child_process.ts"); -/* harmony import */ var _fs__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/fs.ts"); -/* harmony import */ var _log__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/log.ts"); -/* - * 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. - */ - - - - - - -async function readBazelToolsVersionFile(repoRootPath, versionFilename) { - const version = (await Object(_fs__WEBPACK_IMPORTED_MODULE_3__[/* readFile */ "f"])(Object(path__WEBPACK_IMPORTED_MODULE_1__["resolve"])(repoRootPath, versionFilename))).toString().trim(); - - if (!version) { - throw new Error(`[bazel_tools] Failed on reading bazel tools versions\n ${versionFilename} file do not contain any version set`); - } - - return version; -} - -async function isBazelBinAvailable(repoRootPath) { - try { - const installedVersion = await Object(_child_process__WEBPACK_IMPORTED_MODULE_2__[/* spawn */ "a"])('bazel', ['--version'], { - stdio: 'pipe' - }); - const bazelVersion = await readBazelToolsVersionFile(repoRootPath, '.bazelversion'); - - if (installedVersion.stdout === `bazel ${bazelVersion}`) { - return true; - } else { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].info(`[bazel_tools] Bazel is installed (${installedVersion.stdout}), but was expecting ${bazelVersion}`); - return false; - } - } catch { - return false; - } -} - -async function tryRemoveBazeliskFromYarnGlobal() { - try { - // Check if Bazelisk is installed on the yarn global scope - const { - stdout: bazeliskPkgInstallStdout - } = await Object(_child_process__WEBPACK_IMPORTED_MODULE_2__[/* spawn */ "a"])('yarn', ['global', 'list'], { - stdio: 'pipe' - }); // Bazelisk was found on yarn global scope so lets remove it - - if (bazeliskPkgInstallStdout.includes(`@bazel/bazelisk@`)) { - await Object(_child_process__WEBPACK_IMPORTED_MODULE_2__[/* spawn */ "a"])('yarn', ['global', 'remove', `@bazel/bazelisk`], { - stdio: 'pipe' - }); - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].info(`[bazel_tools] bazelisk was installed on Yarn global packages and is now removed`); - return true; - } - - return false; - } catch { - return false; - } -} - -async function installBazelTools(repoRootPath) { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].debug(`[bazel_tools] reading bazel tools versions from version files`); - const bazeliskVersion = await readBazelToolsVersionFile(repoRootPath, '.bazeliskversion'); - const bazelVersion = await readBazelToolsVersionFile(repoRootPath, '.bazelversion'); // Check what globals are installed - - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].debug(`[bazel_tools] verify if bazelisk is installed`); // Check if we need to remove bazelisk from yarn - - await tryRemoveBazeliskFromYarnGlobal(); // Test if bazel bin is available - - const isBazelBinAlreadyAvailable = await isBazelBinAvailable(repoRootPath); // Install bazelisk if not installed - - if (!isBazelBinAlreadyAvailable) { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].info(`[bazel_tools] installing Bazel tools`); - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].debug(`[bazel_tools] bazelisk is not installed. Installing @bazel/bazelisk@${bazeliskVersion} and bazel@${bazelVersion}`); - await Object(_child_process__WEBPACK_IMPORTED_MODULE_2__[/* spawn */ "a"])('npm', ['install', '--global', `@bazel/bazelisk@${bazeliskVersion}`], { - env: { - USE_BAZEL_VERSION: bazelVersion - }, - stdio: 'pipe' - }); - const isBazelBinAvailableAfterInstall = await isBazelBinAvailable(repoRootPath); - - if (!isBazelBinAvailableAfterInstall) { - throw new Error(dedent__WEBPACK_IMPORTED_MODULE_0___default.a` - [bazel_tools] an error occurred when installing the Bazel tools. Please make sure you have access to npm globally installed modules on your $PATH - `); - } - } - - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].success(`[bazel_tools] all bazel tools are correctly installed`); -} - -/***/ }), - -/***/ "./src/utils/bazel/setup_remote_cache.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return setupRemoteCache; }); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/dedent/dist/dedent.js"); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(dedent__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("fs"); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(fs__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var _child_process__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/child_process.ts"); -/* harmony import */ var _log__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/log.ts"); -/* harmony import */ var _fs__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/fs.ts"); -/* - * 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. - */ - - - - - - - -async function isElasticCommitter() { - try { - const { - stdout: email - } = await Object(_child_process__WEBPACK_IMPORTED_MODULE_3__[/* spawn */ "a"])('git', ['config', 'user.email'], { - stdio: 'pipe' - }); - return email.trim().endsWith('@elastic.co'); - } catch { - return false; - } -} - -async function upToDate(settingsPath) { - if (!(await Object(_fs__WEBPACK_IMPORTED_MODULE_5__[/* isFile */ "d"])(settingsPath))) { - return false; - } - - const readSettingsFile = await Object(_fs__WEBPACK_IMPORTED_MODULE_5__[/* readFile */ "f"])(settingsPath, 'utf8'); - return readSettingsFile.startsWith('# V2 '); -} - -async function setupRemoteCache(repoRootPath) { - // The remote cache is only for Elastic employees working locally (CI cache settings are handled elsewhere) - if (process.env.FORCE_BOOTSTRAP_REMOTE_CACHE !== 'true' && (process.env.CI || !(await isElasticCommitter()))) { - return; - } - - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].debug(`[bazel_tools] setting up remote cache settings if necessary`); - const settingsPath = Object(path__WEBPACK_IMPORTED_MODULE_2__["resolve"])(repoRootPath, '.bazelrc.cache'); // Checks if we should upgrade or install the config file - - if (await upToDate(settingsPath)) { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].debug(`[bazel_tools] remote cache config already exists and is up-to-date, skipping`); - return; - } - - const contents = dedent__WEBPACK_IMPORTED_MODULE_0___default.a` - # V2 - This file is automatically generated by 'yarn kbn bootstrap' - # To regenerate this file, delete it and run 'yarn kbn bootstrap' again. - build --remote_cache=https://storage.googleapis.com/kibana-local-bazel-remote-cache - build --noremote_upload_local_results - build --incompatible_remote_results_ignore_disk - `; - Object(fs__WEBPACK_IMPORTED_MODULE_1__["writeFileSync"])(settingsPath, contents); - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].info(`[bazel_tools] remote cache settings written to ${settingsPath}`); -} - -/***/ }), - -/***/ "./src/utils/bazel/yarn.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return removeYarnIntegrityFileIfExists; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return haveNodeModulesBeenManuallyDeleted; }); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _fs__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/fs.ts"); -/* - * 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. - */ - - // yarn integrity file checker - -async function removeYarnIntegrityFileIfExists(nodeModulesPath) { - try { - const nodeModulesRealPath = await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* tryRealpath */ "g"])(nodeModulesPath); - const yarnIntegrityFilePath = Object(path__WEBPACK_IMPORTED_MODULE_0__["join"])(nodeModulesRealPath, '.yarn-integrity'); // check if the file exists and delete it in that case - - if (await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* isFile */ "d"])(yarnIntegrityFilePath)) { - await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* unlink */ "h"])(yarnIntegrityFilePath); - } - } catch {// no-op - } -} // yarn and bazel integration checkers - -async function areNodeModulesPresent(kbnRootPath) { - try { - return await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* isDirectory */ "c"])(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(kbnRootPath, 'node_modules')); - } catch { - return false; - } -} - -async function haveBazelFoldersBeenCreatedBefore(kbnRootPath) { - try { - return (await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* isDirectory */ "c"])(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(kbnRootPath, 'bazel-bin', 'packages'))) || (await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* isDirectory */ "c"])(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(kbnRootPath, 'bazel-kibana', 'packages'))) || (await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* isDirectory */ "c"])(Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(kbnRootPath, 'bazel-out', 'host'))); - } catch { - return false; - } -} - -async function haveNodeModulesBeenManuallyDeleted(kbnRootPath) { - return !(await areNodeModulesPresent(kbnRootPath)) && (await haveBazelFoldersBeenCreatedBefore(kbnRootPath)); -} - -/***/ }), - -/***/ "./src/utils/child_process.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return spawn; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return spawnStreaming; }); -/* harmony import */ var stream__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("stream"); -/* harmony import */ var stream__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(stream__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var chalk__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/chalk/source/index.js"); -/* harmony import */ var chalk__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(chalk__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var execa__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/execa/index.js"); -/* harmony import */ var execa__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(execa__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var strong_log_transformer__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/strong-log-transformer/index.js"); -/* harmony import */ var strong_log_transformer__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(strong_log_transformer__WEBPACK_IMPORTED_MODULE_3__); -/* harmony import */ var _log__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/log.ts"); -function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; } - -function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; } - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -/* - * 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. - */ - - - - - -const colorWheel = [chalk__WEBPACK_IMPORTED_MODULE_1___default.a.cyan, chalk__WEBPACK_IMPORTED_MODULE_1___default.a.magenta, chalk__WEBPACK_IMPORTED_MODULE_1___default.a.blue, chalk__WEBPACK_IMPORTED_MODULE_1___default.a.yellow, chalk__WEBPACK_IMPORTED_MODULE_1___default.a.green]; - -const getColor = () => { - const color = colorWheel.shift(); - colorWheel.push(color); - return color; -}; - -function spawn(command, args, opts) { - return execa__WEBPACK_IMPORTED_MODULE_2___default()(command, args, _objectSpread({ - stdio: 'inherit', - preferLocal: true - }, opts)); -} - -function streamToLog(debug = true) { - return new stream__WEBPACK_IMPORTED_MODULE_0__["Writable"]({ - objectMode: true, - - write(line, _, cb) { - if (line.endsWith('\n')) { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"][debug ? 'debug' : 'write'](line.slice(0, -1)); - } else { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"][debug ? 'debug' : 'write'](line); - } - - cb(); - } - - }); -} - -function spawnStreaming(command, args, opts, { - prefix, - debug -}) { - const spawned = execa__WEBPACK_IMPORTED_MODULE_2___default()(command, args, _objectSpread({ - stdio: ['ignore', 'pipe', 'pipe'], - preferLocal: true - }, opts)); - const color = getColor(); - const prefixedStdout = strong_log_transformer__WEBPACK_IMPORTED_MODULE_3___default()({ - tag: color.bold(prefix) - }); - const prefixedStderr = strong_log_transformer__WEBPACK_IMPORTED_MODULE_3___default()({ - mergeMultiline: true, - tag: color.bold(prefix) - }); - spawned.stdout.pipe(prefixedStdout).pipe(streamToLog(debug)); // TypeScript note: As long as the proc stdio[1] is 'pipe', then stdout will not be null - - spawned.stderr.pipe(prefixedStderr).pipe(streamToLog(debug)); // TypeScript note: As long as the proc stdio[2] is 'pipe', then stderr will not be null - - return spawned; -} - -/***/ }), - -/***/ "./src/utils/convert_plugin_id_to_package_id.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return convertPluginIdToPackageId; }); -/* - * 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. - */ -function convertPluginIdToPackageId(pluginId) { - if (pluginId === 'core') { - // core is the only non-plugin - return `@kbn/core`; - } - - return `@kbn/${pluginId.split('').flatMap(c => c.toUpperCase() === c ? `-${c.toLowerCase()}` : c).join('')}-plugin`.replace(/-\w(-\w)+-/g, match => `-${match.split('-').join('')}-`).replace(/-plugin-plugin$/, '-plugin'); -} - -/***/ }), - -/***/ "./src/utils/errors.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return CliError; }); -/* - * 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. - */ -class CliError extends Error { - constructor(message, meta = {}) { - super(message); - this.meta = meta; - } - -} - -/***/ }), - -/***/ "./src/utils/fs.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "f", function() { return readFile; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "i", function() { return writeFile; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return chmod; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "e", function() { return mkdirp; }); -/* unused harmony export rmdirp */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "h", function() { return unlink; }); -/* unused harmony export copyDirectory */ -/* unused harmony export isSymlink */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return isDirectory; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "d", function() { return isFile; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return createSymlink; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "g", function() { return tryRealpath; }); -/* harmony import */ var cmd_shim__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/cmd-shim/index.js"); -/* harmony import */ var cmd_shim__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(cmd_shim__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var del__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/del/index.js"); -/* harmony import */ var del__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(del__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("fs"); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(fs__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var ncp__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/ncp/lib/ncp.js"); -/* harmony import */ var ncp__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(ncp__WEBPACK_IMPORTED_MODULE_3__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_4__); -/* harmony import */ var util__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("util"); -/* harmony import */ var util__WEBPACK_IMPORTED_MODULE_5___default = /*#__PURE__*/__webpack_require__.n(util__WEBPACK_IMPORTED_MODULE_5__); -/* - * 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. - */ - - - - - - -const lstat = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.lstat); -const readFile = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.readFile); -const writeFile = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.writeFile); -const symlink = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.symlink); -const chmod = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.chmod); -const cmdShim = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(cmd_shim__WEBPACK_IMPORTED_MODULE_0___default.a); -const mkdir = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.mkdir); -const realpathNative = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.realpath.native); -const mkdirp = async path => await mkdir(path, { - recursive: true -}); -const rmdirp = async path => await del__WEBPACK_IMPORTED_MODULE_1___default()(path, { - force: true -}); -const unlink = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(fs__WEBPACK_IMPORTED_MODULE_2___default.a.unlink); -const copyDirectory = Object(util__WEBPACK_IMPORTED_MODULE_5__["promisify"])(ncp__WEBPACK_IMPORTED_MODULE_3__["ncp"]); - -async function statTest(path, block) { - try { - return block(await lstat(path)); - } catch (e) { - if (e.code === 'ENOENT') { - return false; - } - - throw e; - } -} -/** - * Test if a path points to a symlink. - * @param path - */ - - -async function isSymlink(path) { - return await statTest(path, stats => stats.isSymbolicLink()); -} -/** - * Test if a path points to a directory. - * @param path - */ - -async function isDirectory(path) { - return await statTest(path, stats => stats.isDirectory()); -} -/** - * Test if a path points to a regular file. - * @param path - */ - -async function isFile(path) { - return await statTest(path, stats => stats.isFile()); -} -/** - * Create a symlink at dest that points to src. Adapted from - * https://github.com/lerna/lerna/blob/2f1b87d9e2295f587e4ac74269f714271d8ed428/src/FileSystemUtilities.js#L103. - * - * @param src - * @param dest - * @param type 'dir', 'file', 'junction', or 'exec'. 'exec' on - * windows will use the `cmd-shim` module since symlinks can't be used - * for executable files on windows. - */ - -async function createSymlink(src, dest, type) { - if (process.platform === 'win32') { - if (type === 'exec') { - await cmdShim(src, dest); - } else { - await forceCreate(src, dest, type); - } - } else { - const posixType = type === 'exec' ? 'file' : type; - const relativeSource = Object(path__WEBPACK_IMPORTED_MODULE_4__["relative"])(Object(path__WEBPACK_IMPORTED_MODULE_4__["dirname"])(dest), src); - await forceCreate(relativeSource, dest, posixType); - } -} - -async function forceCreate(src, dest, type) { - try { - // If something exists at `dest` we need to remove it first. - await unlink(dest); - } catch (error) { - if (error.code !== 'ENOENT') { - throw error; - } - } - - await symlink(src, dest, type); -} - -async function tryRealpath(path) { - let calculatedPath = path; - - try { - calculatedPath = await realpathNative(path); - } catch (error) { - if (error.code !== 'ENOENT') { - throw error; - } - } - - return calculatedPath; -} - -/***/ }), - -/***/ "./src/utils/kibana.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Kibana; }); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("fs"); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(fs__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var multimatch__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/multimatch/index.js"); -/* harmony import */ var multimatch__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(multimatch__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var is_path_inside__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("../../node_modules/is-path-inside/index.js"); -/* harmony import */ var is_path_inside__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(is_path_inside__WEBPACK_IMPORTED_MODULE_3__); -/* harmony import */ var _yarn_lock__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/yarn_lock.ts"); -/* harmony import */ var _projects__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/projects.ts"); -/* harmony import */ var _config__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/config.ts"); -function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; } - -function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; } - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -/* - * 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. - */ - - - - - - - -/** - * Helper class for dealing with a set of projects as children of - * the Kibana project. The kbn/pm is currently implemented to be - * more generic, where everything is an operation of generic projects, - * but that leads to exceptions where we need the kibana project and - * do things like `project.get('kibana')!`. - * - * Using this helper we can restructre the generic list of projects - * as a Kibana object which encapulates all the projects in the - * workspace and knows about the root Kibana project. - */ - -class Kibana { - static async loadFrom(rootPath) { - return new Kibana(await Object(_projects__WEBPACK_IMPORTED_MODULE_5__[/* getProjects */ "b"])(rootPath, Object(_config__WEBPACK_IMPORTED_MODULE_6__[/* getProjectPaths */ "a"])({ - rootPath - }))); - } - - constructor(allWorkspaceProjects) { - this.allWorkspaceProjects = allWorkspaceProjects; - - _defineProperty(this, "kibanaProject", void 0); - - const kibanaProject = allWorkspaceProjects.get('kibana'); - - if (!kibanaProject) { - throw new TypeError('Unable to create Kibana object without all projects, including the Kibana project.'); - } - - this.kibanaProject = kibanaProject; - } - /** make an absolute path by resolving subPath relative to the kibana repo */ - - - getAbsolute(...subPath) { - return path__WEBPACK_IMPORTED_MODULE_0___default.a.resolve(this.kibanaProject.path, ...subPath); - } - /** convert an absolute path to a relative path, relative to the kibana repo */ - - - getRelative(absolute) { - return path__WEBPACK_IMPORTED_MODULE_0___default.a.relative(this.kibanaProject.path, absolute); - } - /** get a copy of the map of all projects in the kibana workspace */ - - - getAllProjects() { - return new Map(this.allWorkspaceProjects); - } - /** determine if a project with the given name exists */ - - - hasProject(name) { - return this.allWorkspaceProjects.has(name); - } - /** get a specific project, throws if the name is not known (use hasProject() first) */ - - - getProject(name) { - const project = this.allWorkspaceProjects.get(name); - - if (!project) { - throw new Error(`No package with name "${name}" in the workspace`); - } - - return project; - } - /** get a project and all of the projects it depends on in a ProjectMap */ - - - getProjectAndDeps(name) { - const project = this.getProject(name); - return Object(_projects__WEBPACK_IMPORTED_MODULE_5__[/* includeTransitiveProjects */ "c"])([project], this.allWorkspaceProjects); - } - /** filter the projects to just those matching certain paths/include/exclude tags */ - - - getFilteredProjects(options) { - const allProjects = this.getAllProjects(); - const filteredProjects = new Map(); - const pkgJsonPaths = Array.from(allProjects.values()).map(p => p.packageJsonLocation); - const filteredPkgJsonGlobs = Object(_config__WEBPACK_IMPORTED_MODULE_6__[/* getProjectPaths */ "a"])(_objectSpread(_objectSpread({}, options), {}, { - rootPath: this.kibanaProject.path - })).map(g => path__WEBPACK_IMPORTED_MODULE_0___default.a.resolve(g, 'package.json')); - const matchingPkgJsonPaths = multimatch__WEBPACK_IMPORTED_MODULE_2___default()(pkgJsonPaths, filteredPkgJsonGlobs); - - for (const project of allProjects.values()) { - const pathMatches = matchingPkgJsonPaths.includes(project.packageJsonLocation); - const notExcluded = !options.exclude.includes(project.name); - const isIncluded = !options.include.length || options.include.includes(project.name); - - if (pathMatches && notExcluded && isIncluded) { - filteredProjects.set(project.name, project); - } - } - - return filteredProjects; - } - - isPartOfRepo(project) { - return project.path === this.kibanaProject.path || is_path_inside__WEBPACK_IMPORTED_MODULE_3___default()(project.path, this.kibanaProject.path); - } - - isOutsideRepo(project) { - return !this.isPartOfRepo(project); - } - - resolveAllProductionDependencies(yarnLock, log) { - const kibanaDeps = Object(_yarn_lock__WEBPACK_IMPORTED_MODULE_4__[/* resolveDepsForProject */ "b"])({ - project: this.kibanaProject, - yarnLock, - kbn: this, - includeDependentProject: true, - productionDepsOnly: true, - log - }); - const xpackDeps = Object(_yarn_lock__WEBPACK_IMPORTED_MODULE_4__[/* resolveDepsForProject */ "b"])({ - project: this.getProject('x-pack'), - yarnLock, - kbn: this, - includeDependentProject: true, - productionDepsOnly: true, - log - }); - return new Map([...kibanaDeps.entries(), ...xpackDeps.entries()]); - } - - getUuid() { - try { - return fs__WEBPACK_IMPORTED_MODULE_1___default.a.readFileSync(this.getAbsolute('data/uuid'), 'utf-8').trim(); - } catch (error) { - if (error.code === 'ENOENT') { - return undefined; - } - - throw error; - } - } - -} - -/***/ }), - -/***/ "./src/utils/link_project_executables.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return linkProjectExecutables; }); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _fs__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/fs.ts"); -/* harmony import */ var _log__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("./src/utils/log.ts"); -/* - * 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. - */ - - - - -/** - * Yarn does not link the executables from dependencies that are installed - * using `link:` https://github.com/yarnpkg/yarn/pull/5046 - * - * We simulate this functionality by walking through each project's project - * dependencies, and manually linking their executables if defined. The logic - * for linking was mostly adapted from lerna: https://github.com/lerna/lerna/blob/1d7eb9eeff65d5a7de64dea73613b1bf6bfa8d57/src/PackageUtilities.js#L348 - */ -async function linkProjectExecutables(projectsByName, projectGraph) { - _log__WEBPACK_IMPORTED_MODULE_2__[/* log */ "a"].debug(`Linking package executables`); // Find root and generate executables from dependencies for it - - let rootProject = null; - let rootProjectDeps = []; - - for (const [projectName, projectDeps] of projectGraph) { - const project = projectsByName.get(projectName); - - if (project.isSinglePackageJsonProject) { - rootProject = projectsByName.get(projectName); - rootProjectDeps = projectDeps; - break; - } - } - - if (!rootProject) { - throw new Error('Could not finding root project while linking package executables'); - } // Prepare root project node_modules/.bin - - - const rootBinsDir = Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootProject.nodeModulesLocation, '.bin'); - - for (const rootProjectDep of rootProjectDeps) { - const executables = rootProjectDep.getExecutables(); - - for (const name of Object.keys(executables)) { - const srcPath = executables[name]; // existing logic from lerna -- ensure that the bin we are going to - // point to exists or ignore it - - if (!(await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* isFile */ "d"])(srcPath))) { - continue; - } - - const dest = Object(path__WEBPACK_IMPORTED_MODULE_0__["resolve"])(rootBinsDir, name); // Get relative project path with normalized path separators. - - const rootProjectRelativePath = Object(path__WEBPACK_IMPORTED_MODULE_0__["relative"])(rootProject.path, srcPath).split(path__WEBPACK_IMPORTED_MODULE_0__["sep"]).join('/'); - _log__WEBPACK_IMPORTED_MODULE_2__[/* log */ "a"].debug(`[${rootProject.name}] ${name} -> ${rootProjectRelativePath}`); - await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* mkdirp */ "e"])(Object(path__WEBPACK_IMPORTED_MODULE_0__["dirname"])(dest)); - await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* createSymlink */ "b"])(srcPath, dest, 'exec'); - await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* chmod */ "a"])(dest, '755'); - } - } -} - -/***/ }), - -/***/ "./src/utils/log.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return log; }); -/* unused harmony export Log */ -/* harmony import */ var _kbn_tooling_log__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/@kbn/tooling-log/target_node/index.js"); -/* harmony import */ var _kbn_tooling_log__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_kbn_tooling_log__WEBPACK_IMPORTED_MODULE_0__); -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -/* - * 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. - */ - - -class Log extends _kbn_tooling_log__WEBPACK_IMPORTED_MODULE_0__["ToolingLog"] { - constructor() { - super(); - - _defineProperty(this, "logLevel", void 0); - - this.setLogLevel('info'); - } - - setLogLevel(level) { - this.logLevel = Object(_kbn_tooling_log__WEBPACK_IMPORTED_MODULE_0__["parseLogLevel"])(level); - this.setWriters([new _kbn_tooling_log__WEBPACK_IMPORTED_MODULE_0__["ToolingLogTextWriter"]({ - level: this.logLevel.name, - writeTo: process.stdout - })]); - } - - wouldLogLevel(level) { - return this.logLevel.flags[level]; - } - -} - -const log = new Log(); - - -/***/ }), - -/***/ "./src/utils/package_json.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return readPackageJson; }); -/* unused harmony export writePackageJson */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return isLinkDependency; }); -/* harmony import */ var read_pkg__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/read-pkg/index.js"); -/* harmony import */ var read_pkg__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(read_pkg__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var write_pkg__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/write-pkg/index.js"); -/* harmony import */ var write_pkg__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(write_pkg__WEBPACK_IMPORTED_MODULE_1__); -/* - * 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. - */ - - -function readPackageJson(cwd) { - return read_pkg__WEBPACK_IMPORTED_MODULE_0___default()({ - cwd, - normalize: false - }); -} -function writePackageJson(path, json) { - return write_pkg__WEBPACK_IMPORTED_MODULE_1___default()(path, json); -} -const isLinkDependency = depVersion => depVersion.startsWith('link:'); - -/***/ }), - -/***/ "./src/utils/parallelize.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return parallelizeBatches; }); -/* unused harmony export parallelize */ -/* - * 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. - */ -async function parallelizeBatches(batches, fn) { - for (const batch of batches) { - // We need to make sure the entire batch has completed before we can move on - // to the next batch - await parallelize(batch, fn); - } -} -async function parallelize(items, fn, concurrency = 4) { - if (items.length === 0) { - return; - } - - return new Promise((resolve, reject) => { - let activePromises = 0; - const values = items.slice(0); - - async function scheduleItem(item) { - activePromises++; - - try { - await fn(item); - activePromises--; - - if (values.length > 0) { - // We have more work to do, so we schedule the next promise - scheduleItem(values.shift()); - } else if (activePromises === 0) { - // We have no more values left, and all items have completed, so we've - // completed all the work. - resolve(); - } - } catch (error) { - reject(error); - } - } - - values.splice(0, concurrency).map(scheduleItem); - }); -} - -/***/ }), - -/***/ "./src/utils/project.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return Project; }); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("fs"); -/* harmony import */ var fs__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(fs__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var util__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("util"); -/* harmony import */ var util__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(util__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var _errors__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/errors.ts"); -/* harmony import */ var _log__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/log.ts"); -/* harmony import */ var _package_json__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/package_json.ts"); -/* harmony import */ var _scripts__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/utils/scripts.ts"); -function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; } - -function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; } - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -/* - * 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. - */ - - - - - - - -class Project { - static async fromPath(path) { - const pkgJson = await Object(_package_json__WEBPACK_IMPORTED_MODULE_5__[/* readPackageJson */ "b"])(path); - return new Project(pkgJson, path); - } - /** parsed package.json */ - - - constructor(packageJson, projectPath) { - _defineProperty(this, "json", void 0); - - _defineProperty(this, "packageJsonLocation", void 0); - - _defineProperty(this, "nodeModulesLocation", void 0); - - _defineProperty(this, "targetLocation", void 0); - - _defineProperty(this, "path", void 0); - - _defineProperty(this, "version", void 0); - - _defineProperty(this, "allDependencies", void 0); - - _defineProperty(this, "productionDependencies", void 0); - - _defineProperty(this, "devDependencies", void 0); - - _defineProperty(this, "scripts", void 0); - - _defineProperty(this, "bazelPackage", void 0); - - _defineProperty(this, "isSinglePackageJsonProject", false); - - this.json = Object.freeze(packageJson); - this.path = projectPath; - this.packageJsonLocation = path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(this.path, 'package.json'); - this.nodeModulesLocation = path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(this.path, 'node_modules'); - this.targetLocation = path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(this.path, 'target'); - this.version = this.json.version; - this.productionDependencies = this.json.dependencies || {}; - this.devDependencies = this.json.devDependencies || {}; - this.allDependencies = _objectSpread(_objectSpread({}, this.devDependencies), this.productionDependencies); - this.isSinglePackageJsonProject = this.json.name === 'kibana'; - this.scripts = this.json.scripts || {}; - this.bazelPackage = !this.isSinglePackageJsonProject && fs__WEBPACK_IMPORTED_MODULE_0___default.a.existsSync(path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(this.path, 'BUILD.bazel')); - } - - get name() { - return this.json.name; - } - - getBuildConfig() { - return this.json.kibana && this.json.kibana.build || {}; - } - - getCleanConfig() { - return this.json.kibana && this.json.kibana.clean || {}; - } - - isBazelPackage() { - return this.bazelPackage; - } - - isFlaggedAsDevOnly() { - return !!(this.json.kibana && this.json.kibana.devOnly); - } - - hasScript(name) { - return name in this.scripts; - } - - getExecutables() { - const raw = this.json.bin; - - if (!raw) { - return {}; - } - - if (typeof raw === 'string') { - return { - [this.name]: path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(this.path, raw) - }; - } - - if (typeof raw === 'object') { - const binsConfig = {}; - - for (const binName of Object.keys(raw)) { - binsConfig[binName] = path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(this.path, raw[binName]); - } - - return binsConfig; - } - - throw new _errors__WEBPACK_IMPORTED_MODULE_3__[/* CliError */ "a"](`[${this.name}] has an invalid "bin" field in its package.json, ` + `expected an object or a string`, { - binConfig: Object(util__WEBPACK_IMPORTED_MODULE_2__["inspect"])(raw), - package: `${this.name} (${this.packageJsonLocation})` - }); - } - - async runScript(scriptName, args = []) { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].info(`Running script [${scriptName}] in [${this.name}]:`); - return Object(_scripts__WEBPACK_IMPORTED_MODULE_6__[/* runScriptInPackage */ "a"])(scriptName, args, this); - } - - runScriptStreaming(scriptName, options = {}) { - return Object(_scripts__WEBPACK_IMPORTED_MODULE_6__[/* runScriptInPackageStreaming */ "b"])({ - script: scriptName, - args: options.args || [], - pkg: this, - debug: options.debug - }); - } - - hasDependencies() { - return Object.keys(this.allDependencies).length > 0; - } - - isEveryDependencyLocal() { - return Object.values(this.allDependencies).every(dep => Object(_package_json__WEBPACK_IMPORTED_MODULE_5__[/* isLinkDependency */ "a"])(dep)); - } - -} - -/***/ }), - -/***/ "./src/utils/projects.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return getProjects; }); -/* unused harmony export getNonBazelProjectsOnly */ -/* unused harmony export getBazelProjectsOnly */ -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return buildProjectGraph; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "d", function() { return topologicallyBatchProjects; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return includeTransitiveProjects; }); -/* harmony import */ var glob__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/glob/glob.js"); -/* harmony import */ var glob__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(glob__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var util__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("util"); -/* harmony import */ var util__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(util__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var _errors__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/errors.ts"); -/* harmony import */ var _log__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/log.ts"); -/* harmony import */ var _project__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/project.ts"); -/* - * 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. - */ - - - - - - -const glob = Object(util__WEBPACK_IMPORTED_MODULE_2__["promisify"])(glob__WEBPACK_IMPORTED_MODULE_0___default.a); -/** a Map of project names to Project instances */ - -async function getProjects(rootPath, projectsPathsPatterns, { - include = [], - exclude = [] -} = {}, bazelOnly = false) { - const projects = new Map(); - - for (const pattern of projectsPathsPatterns) { - const pathsToProcess = await packagesFromGlobPattern({ - pattern, - rootPath - }); - - for (const filePath of pathsToProcess) { - const projectConfigPath = normalize(filePath); - const projectDir = path__WEBPACK_IMPORTED_MODULE_1___default.a.dirname(projectConfigPath); - const project = await _project__WEBPACK_IMPORTED_MODULE_5__[/* Project */ "a"].fromPath(projectDir); - const excludeProject = exclude.includes(project.name) || include.length > 0 && !include.includes(project.name) || bazelOnly && !project.isBazelPackage(); - - if (excludeProject) { - continue; - } - - if (projects.has(project.name)) { - throw new _errors__WEBPACK_IMPORTED_MODULE_3__[/* CliError */ "a"](`There are multiple projects with the same name [${project.name}]`, { - name: project.name, - paths: [project.path, projects.get(project.name).path] - }); - } - - projects.set(project.name, project); - } - } - - return projects; -} -async function getNonBazelProjectsOnly(projects) { - const bazelProjectsOnly = new Map(); - - for (const project of projects.values()) { - if (!project.isBazelPackage()) { - bazelProjectsOnly.set(project.name, project); - } - } - - return bazelProjectsOnly; -} -async function getBazelProjectsOnly(projects) { - const bazelProjectsOnly = new Map(); - - for (const project of projects.values()) { - if (project.isBazelPackage()) { - bazelProjectsOnly.set(project.name, project); - } - } - - return bazelProjectsOnly; -} - -function packagesFromGlobPattern({ - pattern, - rootPath -}) { - const globOptions = { - cwd: rootPath, - // Should throw in case of unusual errors when reading the file system - strict: true, - // Always returns absolute paths for matched files - absolute: true, - // Do not match ** against multiple filenames - // (This is only specified because we currently don't have a need for it.) - noglobstar: true - }; - return glob(path__WEBPACK_IMPORTED_MODULE_1___default.a.join(pattern, 'package.json'), globOptions); -} // https://github.com/isaacs/node-glob/blob/master/common.js#L104 -// glob always returns "\\" as "/" in windows, so everyone -// gets normalized because we can't have nice things. - - -function normalize(dir) { - return path__WEBPACK_IMPORTED_MODULE_1___default.a.normalize(dir); -} - -function buildProjectGraph(projects) { - const projectGraph = new Map(); - - for (const project of projects.values()) { - const projectDeps = []; - const dependencies = project.allDependencies; - - if (!project.isSinglePackageJsonProject && Object.keys(dependencies).length > 0) { - _log__WEBPACK_IMPORTED_MODULE_4__[/* log */ "a"].warning(`${project.name} is not allowed to hold local dependencies and they will be discarded. Please declare them at the root package.json`); - } - - if (!project.isSinglePackageJsonProject) { - projectGraph.set(project.name, projectDeps); - continue; - } - - for (const depName of Object.keys(dependencies)) { - if (projects.has(depName)) { - const dep = projects.get(depName); - projectDeps.push(dep); - } - } - - projectGraph.set(project.name, projectDeps); - } - - return projectGraph; -} -function topologicallyBatchProjects(projectsToBatch, projectGraph) { - // We're going to be chopping stuff out of this list, so copy it. - const projectsLeftToBatch = new Set(projectsToBatch.keys()); - const batches = []; - - while (projectsLeftToBatch.size > 0) { - // Get all projects that have no remaining dependencies within the repo - // that haven't yet been picked. - const batch = []; - - for (const projectName of projectsLeftToBatch) { - const projectDeps = projectGraph.get(projectName); - const needsDependenciesBatched = projectDeps.some(dep => projectsLeftToBatch.has(dep.name)); - - if (!needsDependenciesBatched) { - batch.push(projectsToBatch.get(projectName)); - } - } // If we weren't able to find a project with no remaining dependencies, - // then we've encountered a cycle in the dependency graph. - - - const hasCycles = batch.length === 0; - - if (hasCycles) { - const cycleProjectNames = [...projectsLeftToBatch]; - const message = 'Encountered a cycle in the dependency graph. Projects in cycle are:\n' + cycleProjectNames.join(', '); - throw new _errors__WEBPACK_IMPORTED_MODULE_3__[/* CliError */ "a"](message); - } - - batches.push(batch); - batch.forEach(project => projectsLeftToBatch.delete(project.name)); - } - - return batches; -} -function includeTransitiveProjects(subsetOfProjects, allProjects, { - onlyProductionDependencies = false -} = {}) { - const projectsWithDependents = new Map(); // the current list of packages we are expanding using breadth-first-search - - const toProcess = [...subsetOfProjects]; - - while (toProcess.length > 0) { - const project = toProcess.shift(); - const dependencies = onlyProductionDependencies ? project.productionDependencies : project.allDependencies; - Object.keys(dependencies).forEach(dep => { - if (allProjects.has(dep)) { - toProcess.push(allProjects.get(dep)); - } - }); - projectsWithDependents.set(project.name, project); - } - - return projectsWithDependents; -} - -/***/ }), - -/***/ "./src/utils/projects_tree.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return renderProjectsTree; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return treeToString; }); -/* harmony import */ var chalk__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/chalk/source/index.js"); -/* harmony import */ var chalk__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(chalk__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_1__); -/* - * 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. - */ - - -const projectKey = Symbol('__project'); -function renderProjectsTree(rootPath, projects) { - const projectsTree = buildProjectsTree(rootPath, projects); - return treeToString(createTreeStructure(projectsTree)); -} -function treeToString(tree) { - return [tree.name].concat(childrenToStrings(tree.children, '')).join('\n'); -} - -function childrenToStrings(tree, treePrefix) { - if (tree === undefined) { - return []; - } - - let strings = []; - tree.forEach((node, index) => { - const isLastNode = tree.length - 1 === index; - const nodePrefix = isLastNode ? '└── ' : '├── '; - const childPrefix = isLastNode ? ' ' : '│ '; - const childrenPrefix = treePrefix + childPrefix; - strings.push(`${treePrefix}${nodePrefix}${node.name}`); - strings = strings.concat(childrenToStrings(node.children, childrenPrefix)); - }); - return strings; -} - -function createTreeStructure(tree) { - let name; - const children = []; - - for (const [dir, project] of tree.entries()) { - // This is a leaf node (aka a project) - if (typeof project === 'string') { - name = chalk__WEBPACK_IMPORTED_MODULE_0___default.a.green(project); - continue; - } // If there's only one project and the key indicates it's a leaf node, we - // know that we're at a package folder that contains a package.json, so we - // "inline it" so we don't get unnecessary levels, i.e. we'll just see - // `foo` instead of `foo -> foo`. - - - if (project.size === 1 && project.has(projectKey)) { - const projectName = project.get(projectKey); - children.push({ - children: [], - name: dirOrProjectName(dir, projectName) - }); - continue; - } - - const subtree = createTreeStructure(project); // If the name is specified, we know there's a package at the "root" of the - // subtree itself. - - if (subtree.name !== undefined) { - const projectName = subtree.name; - children.push({ - children: subtree.children, - name: dirOrProjectName(dir, projectName) - }); - continue; - } // Special-case whenever we have one child, so we don't get unnecessary - // folders in the output. E.g. instead of `foo -> bar -> baz` we get - // `foo/bar/baz` instead. - - - if (subtree.children && subtree.children.length === 1) { - const child = subtree.children[0]; - const newName = chalk__WEBPACK_IMPORTED_MODULE_0___default.a.dim(path__WEBPACK_IMPORTED_MODULE_1___default.a.join(dir.toString(), child.name)); - children.push({ - children: child.children, - name: newName - }); - continue; - } - - children.push({ - children: subtree.children, - name: chalk__WEBPACK_IMPORTED_MODULE_0___default.a.dim(dir.toString()) - }); - } - - return { - name, - children - }; -} - -function dirOrProjectName(dir, projectName) { - return dir === projectName ? chalk__WEBPACK_IMPORTED_MODULE_0___default.a.green(dir) : chalk__WEBPACK_IMPORTED_MODULE_0___default.a`{dim ${dir.toString()} ({reset.green ${projectName}})}`; -} - -function buildProjectsTree(rootPath, projects) { - const tree = new Map(); - - for (const project of projects.values()) { - if (rootPath === project.path) { - tree.set(projectKey, project.name); - } else { - const relativeProjectPath = path__WEBPACK_IMPORTED_MODULE_1___default.a.relative(rootPath, project.path); - addProjectToTree(tree, relativeProjectPath.split(path__WEBPACK_IMPORTED_MODULE_1___default.a.sep), project); - } - } - - return tree; -} - -function addProjectToTree(tree, pathParts, project) { - if (pathParts.length === 0) { - tree.set(projectKey, project.name); - } else { - const [currentDir, ...rest] = pathParts; - - if (!tree.has(currentDir)) { - tree.set(currentDir, new Map()); - } - - const subtree = tree.get(currentDir); - addProjectToTree(subtree, rest, project); - } -} - -/***/ }), - -/***/ "./src/utils/regenerate_base_tsconfig.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return regenerateBaseTsconfig; }); -/* harmony import */ var fs_promises__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("fs/promises"); -/* harmony import */ var fs_promises__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(fs_promises__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var normalize_path__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/normalize-path/index.js"); -/* harmony import */ var normalize_path__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(normalize_path__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var _convert_plugin_id_to_package_id__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/convert_plugin_id_to_package_id.ts"); -/* - * 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. - */ - - - - -async function regenerateBaseTsconfig(plugins, repoRoot) { - const tsconfigPath = path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(repoRoot, 'tsconfig.base.json'); - const lines = (await fs_promises__WEBPACK_IMPORTED_MODULE_0___default.a.readFile(tsconfigPath, 'utf-8')).split('\n'); - const packageMap = plugins.slice().sort((a, b) => a.manifestPath.localeCompare(b.manifestPath)).flatMap(p => { - const id = Object(_convert_plugin_id_to_package_id__WEBPACK_IMPORTED_MODULE_3__[/* convertPluginIdToPackageId */ "a"])(p.manifest.id); - const path = normalize_path__WEBPACK_IMPORTED_MODULE_2___default()(path__WEBPACK_IMPORTED_MODULE_1___default.a.relative(repoRoot, p.directory)); - return [` "${id}": ["${path}"],`, ` "${id}/*": ["${path}/*"],`]; - }); - const start = lines.findIndex(l => l.trim() === '// START AUTOMATED PACKAGE LISTING'); - const end = lines.findIndex(l => l.trim() === '// END AUTOMATED PACKAGE LISTING'); - await fs_promises__WEBPACK_IMPORTED_MODULE_0___default.a.writeFile(tsconfigPath, [...lines.slice(0, start + 1), ...packageMap, ...lines.slice(end)].join('\n')); -} - -/***/ }), - -/***/ "./src/utils/regenerate_package_json.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return regeneratePackageJson; }); -/* harmony import */ var fs_promises__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("fs/promises"); -/* harmony import */ var fs_promises__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(fs_promises__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var _kbn_sort_package_json__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/@kbn/sort-package-json/target_node/index.js"); -/* harmony import */ var _kbn_sort_package_json__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(_kbn_sort_package_json__WEBPACK_IMPORTED_MODULE_2__); -/* - * 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. - */ - - - -async function regeneratePackageJson(rootPath) { - const path = path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(rootPath, 'package.json'); - const json = await fs_promises__WEBPACK_IMPORTED_MODULE_0___default.a.readFile(path, 'utf8'); - await fs_promises__WEBPACK_IMPORTED_MODULE_0___default.a.writeFile(path, Object(_kbn_sort_package_json__WEBPACK_IMPORTED_MODULE_2__["sortPackageJson"])(json)); -} - -/***/ }), - -/***/ "./src/utils/regenerate_synthetic_package_map.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return regenerateSyntheticPackageMap; }); -/* harmony import */ var fs_promises__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("fs/promises"); -/* harmony import */ var fs_promises__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(fs_promises__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var normalize_path__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/normalize-path/index.js"); -/* harmony import */ var normalize_path__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(normalize_path__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var _convert_plugin_id_to_package_id__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("./src/utils/convert_plugin_id_to_package_id.ts"); -/* - * 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. - */ - - - - -async function regenerateSyntheticPackageMap(plugins, repoRoot) { - const entries = [['@kbn/core', 'src/core']]; - - for (const plugin of plugins) { - entries.push([Object(_convert_plugin_id_to_package_id__WEBPACK_IMPORTED_MODULE_3__[/* convertPluginIdToPackageId */ "a"])(plugin.manifest.id), normalize_path__WEBPACK_IMPORTED_MODULE_2___default()(path__WEBPACK_IMPORTED_MODULE_1___default.a.relative(repoRoot, plugin.directory))]); - } - - await fs_promises__WEBPACK_IMPORTED_MODULE_0___default.a.writeFile(path__WEBPACK_IMPORTED_MODULE_1___default.a.resolve(repoRoot, 'packages/kbn-synthetic-package-map/synthetic-packages.json'), JSON.stringify(entries, null, 2)); -} - -/***/ }), - -/***/ "./src/utils/scripts.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return runScriptInPackage; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return runScriptInPackageStreaming; }); -/* harmony import */ var _child_process__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("./src/utils/child_process.ts"); -/* - * 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. - */ - -const YARN_EXEC = process.env.npm_execpath || 'yarn'; -/** - * Run script in the given directory - */ - -async function runScriptInPackage(script, args, pkg) { - const execOpts = { - cwd: pkg.path - }; - await Object(_child_process__WEBPACK_IMPORTED_MODULE_0__[/* spawn */ "a"])(YARN_EXEC, ['run', script, ...args], execOpts); -} -/** - * Run script in the given directory - */ - -function runScriptInPackageStreaming({ - script, - args, - pkg, - debug -}) { - const execOpts = { - cwd: pkg.path - }; - return Object(_child_process__WEBPACK_IMPORTED_MODULE_0__[/* spawnStreaming */ "b"])(YARN_EXEC, ['run', script, ...args], execOpts, { - prefix: pkg.name, - debug - }); -} - -/***/ }), - -/***/ "./src/utils/validate_dependencies.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return validateDependencies; }); -/* harmony import */ var _yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/@yarnpkg/lockfile/index.js"); -/* harmony import */ var _yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("../../node_modules/dedent/dist/dedent.js"); -/* harmony import */ var dedent__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(dedent__WEBPACK_IMPORTED_MODULE_1__); -/* harmony import */ var chalk__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__("../../node_modules/chalk/source/index.js"); -/* harmony import */ var chalk__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(chalk__WEBPACK_IMPORTED_MODULE_2__); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__("path"); -/* harmony import */ var path__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(path__WEBPACK_IMPORTED_MODULE_3__); -/* harmony import */ var _fs__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__("./src/utils/fs.ts"); -/* harmony import */ var _log__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__("./src/utils/log.ts"); -/* harmony import */ var _package_json__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__("./src/utils/package_json.ts"); -/* harmony import */ var _projects_tree__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__("./src/utils/projects_tree.ts"); -/* - * 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. - */ -// @ts-expect-error published types are useless - - - - - - - - -async function validateDependencies(kbn, yarnLock) { - // look through all of the packages in the yarn.lock file to see if - // we have accidentally installed multiple lodash v4 versions - const lodash4Versions = new Set(); - const lodash4Reqs = new Set(); - - for (const [req, dep] of Object.entries(yarnLock)) { - if (req.startsWith('lodash@') && dep.version.startsWith('4.')) { - lodash4Reqs.add(req); - lodash4Versions.add(dep.version); - } - } // if we find more than one lodash v4 version installed then delete - // lodash v4 requests from the yarn.lock file and prompt the user to - // retry bootstrap so that a single v4 version will be installed - - - if (lodash4Versions.size > 1) { - for (const req of lodash4Reqs) { - delete yarnLock[req]; - } - - await Object(_fs__WEBPACK_IMPORTED_MODULE_4__[/* writeFile */ "i"])(kbn.getAbsolute('yarn.lock'), Object(_yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0__["stringify"])(yarnLock), 'utf8'); - _log__WEBPACK_IMPORTED_MODULE_5__[/* log */ "a"].error(dedent__WEBPACK_IMPORTED_MODULE_1___default.a` - - Multiple version of lodash v4 were detected, so they have been removed - from the yarn.lock file. Please rerun yarn kbn bootstrap to coalese the - lodash versions installed. - - If you still see this error when you re-bootstrap then you might need - to force a new dependency to use the latest version of lodash via the - "resolutions" field in package.json. - - If you have questions about this please reach out to the operations team. - - `); - process.exit(1); - } // look through all the dependencies of production packages and production - // dependencies of those packages to determine if we're shipping any versions - // of lodash v3 in the distributable - - - const prodDependencies = kbn.resolveAllProductionDependencies(yarnLock, _log__WEBPACK_IMPORTED_MODULE_5__[/* log */ "a"]); - const lodash3Versions = new Set(); - - for (const dep of prodDependencies.values()) { - if (dep.name === 'lodash' && dep.version.startsWith('3.')) { - lodash3Versions.add(dep.version); - } - } // if any lodash v3 packages were found we abort and tell the user to fix things - - - if (lodash3Versions.size) { - _log__WEBPACK_IMPORTED_MODULE_5__[/* log */ "a"].error(dedent__WEBPACK_IMPORTED_MODULE_1___default.a` - - Due to changes in the yarn.lock file and/or package.json files a version of - lodash 3 is now included in the production dependencies. To reduce the size of - our distributable and especially our front-end bundles we have decided to - prevent adding any new instances of lodash 3. - - Please inspect the changes to yarn.lock or package.json files to identify where - the lodash 3 version is coming from and remove it. - - If you have questions about this please reack out to the operations team. - - `); - process.exit(1); - } // TODO: remove this once we move into a single package.json - // look through all the package.json files to find packages which have mismatched version ranges - - - const depRanges = new Map(); - - for (const project of kbn.getAllProjects().values()) { - var _kbn$kibanaProject; - - // Skip if this is an external plugin - if (project.path.includes(`${(_kbn$kibanaProject = kbn.kibanaProject) === null || _kbn$kibanaProject === void 0 ? void 0 : _kbn$kibanaProject.path}${path__WEBPACK_IMPORTED_MODULE_3__["sep"]}plugins`)) { - continue; - } - - for (const [dep, range] of Object.entries(project.allDependencies)) { - const existingDep = depRanges.get(dep); - - if (!existingDep) { - depRanges.set(dep, [{ - range, - projects: [project] - }]); - continue; - } - - const existingRange = existingDep.find(existing => existing.range === range); - - if (!existingRange) { - existingDep.push({ - range, - projects: [project] - }); - continue; - } - - existingRange.projects.push(project); - } - } - - const duplicateRanges = Array.from(depRanges.entries()).filter(([, ranges]) => ranges.length > 1 && !ranges.every(rng => Object(_package_json__WEBPACK_IMPORTED_MODULE_6__[/* isLinkDependency */ "a"])(rng.range))).reduce((acc, [dep, ranges]) => [...acc, dep, ...ranges.map(({ - range, - projects - }) => ` ${range} => ${projects.map(p => p.name).join(', ')}`)], []).join('\n '); - - if (duplicateRanges) { - _log__WEBPACK_IMPORTED_MODULE_5__[/* log */ "a"].error(dedent__WEBPACK_IMPORTED_MODULE_1___default.a` - - [single_version_dependencies] Multiple version ranges for the same dependency - were found declared across different package.json files. Please consolidate - those to match across all package.json files. Different versions for the - same dependency is not supported. - - If you have questions about this please reach out to the operations team. - - The conflicting dependencies are: - - ${duplicateRanges} - `); - process.exit(1); - } // look for packages that have the the `kibana.devOnly` flag in their package.json - // and make sure they aren't included in the production dependencies of Kibana - - - const devOnlyProjectsInProduction = getDevOnlyProductionDepsTree(kbn, 'kibana'); - - if (devOnlyProjectsInProduction) { - _log__WEBPACK_IMPORTED_MODULE_5__[/* log */ "a"].error(dedent__WEBPACK_IMPORTED_MODULE_1___default.a` - Some of the packages in the production dependency chain for Kibana and X-Pack are - flagged with "kibana.devOnly" in their package.json. Please check changes made to - packages and their dependencies to ensure they don't end up in production. - - The devOnly dependencies that are being dependend on in production are: - - ${Object(_projects_tree__WEBPACK_IMPORTED_MODULE_7__[/* treeToString */ "b"])(devOnlyProjectsInProduction).split('\n').join('\n ')} - `); - process.exit(1); - } - - _log__WEBPACK_IMPORTED_MODULE_5__[/* log */ "a"].success('yarn.lock analysis completed without any issues'); -} - -function getDevOnlyProductionDepsTree(kbn, projectName) { - const project = kbn.getProject(projectName); - const childProjectNames = [...Object.keys(project.productionDependencies).filter(name => kbn.hasProject(name)), ...(projectName === 'kibana' ? ['x-pack'] : [])]; - const children = childProjectNames.map(n => getDevOnlyProductionDepsTree(kbn, n)).filter(t => !!t); - - if (!children.length && !project.isFlaggedAsDevOnly()) { - return; - } - - const tree = { - name: project.isFlaggedAsDevOnly() ? chalk__WEBPACK_IMPORTED_MODULE_2___default.a.red.bold(projectName) : projectName, - children - }; - return tree; -} - -/***/ }), - -/***/ "./src/utils/yarn_lock.ts": -/***/ (function(module, __webpack_exports__, __webpack_require__) { - -"use strict"; -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return readYarnLock; }); -/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return resolveDepsForProject; }); -/* harmony import */ var _yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__("../../node_modules/@yarnpkg/lockfile/index.js"); -/* harmony import */ var _yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0__); -/* harmony import */ var _fs__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__("./src/utils/fs.ts"); -/* - * 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. - */ -// @ts-expect-error published types are worthless - - -async function readYarnLock(kbn) { - try { - const contents = await Object(_fs__WEBPACK_IMPORTED_MODULE_1__[/* readFile */ "f"])(kbn.getAbsolute('yarn.lock'), 'utf8'); - const yarnLock = Object(_yarnpkg_lockfile__WEBPACK_IMPORTED_MODULE_0__["parse"])(contents); - - if (yarnLock.type === 'success') { - return yarnLock.object; - } - - throw new Error('unable to read yarn.lock file, please run `yarn kbn bootstrap`'); - } catch (error) { - if (error.code !== 'ENOENT') { - throw error; - } - } - - return {}; -} -/** - * Get a list of the absolute dependencies of this project, as resolved - * in the yarn.lock file, does not include other projects in the workspace - * or their dependencies - */ - -function resolveDepsForProject({ - project: rootProject, - yarnLock, - kbn, - log, - productionDepsOnly, - includeDependentProject -}) { - /** map of [name@range, { name, version }] */ - const resolved = new Map(); - const seenProjects = new Set(); - const projectQueue = [rootProject]; - const depQueue = []; - - while (projectQueue.length) { - const project = projectQueue.shift(); - - if (seenProjects.has(project)) { - continue; - } - - seenProjects.add(project); - const projectDeps = Object.entries(productionDepsOnly ? project.productionDependencies : project.allDependencies); - - for (const [name, versionRange] of projectDeps) { - depQueue.push([name, versionRange]); - } - - while (depQueue.length) { - const [name, versionRange] = depQueue.shift(); - const req = `${name}@${versionRange}`; - - if (resolved.has(req)) { - continue; - } - - if (includeDependentProject && kbn.hasProject(name)) { - projectQueue.push(kbn.getProject(name)); - } - - if (!kbn.hasProject(name)) { - const pkg = yarnLock[req]; - - if (!pkg) { - log.warning('yarn.lock file is out of date, please run `yarn kbn bootstrap` to re-enable caching'); - return; - } - - resolved.set(req, { - name, - version: pkg.version - }); - const allDepsEntries = [...Object.entries(pkg.dependencies || {}), ...Object.entries(pkg.optionalDependencies || {})]; - - for (const [childName, childVersionRange] of allDepsEntries) { - depQueue.push([childName, childVersionRange]); - } - } - } - } - - return resolved; -} - -/***/ }), - -/***/ "assert": -/***/ (function(module, exports) { - -module.exports = require("assert"); - -/***/ }), - -/***/ "buffer": -/***/ (function(module, exports) { - -module.exports = require("buffer"); - -/***/ }), - -/***/ "child_process": -/***/ (function(module, exports) { - -module.exports = require("child_process"); - -/***/ }), - -/***/ "constants": -/***/ (function(module, exports) { - -module.exports = require("constants"); - -/***/ }), - -/***/ "crypto": -/***/ (function(module, exports) { - -module.exports = require("crypto"); - -/***/ }), - -/***/ "events": -/***/ (function(module, exports) { - -module.exports = require("events"); - -/***/ }), - -/***/ "fs": -/***/ (function(module, exports) { - -module.exports = require("fs"); - -/***/ }), - -/***/ "fs/promises": -/***/ (function(module, exports) { - -module.exports = require("fs/promises"); - -/***/ }), - -/***/ "http": -/***/ (function(module, exports) { - -module.exports = require("http"); - -/***/ }), - -/***/ "https": -/***/ (function(module, exports) { - -module.exports = require("https"); - -/***/ }), - -/***/ "net": -/***/ (function(module, exports) { - -module.exports = require("net"); - -/***/ }), - -/***/ "os": -/***/ (function(module, exports) { - -module.exports = require("os"); - -/***/ }), - -/***/ "path": -/***/ (function(module, exports) { - -module.exports = require("path"); - -/***/ }), - -/***/ "readline": -/***/ (function(module, exports) { - -module.exports = require("readline"); - -/***/ }), - -/***/ "stream": -/***/ (function(module, exports) { - -module.exports = require("stream"); - -/***/ }), - -/***/ "string_decoder": -/***/ (function(module, exports) { - -module.exports = require("string_decoder"); - -/***/ }), - -/***/ "tty": -/***/ (function(module, exports) { - -module.exports = require("tty"); - -/***/ }), - -/***/ "url": -/***/ (function(module, exports) { - -module.exports = require("url"); - -/***/ }), - -/***/ "util": -/***/ (function(module, exports) { - -module.exports = require("util"); - -/***/ }), - -/***/ "worker_threads": -/***/ (function(module, exports) { - -module.exports = require(undefined); - -/***/ }), - -/***/ "zlib": -/***/ (function(module, exports) { - -module.exports = require("zlib"); - -/***/ }) - -/******/ }); \ No newline at end of file diff --git a/packages/kbn-pm/package.json b/packages/kbn-pm/package.json deleted file mode 100644 index 72061c9625b09..0000000000000 --- a/packages/kbn-pm/package.json +++ /dev/null @@ -1,15 +0,0 @@ -{ - "name": "@kbn/pm", - "main": "./dist/index.js", - "version": "1.0.0", - "license": "SSPL-1.0 OR Elastic License 2.0", - "private": true, - "kibana": { - "devOnly": true - }, - "scripts": { - "build": "../../node_modules/.bin/webpack", - "kbn:watch": "../../node_modules/.bin/webpack --watch", - "prettier": "../../node_modules/.bin/prettier --write './src/**/*.ts'" - } -} \ No newline at end of file diff --git a/packages/kbn-pm/src/__snapshots__/run.test.ts.snap b/packages/kbn-pm/src/__snapshots__/run.test.ts.snap deleted file mode 100644 index 28e1b98e0fcd9..0000000000000 --- a/packages/kbn-pm/src/__snapshots__/run.test.ts.snap +++ /dev/null @@ -1,97 +0,0 @@ -// Jest Snapshot v1, https://goo.gl/fbAQLP - -exports[`excludes project if single \`exclude\` filter is specified 1`] = ` -Object { - "graph": Object { - "bar": Array [], - "baz": Array [], - "kibana": Array [], - "quux": Array [], - "with-additional-projects": Array [], - }, - "projects": Array [ - "bar", - "baz", - "kibana", - "quux", - "with-additional-projects", - ], -} -`; - -exports[`excludes projects if multiple \`exclude\` filter are specified 1`] = ` -Object { - "graph": Object { - "kibana": Array [], - "quux": Array [], - "with-additional-projects": Array [], - }, - "projects": Array [ - "kibana", - "quux", - "with-additional-projects", - ], -} -`; - -exports[`includes only projects specified in multiple \`include\` filters 1`] = ` -Object { - "graph": Object { - "bar": Array [], - "baz": Array [], - "foo": Array [], - }, - "projects": Array [ - "bar", - "baz", - "foo", - ], -} -`; - -exports[`includes single project if single \`include\` filter is specified 1`] = ` -Object { - "graph": Object { - "foo": Array [], - }, - "projects": Array [ - "foo", - ], -} -`; - -exports[`passes all found projects to the command if no filter is specified 1`] = ` -Object { - "graph": Object { - "bar": Array [], - "baz": Array [], - "foo": Array [], - "kibana": Array [ - "foo", - ], - "quux": Array [], - "with-additional-projects": Array [], - }, - "projects": Array [ - "bar", - "baz", - "foo", - "kibana", - "quux", - "with-additional-projects", - ], -} -`; - -exports[`respects both \`include\` and \`exclude\` filters if specified at the same time 1`] = ` -Object { - "graph": Object { - "baz": Array [], - "foo": Array [], - }, - "projects": Array [ - "baz", - "foo", - ], -} -`; diff --git a/packages/kbn-pm/src/cli.ts b/packages/kbn-pm/src/cli.ts deleted file mode 100644 index 8b313be500841..0000000000000 --- a/packages/kbn-pm/src/cli.ts +++ /dev/null @@ -1,108 +0,0 @@ -/* - * 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 dedent from 'dedent'; -import getopts from 'getopts'; -import { resolve } from 'path'; -import { pickLevelFromFlags } from '@kbn/tooling-log'; - -import { commands } from './commands'; -import { runCommand } from './run'; -import { log } from './utils/log'; - -function help() { - log.info( - dedent` - usage: kbn [] - - By default commands are run for Kibana itself, all packages in the 'packages/' - folder and for all plugins in './plugins' and '../kibana-extra'. - - Available commands: - - ${Object.values(commands) - .map((command) => `${command.name} - ${command.description}`) - .join('\n ')} - - Global options: - - -e, --exclude Exclude specified project. Can be specified multiple times to exclude multiple projects, e.g. '-e kibana -e @kbn/pm'. - -i, --include Include only specified projects. If left unspecified, it defaults to including all projects. - --oss Do not include the x-pack when running command. - --skip-kibana-plugins Filter all plugins in ./plugins and ../kibana-extra when running command. - --no-cache Disable the kbn packages bootstrap cache - --no-validate Disable the bootstrap yarn.lock validation - --force-install Forces yarn install to run on bootstrap - --offline Run in offline mode - --verbose Set log level to verbose - --debug Set log level to debug - --quiet Set log level to error - --silent Disable log output - - "run" options: - --skip-missing Ignore packages which don't have the requested script - ` + '\n' - ); -} - -export async function run(argv: string[]) { - log.setLogLevel( - pickLevelFromFlags( - getopts(argv, { - boolean: ['verbose', 'debug', 'quiet', 'silent', 'skip-missing'], - }) - ) - ); - - // We can simplify this setup (and remove this extra handling) once Yarn - // starts forwarding the `--` directly to this script, see - // https://github.com/yarnpkg/yarn/blob/b2d3e1a8fe45ef376b716d597cc79b38702a9320/src/cli/index.js#L174-L182 - if (argv.includes('--')) { - log.error(`Using "--" is not allowed, as it doesn't work with 'yarn kbn'.`); - process.exit(1); - } - - const options = getopts(argv, { - alias: { - e: 'exclude', - h: 'help', - i: 'include', - }, - default: { - cache: true, - 'force-install': false, - offline: false, - validate: true, - }, - boolean: ['cache', 'force-install', 'offline', 'validate'], - }); - - const args = options._; - - if (options.help || args.length === 0) { - help(); - return; - } - - // This `rootPath` is relative to `./dist/` as that's the location of the - // built version of this tool. - const rootPath = resolve(__dirname, '../../../'); - - const commandName = args[0]; - const extraArgs = args.slice(1); - - const commandOptions = { options, extraArgs, rootPath }; - - const command = commands[commandName]; - if (command === undefined) { - log.error(`[${commandName}] is not a valid command, see 'kbn --help'`); - process.exit(1); - } - - await runCommand(command, commandOptions); -} diff --git a/packages/kbn-pm/src/commands/bootstrap.ts b/packages/kbn-pm/src/commands/bootstrap.ts deleted file mode 100644 index 8ac55b3478363..0000000000000 --- a/packages/kbn-pm/src/commands/bootstrap.ts +++ /dev/null @@ -1,148 +0,0 @@ -/* - * 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 Path from 'path'; -import { CiStatsReporter } from '@kbn/ci-stats-reporter'; -import { runBazel } from '@kbn/bazel-runner'; - -import { log } from '../utils/log'; -import { spawnStreaming } from '../utils/child_process'; -import { linkProjectExecutables } from '../utils/link_project_executables'; -import { ICommand } from '.'; -import { readYarnLock } from '../utils/yarn_lock'; -import { validateDependencies } from '../utils/validate_dependencies'; -import { - installBazelTools, - haveNodeModulesBeenManuallyDeleted, - removeYarnIntegrityFileIfExists, -} from '../utils/bazel'; -import { setupRemoteCache } from '../utils/bazel/setup_remote_cache'; - -export const BootstrapCommand: ICommand = { - description: 'Install dependencies and crosslink projects', - name: 'bootstrap', - - reportTiming: { - group: 'scripts/kbn bootstrap', - id: 'total', - }, - - async run(projects, projectGraph, { options, kbn, rootPath }) { - const kibanaProjectPath = projects.get('kibana')?.path || ''; - const offline = options?.offline === true; - const reporter = CiStatsReporter.fromEnv(log); - - const timings: Array<{ id: string; ms: number }> = []; - const time = async (id: string, body: () => Promise): Promise => { - const start = Date.now(); - try { - return await body(); - } finally { - timings.push({ - id, - ms: Date.now() - start, - }); - } - }; - - // Force install is set in case a flag is passed into yarn kbn bootstrap or - // our custom logic have determined there is a chance node_modules have been manually deleted and as such bazel - // tracking mechanism is no longer valid - const forceInstall = - (!!options && options['force-install'] === true) || - (await haveNodeModulesBeenManuallyDeleted(kibanaProjectPath)); - - // Install bazel machinery tools if needed - await installBazelTools(rootPath); - - // Setup remote cache settings in .bazelrc.cache if needed - await setupRemoteCache(rootPath); - - // Bootstrap process for Bazel packages - // Bazel is now managing dependencies so yarn install - // will happen as part of this - // - // NOTE: Bazel projects will be introduced incrementally - // And should begin from the ones with none dependencies forward. - // That way non bazel projects could depend on bazel projects but not the other way around - // That is only intended during the migration process while non Bazel projects are not removed at all. - // - - if (forceInstall) { - await time('force install dependencies', async () => { - await removeYarnIntegrityFileIfExists(Path.resolve(kibanaProjectPath, 'node_modules')); - await runBazel({ - bazelArgs: ['clean', '--expunge'], - log, - }); - await runBazel({ - bazelArgs: ['run', '@nodejs//:yarn'], - offline, - log, - execaOpts: { - env: { - SASS_BINARY_SITE: - 'https://us-central1-elastic-kibana-184716.cloudfunctions.net/kibana-ci-proxy-cache/node-sass', - RE2_DOWNLOAD_MIRROR: - 'https://us-central1-elastic-kibana-184716.cloudfunctions.net/kibana-ci-proxy-cache/node-re2', - }, - }, - }); - }); - } - - // build packages - await time('build packages', async () => { - await runBazel({ - bazelArgs: ['build', '//packages:build', '--show_result=1'], - log, - offline, - }); - }); - - const yarnLock = await time('read yarn.lock', async () => await readYarnLock(kbn)); - - if (options.validate) { - await time('validate dependencies', async () => { - await validateDependencies(kbn, yarnLock); - }); - } - - // Assure all kbn projects with bin defined scripts - // copy those scripts into the top level node_modules folder - // - // NOTE: We don't probably need this anymore, is actually not being used - await time('link project executables', async () => { - await linkProjectExecutables(projects, projectGraph); - }); - - await time('update vscode config', async () => { - // Update vscode settings - await spawnStreaming( - process.execPath, - ['scripts/update_vscode_config'], - { - cwd: kbn.getAbsolute(), - env: process.env, - }, - { prefix: '[vscode]', debug: false } - ); - }); - - // send timings - await reporter.timings({ - upstreamBranch: kbn.kibanaProject.json.branch, - // prevent loading @kbn/utils by passing null - kibanaUuid: kbn.getUuid() || null, - timings: timings.map((t) => ({ - group: 'scripts/kbn bootstrap', - ...t, - })), - }); - }, -}; diff --git a/packages/kbn-pm/src/commands/build.ts b/packages/kbn-pm/src/commands/build.ts deleted file mode 100644 index 567b4addddee7..0000000000000 --- a/packages/kbn-pm/src/commands/build.ts +++ /dev/null @@ -1,30 +0,0 @@ -/* - * 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 { runBazel } from '@kbn/bazel-runner'; -import { ICommand } from '.'; -import { log } from '../utils/log'; - -export const BuildCommand: ICommand = { - description: 'Runs a build in the Bazel built packages', - name: 'build', - - reportTiming: { - group: 'scripts/kbn build', - id: 'total', - }, - - async run(projects, projectGraph, { options }) { - // Call bazel with the target to build all available packages - await runBazel({ - bazelArgs: ['build', '//packages:build', '--show_result=1'], - log, - offline: options?.offline === true, - }); - }, -}; diff --git a/packages/kbn-pm/src/commands/clean.ts b/packages/kbn-pm/src/commands/clean.ts deleted file mode 100644 index 8f8564add2096..0000000000000 --- a/packages/kbn-pm/src/commands/clean.ts +++ /dev/null @@ -1,94 +0,0 @@ -/* - * 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 dedent from 'dedent'; -import del from 'del'; -import ora from 'ora'; -import { join, relative } from 'path'; -import { runBazel } from '@kbn/bazel-runner'; - -import { isBazelBinAvailable } from '../utils/bazel'; -import { isDirectory } from '../utils/fs'; -import { log } from '../utils/log'; -import { ICommand } from '.'; - -export const CleanCommand: ICommand = { - description: 'Deletes output directories and resets internal caches.', - name: 'clean', - - reportTiming: { - group: 'scripts/kbn clean', - id: 'total', - }, - - async run(projects, projectGraph, { kbn }) { - log.warning(dedent` - This command is only necessary for the circumstance where you need to recover a consistent - state when problems arise. If you need to run this command often, please let us know by - filling out this form: https://ela.st/yarn-kbn-clean. - Please not it might not solve problems with node_modules. To solve problems around node_modules - you might need to run 'yarn kbn reset'. - `); - - const toDelete = []; - for (const project of projects.values()) { - if (await isDirectory(project.targetLocation)) { - toDelete.push({ - cwd: project.path, - pattern: relative(project.path, project.targetLocation), - }); - } - - const { extraPatterns } = project.getCleanConfig(); - if (extraPatterns) { - toDelete.push({ - cwd: project.path, - pattern: extraPatterns, - }); - } - } - - // Runs Bazel soft clean - if (await isBazelBinAvailable(kbn.getAbsolute())) { - await runBazel({ - bazelArgs: ['clean'], - log, - }); - log.success('Soft cleaned bazel'); - } - - if (toDelete.length === 0) { - log.success('Nothing to delete'); - } else { - /** - * In order to avoid patterns like `/build` in packages from accidentally - * impacting files outside the package we use `process.chdir()` to change - * the cwd to the package and execute `del()` without the `force` option - * so it will check that each file being deleted is within the package. - * - * `del()` does support a `cwd` option, but it's only for resolving the - * patterns and does not impact the cwd check. - */ - const originalCwd = process.cwd(); - try { - for (const { pattern, cwd } of toDelete) { - process.chdir(cwd); - const promise = del(pattern); - - if (log.wouldLogLevel('info')) { - ora.promise(promise, relative(originalCwd, join(cwd, String(pattern)))); - } - - await promise; - } - } finally { - process.chdir(originalCwd); - } - } - }, -}; diff --git a/packages/kbn-pm/src/commands/index.ts b/packages/kbn-pm/src/commands/index.ts deleted file mode 100644 index 4c7992859ebdd..0000000000000 --- a/packages/kbn-pm/src/commands/index.ts +++ /dev/null @@ -1,44 +0,0 @@ -/* - * 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 { ProjectGraph, ProjectMap } from '../utils/projects'; - -export interface ICommandConfig { - extraArgs: string[]; - options: { [key: string]: any }; - rootPath: string; - kbn: Kibana; -} - -export interface ICommand { - name: string; - description: string; - reportTiming?: { - group: string; - id: string; - }; - - run: (projects: ProjectMap, projectGraph: ProjectGraph, config: ICommandConfig) => Promise; -} - -import { BootstrapCommand } from './bootstrap'; -import { BuildCommand } from './build'; -import { CleanCommand } from './clean'; -import { ResetCommand } from './reset'; -import { RunCommand } from './run'; -import { WatchCommand } from './watch'; -import { Kibana } from '../utils/kibana'; - -export const commands: { [key: string]: ICommand } = { - bootstrap: BootstrapCommand, - build: BuildCommand, - clean: CleanCommand, - reset: ResetCommand, - run: RunCommand, - watch: WatchCommand, -}; diff --git a/packages/kbn-pm/src/commands/reset.ts b/packages/kbn-pm/src/commands/reset.ts deleted file mode 100644 index 5b6aac40149c2..0000000000000 --- a/packages/kbn-pm/src/commands/reset.ts +++ /dev/null @@ -1,112 +0,0 @@ -/* - * 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 dedent from 'dedent'; -import del from 'del'; -import ora from 'ora'; -import { join, relative } from 'path'; - -import { runBazel } from '@kbn/bazel-runner'; - -import { - getBazelDiskCacheFolder, - getBazelRepositoryCacheFolder, - isBazelBinAvailable, -} from '../utils/bazel'; -import { isDirectory } from '../utils/fs'; -import { log } from '../utils/log'; -import { ICommand } from '.'; - -export const ResetCommand: ICommand = { - description: - 'Deletes node_modules and output directories, resets internal and disk caches, and stops Bazel server', - name: 'reset', - - reportTiming: { - group: 'scripts/kbn reset', - id: 'total', - }, - - async run(projects, projectGraph, { kbn }) { - log.warning(dedent` - In most cases, 'yarn kbn clean' is all that should be needed to recover a consistent state when - problems arise. However for the rare cases where something get corrupt on node_modules you might need this command. - If you think you need to use this command very often (which is not normal), please let us know. - `); - - const toDelete = []; - for (const project of projects.values()) { - if (await isDirectory(project.nodeModulesLocation)) { - toDelete.push({ - cwd: project.path, - pattern: relative(project.path, project.nodeModulesLocation), - }); - } - - if (await isDirectory(project.targetLocation)) { - toDelete.push({ - cwd: project.path, - pattern: relative(project.path, project.targetLocation), - }); - } - - const { extraPatterns } = project.getCleanConfig(); - if (extraPatterns) { - toDelete.push({ - cwd: project.path, - pattern: extraPatterns, - }); - } - } - - // Runs Bazel hard clean and deletes Bazel Cache Folders - if (await isBazelBinAvailable(kbn.getAbsolute())) { - // Hard cleaning bazel - await runBazel({ - bazelArgs: ['clean', '--expunge'], - log, - }); - log.success('Hard cleaned bazel'); - - // Deletes Bazel Cache Folders - await del([await getBazelDiskCacheFolder(), await getBazelRepositoryCacheFolder()], { - force: true, - }); - log.success('Removed disk caches'); - } - - if (toDelete.length === 0) { - return; - } - - /** - * In order to avoid patterns like `/build` in packages from accidentally - * impacting files outside the package we use `process.chdir()` to change - * the cwd to the package and execute `del()` without the `force` option - * so it will check that each file being deleted is within the package. - * - * `del()` does support a `cwd` option, but it's only for resolving the - * patterns and does not impact the cwd check. - */ - const originalCwd = process.cwd(); - try { - for (const { pattern, cwd } of toDelete) { - process.chdir(cwd); - const promise = del(pattern); - - if (log.wouldLogLevel('info')) { - ora.promise(promise, relative(originalCwd, join(cwd, String(pattern)))); - } - - await promise; - } - } finally { - process.chdir(originalCwd); - } - }, -}; diff --git a/packages/kbn-pm/src/commands/run.ts b/packages/kbn-pm/src/commands/run.ts deleted file mode 100644 index 67cc7855d8e19..0000000000000 --- a/packages/kbn-pm/src/commands/run.ts +++ /dev/null @@ -1,60 +0,0 @@ -/* - * 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 dedent from 'dedent'; -import { CliError } from '../utils/errors'; -import { log } from '../utils/log'; -import { parallelizeBatches } from '../utils/parallelize'; -import { topologicallyBatchProjects } from '../utils/projects'; -import { ICommand } from '.'; - -export const RunCommand: ICommand = { - description: - 'Run script defined in package.json in each package that contains that script (only works on packages not using Bazel yet)', - name: 'run', - - reportTiming: { - group: 'scripts/kbn run', - id: 'total', - }, - - async run(projects, projectGraph, { extraArgs, options }) { - log.warning(dedent` - We are migrating packages into the Bazel build system and we will no longer support running npm scripts on - packages using 'yarn kbn run' on Bazel built packages. If the package you are trying to act on contains a - BUILD.bazel file please just use 'yarn kbn build' to build it or 'yarn kbn watch' to watch it - `); - - const batchedProjects = topologicallyBatchProjects(projects, projectGraph); - - if (extraArgs.length === 0) { - throw new CliError('No script specified'); - } - - const scriptName = extraArgs[0]; - const scriptArgs = extraArgs.slice(1); - - await parallelizeBatches(batchedProjects, async (project) => { - if (!project.hasScript(scriptName)) { - if (!!options['skip-missing']) { - return; - } - - throw new CliError( - `[${project.name}] no "${scriptName}" script defined. To skip packages without the "${scriptName}" script pass --skip-missing` - ); - } - - log.info(`[${project.name}] running "${scriptName}" script`); - await project.runScriptStreaming(scriptName, { - args: scriptArgs, - }); - log.success(`[${project.name}] complete`); - }); - }, -}; diff --git a/packages/kbn-pm/src/commands/watch.ts b/packages/kbn-pm/src/commands/watch.ts deleted file mode 100644 index 2bae2ddc66235..0000000000000 --- a/packages/kbn-pm/src/commands/watch.ts +++ /dev/null @@ -1,35 +0,0 @@ -/* - * 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 { runIBazel } from '@kbn/bazel-runner'; -import { ICommand } from '.'; -import { log } from '../utils/log'; - -export const WatchCommand: ICommand = { - description: 'Runs a build in the Bazel built packages and keeps watching them for changes', - name: 'watch', - - reportTiming: { - group: 'scripts/kbn watch', - id: 'total', - }, - - async run(projects, projectGraph, { options }) { - const runOffline = options?.offline === true; - - // Call bazel with the target to build all available packages and run it through iBazel to watch it for changes - // - // Note: --run_output=false arg will disable the iBazel notifications about gazelle and buildozer when running it - // Can also be solved by adding a root `.bazel_fix_commands.json` but its not needed at the moment - await runIBazel({ - bazelArgs: ['--run_output=false', 'build', '//packages:build', '--show_result=1'], - log, - offline: runOffline, - }); - }, -}; diff --git a/packages/kbn-pm/src/config.ts b/packages/kbn-pm/src/config.ts deleted file mode 100644 index 666a2fed7a33c..0000000000000 --- a/packages/kbn-pm/src/config.ts +++ /dev/null @@ -1,54 +0,0 @@ -/* - * 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 { resolve } from 'path'; - -interface Options { - rootPath: string; - skipKibanaPlugins?: boolean; - ossOnly?: boolean; -} - -/** - * Returns all the paths where plugins are located - */ -export function getProjectPaths({ rootPath, ossOnly, skipKibanaPlugins }: Options) { - const projectPaths = [rootPath, resolve(rootPath, 'packages/*')]; - - // This is needed in order to install the dependencies for the declared - // plugin functional used in the selenium functional tests. - // As we are now using the webpack dll for the client vendors dependencies - // when we run the plugin functional tests against the distributable - // dependencies used by such plugins like @eui, react and react-dom can't - // be loaded from the dll as the context is different from the one declared - // into the webpack dll reference plugin. - // In anyway, have a plugin declaring their own dependencies is the - // correct and the expect behavior. - projectPaths.push(resolve(rootPath, 'test/plugin_functional/plugins/*')); - projectPaths.push(resolve(rootPath, 'test/interpreter_functional/plugins/*')); - projectPaths.push(resolve(rootPath, 'test/server_integration/__fixtures__/plugins/*')); - projectPaths.push(resolve(rootPath, 'examples/*')); - - if (!ossOnly) { - projectPaths.push(resolve(rootPath, 'x-pack')); - projectPaths.push(resolve(rootPath, 'x-pack/plugins/*')); - projectPaths.push(resolve(rootPath, 'x-pack/legacy/plugins/*')); - projectPaths.push(resolve(rootPath, 'x-pack/test/functional_with_es_ssl/fixtures/plugins/*')); - } - - if (!skipKibanaPlugins) { - projectPaths.push(resolve(rootPath, '../kibana-extra/*')); - projectPaths.push(resolve(rootPath, '../kibana-extra/*/packages/*')); - projectPaths.push(resolve(rootPath, '../kibana-extra/*/plugins/*')); - projectPaths.push(resolve(rootPath, 'plugins/*')); - projectPaths.push(resolve(rootPath, 'plugins/*/packages/*')); - projectPaths.push(resolve(rootPath, 'plugins/*/plugins/*')); - } - - return projectPaths; -} diff --git a/packages/kbn-pm/src/index.ts b/packages/kbn-pm/src/index.ts deleted file mode 100644 index d2f907a43db20..0000000000000 --- a/packages/kbn-pm/src/index.ts +++ /dev/null @@ -1,12 +0,0 @@ -/* - * 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. - */ - -export { run } from './cli'; -export { getProjects } from './utils/projects'; -export { Project } from './utils/project'; -export { getProjectPaths } from './config'; diff --git a/packages/kbn-pm/src/run.test.ts b/packages/kbn-pm/src/run.test.ts deleted file mode 100644 index 5584c35619ba9..0000000000000 --- a/packages/kbn-pm/src/run.test.ts +++ /dev/null @@ -1,121 +0,0 @@ -/* - * 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 { resolve } from 'path'; - -import { ICommand, ICommandConfig } from './commands'; -import { runCommand } from './run'; -import { Project } from './utils/project'; -import { log } from './utils/log'; - -log.setLogLevel('silent'); - -const rootPath = resolve(__dirname, 'utils/__fixtures__/kibana'); - -jest.mock('./utils/regenerate_package_json'); -jest.mock('./utils/regenerate_synthetic_package_map'); -jest.mock('./utils/regenerate_base_tsconfig'); - -function getExpectedProjectsAndGraph(runMock: any) { - const [fullProjects, fullProjectGraph] = (runMock as jest.Mock).mock.calls[0]; - - const projects = [...fullProjects.keys()].sort(); - - const graph = [...fullProjectGraph.entries()].reduce((expected, [projectName, dependencies]) => { - expected[projectName] = dependencies.map((project: Project) => project.name); - return expected; - }, {}); - - return { projects, graph }; -} - -let command: ICommand; -let config: Omit; -beforeEach(() => { - command = { - description: 'test description', - name: 'test name', - run: jest.fn(), - }; - - config = { - extraArgs: [], - options: {}, - rootPath, - }; -}); - -test('passes all found projects to the command if no filter is specified', async () => { - await runCommand(command, config); - - expect(command.run).toHaveBeenCalledTimes(1); - expect(getExpectedProjectsAndGraph(command.run)).toMatchSnapshot(); -}); - -test('excludes project if single `exclude` filter is specified', async () => { - await runCommand(command, { - ...config, - options: { exclude: 'foo' }, - }); - - expect(command.run).toHaveBeenCalledTimes(1); - expect(getExpectedProjectsAndGraph(command.run)).toMatchSnapshot(); -}); - -test('excludes projects if multiple `exclude` filter are specified', async () => { - await runCommand(command, { - ...config, - options: { exclude: ['foo', 'bar', 'baz'] }, - }); - - expect(command.run).toHaveBeenCalledTimes(1); - expect(getExpectedProjectsAndGraph(command.run)).toMatchSnapshot(); -}); - -test('includes single project if single `include` filter is specified', async () => { - await runCommand(command, { - ...config, - options: { include: 'foo' }, - }); - - expect(command.run).toHaveBeenCalledTimes(1); - expect(getExpectedProjectsAndGraph(command.run)).toMatchSnapshot(); -}); - -test('includes only projects specified in multiple `include` filters', async () => { - await runCommand(command, { - ...config, - options: { include: ['foo', 'bar', 'baz'] }, - }); - - expect(command.run).toHaveBeenCalledTimes(1); - expect(getExpectedProjectsAndGraph(command.run)).toMatchSnapshot(); -}); - -test('respects both `include` and `exclude` filters if specified at the same time', async () => { - await runCommand(command, { - ...config, - options: { include: ['foo', 'bar', 'baz'], exclude: 'bar' }, - }); - - expect(command.run).toHaveBeenCalledTimes(1); - expect(getExpectedProjectsAndGraph(command.run)).toMatchSnapshot(); -}); - -test('does not run command if all projects are filtered out', async () => { - const mockProcessExit = jest.spyOn(process, 'exit').mockReturnValue(undefined as never); - - await runCommand(command, { - ...config, - // Including and excluding the same project will result in 0 projects selected. - options: { include: ['foo'], exclude: ['foo'] }, - }); - - expect(command.run).not.toHaveBeenCalled(); - expect(mockProcessExit).toHaveBeenCalledWith(1); -}); diff --git a/packages/kbn-pm/src/run.ts b/packages/kbn-pm/src/run.ts deleted file mode 100644 index 0529ebd6425ca..0000000000000 --- a/packages/kbn-pm/src/run.ts +++ /dev/null @@ -1,162 +0,0 @@ -/* - * 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 { CiStatsReporter, CiStatsTiming } from '@kbn/ci-stats-reporter'; - -import { simpleKibanaPlatformPluginDiscovery, getPluginSearchPaths } from '@kbn/plugin-discovery'; -import { ICommand, ICommandConfig } from './commands'; -import { CliError } from './utils/errors'; -import { log } from './utils/log'; -import { buildProjectGraph } from './utils/projects'; -import { renderProjectsTree } from './utils/projects_tree'; -import { regeneratePackageJson } from './utils/regenerate_package_json'; -import { regenerateSyntheticPackageMap } from './utils/regenerate_synthetic_package_map'; -import { regenerateBaseTsconfig } from './utils/regenerate_base_tsconfig'; -import { Kibana } from './utils/kibana'; - -process.env.CI_STATS_NESTED_TIMING = 'true'; - -export async function runCommand(command: ICommand, config: Omit) { - const runStartTime = Date.now(); - let kbn: undefined | Kibana; - const timings: Array> = []; - async function time(id: string, block: () => Promise): Promise { - const start = Date.now(); - let success = true; - try { - return await block(); - } catch (error) { - success = false; - throw error; - } finally { - timings.push({ - id, - ms: Date.now() - start, - meta: { - success, - }, - }); - } - } - - async function reportTimes(timingConfig: { group: string; id: string }, error?: Error) { - if (!kbn) { - // things are too broken to report remotely - return; - } - - const reporter = CiStatsReporter.fromEnv(log); - - try { - await reporter.timings({ - upstreamBranch: kbn.kibanaProject.json.branch, - // prevent loading @kbn/utils by passing null - kibanaUuid: kbn.getUuid() || null, - timings: [ - ...timings.map((t) => ({ ...timingConfig, ...t })), - { - group: timingConfig.group, - id: timingConfig.id, - ms: Date.now() - runStartTime, - meta: { - success: !error, - }, - }, - ], - }); - } catch (e) { - // prevent hiding bootstrap errors - log.error('failed to report timings:'); - log.error(e); - } - } - - try { - log.debug(`Running [${command.name}] command from [${config.rootPath}]`); - - await time('regenerate package.json, synthetic-package map and tsconfig', async () => { - const plugins = simpleKibanaPlatformPluginDiscovery( - getPluginSearchPaths({ - rootDir: config.rootPath, - oss: false, - examples: true, - testPlugins: true, - }), - [] - ); - - await Promise.all([ - regeneratePackageJson(config.rootPath), - regenerateSyntheticPackageMap(plugins, config.rootPath), - regenerateBaseTsconfig(plugins, config.rootPath), - ]); - }); - - kbn = await time('load Kibana project', async () => await Kibana.loadFrom(config.rootPath)); - const projects = kbn.getFilteredProjects({ - skipKibanaPlugins: Boolean(config.options['skip-kibana-plugins']), - ossOnly: Boolean(config.options.oss), - exclude: toArray(config.options.exclude), - include: toArray(config.options.include), - }); - - if (projects.size === 0) { - log.error( - `There are no projects found. Double check project name(s) in '-i/--include' and '-e/--exclude' filters.` - ); - return process.exit(1); - } - - const projectGraph = buildProjectGraph(projects); - - log.debug(`Found ${projects.size.toString()} projects`); - log.debug(renderProjectsTree(config.rootPath, projects)); - - await command.run(projects, projectGraph, { - ...config, - kbn, - }); - - if (command.reportTiming) { - await reportTimes(command.reportTiming); - } - } catch (error) { - if (command.reportTiming) { - await reportTimes(command.reportTiming, error); - } - - log.error(`[${command.name}] failed:`); - - if (error instanceof CliError) { - log.error(error.message); - - const metaOutput = Object.entries(error.meta) - .map(([key, value]) => `${key}: ${value}`) - .join('\n'); - - if (metaOutput) { - log.info('Additional debugging info:\n'); - log.indent(2); - log.info(metaOutput); - log.indent(-2); - } - } else { - log.error(error); - } - - process.exit(1); - } -} - -function toArray(value?: T | T[]) { - if (value == null) { - return []; - } - - return Array.isArray(value) ? value : [value]; -} diff --git a/packages/kbn-pm/src/test_helpers/absolute_path_snapshot_serializer.ts b/packages/kbn-pm/src/test_helpers/absolute_path_snapshot_serializer.ts deleted file mode 100644 index b220d7073a5aa..0000000000000 --- a/packages/kbn-pm/src/test_helpers/absolute_path_snapshot_serializer.ts +++ /dev/null @@ -1,40 +0,0 @@ -/* - * 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 { cloneDeepWith } from 'lodash'; -import { resolve, sep as pathSep } from 'path'; - -const repoRoot = resolve(__dirname, '../../../../'); - -const normalizePaths = (value: any) => { - let didReplacement = false; - const clone = cloneDeepWith(value, (v: any) => { - if (typeof v === 'string' && v.startsWith(repoRoot)) { - didReplacement = true; - return v - .replace(repoRoot, '') - .split(pathSep) // normalize path separators - .join('/'); - } - }); - - return { - clone, - didReplacement, - }; -}; - -export const absolutePathSnapshotSerializer = { - print(value: any, serialize: (val: any) => string) { - return serialize(normalizePaths(value).clone); - }, - - test(value: any) { - return normalizePaths(value).didReplacement; - }, -}; diff --git a/packages/kbn-pm/src/test_helpers/index.ts b/packages/kbn-pm/src/test_helpers/index.ts deleted file mode 100644 index 80e2464906348..0000000000000 --- a/packages/kbn-pm/src/test_helpers/index.ts +++ /dev/null @@ -1,11 +0,0 @@ -/* - * 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. - */ - -export { absolutePathSnapshotSerializer } from './absolute_path_snapshot_serializer'; - -export { stripAnsiSnapshotSerializer } from './strip_ansi_snapshot_serializer'; diff --git a/packages/kbn-pm/src/test_helpers/strip_ansi_snapshot_serializer.ts b/packages/kbn-pm/src/test_helpers/strip_ansi_snapshot_serializer.ts deleted file mode 100644 index ddb01680606e9..0000000000000 --- a/packages/kbn-pm/src/test_helpers/strip_ansi_snapshot_serializer.ts +++ /dev/null @@ -1,20 +0,0 @@ -/* - * 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 hasAnsi from 'has-ansi'; -import stripAnsi from 'strip-ansi'; - -export const stripAnsiSnapshotSerializer: jest.SnapshotSerializerPlugin = { - serialize(value: string) { - return stripAnsi(value); - }, - - test(value: any) { - return typeof value === 'string' && hasAnsi(value); - }, -}; diff --git a/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/package.json b/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/package.json deleted file mode 100644 index a9fd807525091..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "with-additional-projects", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/packages/baz/package.json b/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/packages/baz/package.json deleted file mode 100644 index 7a2708cb51d4e..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/packages/baz/package.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "name": "baz", - "version": "1.0.0", - "dependencies": { - "bar": "link:../../../../kibana/packages/bar" - } -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/plugins/quux/package.json b/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/plugins/quux/package.json deleted file mode 100644 index abe001edaa6be..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/kibana-extra/additional_projects/plugins/quux/package.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "name": "quux", - "version": "1.0.0", - "dependencies": { - "bar": "link:../../../../kibana/packages/bar", - "baz": "link:../../packages/baz" - } -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/kibana/package.json b/packages/kbn-pm/src/utils/__fixtures__/kibana/package.json deleted file mode 100644 index 98bc15383f844..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/kibana/package.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "name": "kibana", - "version": "1.0.0", - "dependencies": { - "foo": "link:packages/foo" - } -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/kibana/packages/bar/package.json b/packages/kbn-pm/src/utils/__fixtures__/kibana/packages/bar/package.json deleted file mode 100644 index 06a8b8dcc6aa8..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/kibana/packages/bar/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "bar", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/kibana/packages/foo/package.json b/packages/kbn-pm/src/utils/__fixtures__/kibana/packages/foo/package.json deleted file mode 100644 index da86787ad3ecc..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/kibana/packages/foo/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "foo", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/other-plugins/baz/package.json b/packages/kbn-pm/src/utils/__fixtures__/other-plugins/baz/package.json deleted file mode 100644 index d689f6bc97070..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/other-plugins/baz/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "baz", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/plugins/baz/package.json b/packages/kbn-pm/src/utils/__fixtures__/plugins/baz/package.json deleted file mode 100644 index d689f6bc97070..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/plugins/baz/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "baz", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/plugins/quux/package.json b/packages/kbn-pm/src/utils/__fixtures__/plugins/quux/package.json deleted file mode 100644 index f2a3062454509..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/plugins/quux/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "quux", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/plugins/zorge/package.json b/packages/kbn-pm/src/utils/__fixtures__/plugins/zorge/package.json deleted file mode 100644 index 3f22a1845b66a..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/plugins/zorge/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "zorge", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__fixtures__/symlinked-plugins/corge/package.json b/packages/kbn-pm/src/utils/__fixtures__/symlinked-plugins/corge/package.json deleted file mode 100644 index 20484e93d285d..0000000000000 --- a/packages/kbn-pm/src/utils/__fixtures__/symlinked-plugins/corge/package.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "name": "corge", - "version": "1.0.0" -} diff --git a/packages/kbn-pm/src/utils/__snapshots__/link_project_executables.test.ts.snap b/packages/kbn-pm/src/utils/__snapshots__/link_project_executables.test.ts.snap deleted file mode 100644 index 8aeae04c265cf..0000000000000 --- a/packages/kbn-pm/src/utils/__snapshots__/link_project_executables.test.ts.snap +++ /dev/null @@ -1,35 +0,0 @@ -// Jest Snapshot v1, https://goo.gl/fbAQLP - -exports[`bin script points nowhere does not try to create symlink on node_modules/.bin for that bin script: fs module calls 1`] = ` -Object { - "chmod": Array [], - "copyDirectory": Array [], - "createSymlink": Array [], - "isDirectory": Array [], - "isFile": Array [], - "isSymlink": Array [], - "mkdirp": Array [], - "readFile": Array [], - "rmdirp": Array [], - "tryRealpath": Array [], - "unlink": Array [], - "writeFile": Array [], -} -`; - -exports[`bin script points to a file creates a symlink for the project bin into the roots project node_modules/.bin directory as well as node_modules/.bin directory symlink into the roots one: fs module calls 1`] = ` -Object { - "chmod": Array [], - "copyDirectory": Array [], - "createSymlink": Array [], - "isDirectory": Array [], - "isFile": Array [], - "isSymlink": Array [], - "mkdirp": Array [], - "readFile": Array [], - "rmdirp": Array [], - "tryRealpath": Array [], - "unlink": Array [], - "writeFile": Array [], -} -`; diff --git a/packages/kbn-pm/src/utils/__snapshots__/project.test.ts.snap b/packages/kbn-pm/src/utils/__snapshots__/project.test.ts.snap deleted file mode 100644 index d4a4e5ca23452..0000000000000 --- a/packages/kbn-pm/src/utils/__snapshots__/project.test.ts.snap +++ /dev/null @@ -1,3 +0,0 @@ -// Jest Snapshot v1, https://goo.gl/fbAQLP - -exports[`#getExecutables() throws CliError when bin is something strange 1`] = `"[kibana] has an invalid \\"bin\\" field in its package.json, expected an object or a string"`; diff --git a/packages/kbn-pm/src/utils/__snapshots__/projects.test.ts.snap b/packages/kbn-pm/src/utils/__snapshots__/projects.test.ts.snap deleted file mode 100644 index a716b9fab4e5b..0000000000000 --- a/packages/kbn-pm/src/utils/__snapshots__/projects.test.ts.snap +++ /dev/null @@ -1,41 +0,0 @@ -// Jest Snapshot v1, https://goo.gl/fbAQLP - -exports[`#buildProjectGraph builds full project graph 1`] = ` -Object { - "bar": Array [], - "baz": Array [], - "foo": Array [], - "kibana": Array [ - "foo", - ], - "quux": Array [], - "zorge": Array [], -} -`; - -exports[`#topologicallyBatchProjects batches projects topologically based on their project dependencies 1`] = ` -Array [ - Array [ - "bar", - "foo", - "baz", - "quux", - "zorge", - ], - Array [ - "kibana", - ], -] -`; - -exports[`#topologicallyBatchProjects batches projects topologically even if graph contains projects not presented in the project map 1`] = ` -Array [ - Array [ - "kibana", - "bar", - "baz", - "quux", - "zorge", - ], -] -`; diff --git a/packages/kbn-pm/src/utils/__snapshots__/projects_tree.test.ts.snap b/packages/kbn-pm/src/utils/__snapshots__/projects_tree.test.ts.snap deleted file mode 100644 index 9993e2eaf377a..0000000000000 --- a/packages/kbn-pm/src/utils/__snapshots__/projects_tree.test.ts.snap +++ /dev/null @@ -1,29 +0,0 @@ -// Jest Snapshot v1, https://goo.gl/fbAQLP - -exports[`handles projects outside root folder 1`] = ` -kibana -├── packages -│ ├── bar -│ └── foo -└── ../plugins - ├── baz - ├── quux - └── zorge -`; - -exports[`handles projects with root folder 1`] = ` -kibana -└── packages - ├── bar - └── foo -`; - -exports[`handles projects within projects outside root folder 1`] = ` -kibana -├── packages -│ ├── bar -│ └── foo -└── ../kibana-extra/additional_projects (with-additional-projects) - ├── packages/baz - └── plugins/quux -`; diff --git a/packages/kbn-pm/src/utils/bazel/get_cache_folders.ts b/packages/kbn-pm/src/utils/bazel/get_cache_folders.ts deleted file mode 100644 index 8426bfd58296c..0000000000000 --- a/packages/kbn-pm/src/utils/bazel/get_cache_folders.ts +++ /dev/null @@ -1,25 +0,0 @@ -/* - * 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 { dirname, resolve } from 'path'; -import { spawn } from '../child_process'; - -async function rawRunBazelInfoRepoCache() { - const { stdout: bazelRepositoryCachePath } = await spawn('bazel', ['info', 'repository_cache'], { - stdio: 'pipe', - }); - return bazelRepositoryCachePath; -} - -export async function getBazelDiskCacheFolder() { - return resolve(dirname(await rawRunBazelInfoRepoCache()), 'disk-cache'); -} - -export async function getBazelRepositoryCacheFolder() { - return await rawRunBazelInfoRepoCache(); -} diff --git a/packages/kbn-pm/src/utils/bazel/install_tools.ts b/packages/kbn-pm/src/utils/bazel/install_tools.ts deleted file mode 100644 index e5d07748fdccf..0000000000000 --- a/packages/kbn-pm/src/utils/bazel/install_tools.ts +++ /dev/null @@ -1,105 +0,0 @@ -/* - * 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 dedent from 'dedent'; -import { resolve } from 'path'; -import { spawn } from '../child_process'; -import { readFile } from '../fs'; -import { log } from '../log'; - -async function readBazelToolsVersionFile(repoRootPath: string, versionFilename: string) { - const version = (await readFile(resolve(repoRootPath, versionFilename))).toString().trim(); - - if (!version) { - throw new Error( - `[bazel_tools] Failed on reading bazel tools versions\n ${versionFilename} file do not contain any version set` - ); - } - - return version; -} - -export async function isBazelBinAvailable(repoRootPath: string) { - try { - const installedVersion = await spawn('bazel', ['--version'], { stdio: 'pipe' }); - const bazelVersion = await readBazelToolsVersionFile(repoRootPath, '.bazelversion'); - - if (installedVersion.stdout === `bazel ${bazelVersion}`) { - return true; - } else { - log.info( - `[bazel_tools] Bazel is installed (${installedVersion.stdout}), but was expecting ${bazelVersion}` - ); - return false; - } - } catch { - return false; - } -} - -async function tryRemoveBazeliskFromYarnGlobal() { - try { - // Check if Bazelisk is installed on the yarn global scope - const { stdout: bazeliskPkgInstallStdout } = await spawn('yarn', ['global', 'list'], { - stdio: 'pipe', - }); - - // Bazelisk was found on yarn global scope so lets remove it - if (bazeliskPkgInstallStdout.includes(`@bazel/bazelisk@`)) { - await spawn('yarn', ['global', 'remove', `@bazel/bazelisk`], { - stdio: 'pipe', - }); - - log.info(`[bazel_tools] bazelisk was installed on Yarn global packages and is now removed`); - return true; - } - - return false; - } catch { - return false; - } -} - -export async function installBazelTools(repoRootPath: string) { - log.debug(`[bazel_tools] reading bazel tools versions from version files`); - const bazeliskVersion = await readBazelToolsVersionFile(repoRootPath, '.bazeliskversion'); - const bazelVersion = await readBazelToolsVersionFile(repoRootPath, '.bazelversion'); - - // Check what globals are installed - log.debug(`[bazel_tools] verify if bazelisk is installed`); - - // Check if we need to remove bazelisk from yarn - await tryRemoveBazeliskFromYarnGlobal(); - - // Test if bazel bin is available - const isBazelBinAlreadyAvailable = await isBazelBinAvailable(repoRootPath); - - // Install bazelisk if not installed - if (!isBazelBinAlreadyAvailable) { - log.info(`[bazel_tools] installing Bazel tools`); - - log.debug( - `[bazel_tools] bazelisk is not installed. Installing @bazel/bazelisk@${bazeliskVersion} and bazel@${bazelVersion}` - ); - await spawn('npm', ['install', '--global', `@bazel/bazelisk@${bazeliskVersion}`], { - env: { - USE_BAZEL_VERSION: bazelVersion, - }, - stdio: 'pipe', - }); - - const isBazelBinAvailableAfterInstall = await isBazelBinAvailable(repoRootPath); - if (!isBazelBinAvailableAfterInstall) { - throw new Error(dedent` - [bazel_tools] an error occurred when installing the Bazel tools. Please make sure you have access to npm globally installed modules on your $PATH - `); - } - } - - log.success(`[bazel_tools] all bazel tools are correctly installed`); -} diff --git a/packages/kbn-pm/src/utils/bazel/yarn.ts b/packages/kbn-pm/src/utils/bazel/yarn.ts deleted file mode 100644 index 24e44be3b3cdf..0000000000000 --- a/packages/kbn-pm/src/utils/bazel/yarn.ts +++ /dev/null @@ -1,53 +0,0 @@ -/* - * 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 { join, resolve } from 'path'; -import { isDirectory, isFile, tryRealpath, unlink } from '../fs'; - -// yarn integrity file checker -export async function removeYarnIntegrityFileIfExists(nodeModulesPath: string) { - try { - const nodeModulesRealPath = await tryRealpath(nodeModulesPath); - const yarnIntegrityFilePath = join(nodeModulesRealPath, '.yarn-integrity'); - - // check if the file exists and delete it in that case - if (await isFile(yarnIntegrityFilePath)) { - await unlink(yarnIntegrityFilePath); - } - } catch { - // no-op - } -} - -// yarn and bazel integration checkers -async function areNodeModulesPresent(kbnRootPath: string) { - try { - return await isDirectory(resolve(kbnRootPath, 'node_modules')); - } catch { - return false; - } -} - -async function haveBazelFoldersBeenCreatedBefore(kbnRootPath: string) { - try { - return ( - (await isDirectory(resolve(kbnRootPath, 'bazel-bin', 'packages'))) || - (await isDirectory(resolve(kbnRootPath, 'bazel-kibana', 'packages'))) || - (await isDirectory(resolve(kbnRootPath, 'bazel-out', 'host'))) - ); - } catch { - return false; - } -} - -export async function haveNodeModulesBeenManuallyDeleted(kbnRootPath: string) { - return ( - !(await areNodeModulesPresent(kbnRootPath)) && - (await haveBazelFoldersBeenCreatedBefore(kbnRootPath)) - ); -} diff --git a/packages/kbn-pm/src/utils/child_process.ts b/packages/kbn-pm/src/utils/child_process.ts deleted file mode 100644 index 662a83f3811b0..0000000000000 --- a/packages/kbn-pm/src/utils/child_process.ts +++ /dev/null @@ -1,67 +0,0 @@ -/* - * 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 { Writable } from 'stream'; - -import chalk from 'chalk'; -import execa from 'execa'; -import logTransformer from 'strong-log-transformer'; - -import { log } from './log'; - -const colorWheel = [chalk.cyan, chalk.magenta, chalk.blue, chalk.yellow, chalk.green]; -const getColor = () => { - const color = colorWheel.shift()!; - colorWheel.push(color); - return color; -}; - -export function spawn(command: string, args: string[], opts: execa.Options) { - return execa(command, args, { - stdio: 'inherit', - preferLocal: true, - ...opts, - }); -} - -function streamToLog(debug: boolean = true) { - return new Writable({ - objectMode: true, - write(line, _, cb) { - if (line.endsWith('\n')) { - log[debug ? 'debug' : 'write'](line.slice(0, -1)); - } else { - log[debug ? 'debug' : 'write'](line); - } - - cb(); - }, - }); -} - -export function spawnStreaming( - command: string, - args: string[], - opts: execa.Options, - { prefix, debug }: { prefix: string; debug?: boolean } -) { - const spawned = execa(command, args, { - stdio: ['ignore', 'pipe', 'pipe'], - preferLocal: true, - ...opts, - }); - - const color = getColor(); - const prefixedStdout = logTransformer({ tag: color.bold(prefix) }); - const prefixedStderr = logTransformer({ mergeMultiline: true, tag: color.bold(prefix) }); - - spawned.stdout!.pipe(prefixedStdout).pipe(streamToLog(debug)); // TypeScript note: As long as the proc stdio[1] is 'pipe', then stdout will not be null - spawned.stderr!.pipe(prefixedStderr).pipe(streamToLog(debug)); // TypeScript note: As long as the proc stdio[2] is 'pipe', then stderr will not be null - - return spawned; -} diff --git a/packages/kbn-pm/src/utils/convert_plugin_id_to_package_id.ts b/packages/kbn-pm/src/utils/convert_plugin_id_to_package_id.ts deleted file mode 100644 index 613ab6abc3a6f..0000000000000 --- a/packages/kbn-pm/src/utils/convert_plugin_id_to_package_id.ts +++ /dev/null @@ -1,21 +0,0 @@ -/* - * 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. - */ - -export function convertPluginIdToPackageId(pluginId: string) { - if (pluginId === 'core') { - // core is the only non-plugin - return `@kbn/core`; - } - - return `@kbn/${pluginId - .split('') - .flatMap((c) => (c.toUpperCase() === c ? `-${c.toLowerCase()}` : c)) - .join('')}-plugin` - .replace(/-\w(-\w)+-/g, (match) => `-${match.split('-').join('')}-`) - .replace(/-plugin-plugin$/, '-plugin'); -} diff --git a/packages/kbn-pm/src/utils/errors.ts b/packages/kbn-pm/src/utils/errors.ts deleted file mode 100644 index c0e10623a3cef..0000000000000 --- a/packages/kbn-pm/src/utils/errors.ts +++ /dev/null @@ -1,13 +0,0 @@ -/* - * 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. - */ - -export class CliError extends Error { - constructor(message: string, public readonly meta = {}) { - super(message); - } -} diff --git a/packages/kbn-pm/src/utils/fs.ts b/packages/kbn-pm/src/utils/fs.ts deleted file mode 100644 index 5739d319e08e7..0000000000000 --- a/packages/kbn-pm/src/utils/fs.ts +++ /dev/null @@ -1,113 +0,0 @@ -/* - * 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 cmdShimCb from 'cmd-shim'; -import del from 'del'; -import fs from 'fs'; -import { ncp } from 'ncp'; -import { dirname, relative } from 'path'; -import { promisify } from 'util'; - -const lstat = promisify(fs.lstat); -export const readFile = promisify(fs.readFile); -export const writeFile = promisify(fs.writeFile); -const symlink = promisify(fs.symlink); -export const chmod = promisify(fs.chmod); -const cmdShim = promisify(cmdShimCb); -const mkdir = promisify(fs.mkdir); -const realpathNative = promisify(fs.realpath.native); -export const mkdirp = async (path: string) => await mkdir(path, { recursive: true }); -export const rmdirp = async (path: string) => await del(path, { force: true }); -export const unlink = promisify(fs.unlink); -export const copyDirectory = promisify(ncp); - -async function statTest(path: string, block: (stats: fs.Stats) => boolean) { - try { - return block(await lstat(path)); - } catch (e) { - if (e.code === 'ENOENT') { - return false; - } - throw e; - } -} - -/** - * Test if a path points to a symlink. - * @param path - */ -export async function isSymlink(path: string) { - return await statTest(path, (stats) => stats.isSymbolicLink()); -} - -/** - * Test if a path points to a directory. - * @param path - */ -export async function isDirectory(path: string) { - return await statTest(path, (stats) => stats.isDirectory()); -} - -/** - * Test if a path points to a regular file. - * @param path - */ -export async function isFile(path: string) { - return await statTest(path, (stats) => stats.isFile()); -} - -/** - * Create a symlink at dest that points to src. Adapted from - * https://github.com/lerna/lerna/blob/2f1b87d9e2295f587e4ac74269f714271d8ed428/src/FileSystemUtilities.js#L103. - * - * @param src - * @param dest - * @param type 'dir', 'file', 'junction', or 'exec'. 'exec' on - * windows will use the `cmd-shim` module since symlinks can't be used - * for executable files on windows. - */ -export async function createSymlink(src: string, dest: string, type: string) { - if (process.platform === 'win32') { - if (type === 'exec') { - await cmdShim(src, dest); - } else { - await forceCreate(src, dest, type); - } - } else { - const posixType = type === 'exec' ? 'file' : type; - const relativeSource = relative(dirname(dest), src); - await forceCreate(relativeSource, dest, posixType); - } -} - -async function forceCreate(src: string, dest: string, type: string) { - try { - // If something exists at `dest` we need to remove it first. - await unlink(dest); - } catch (error) { - if (error.code !== 'ENOENT') { - throw error; - } - } - - await symlink(src, dest, type); -} - -export async function tryRealpath(path: string): Promise { - let calculatedPath = path; - - try { - calculatedPath = await realpathNative(path); - } catch (error) { - if (error.code !== 'ENOENT') { - throw error; - } - } - - return calculatedPath; -} diff --git a/packages/kbn-pm/src/utils/kibana.ts b/packages/kbn-pm/src/utils/kibana.ts deleted file mode 100644 index ece64acf3efbf..0000000000000 --- a/packages/kbn-pm/src/utils/kibana.ts +++ /dev/null @@ -1,162 +0,0 @@ -/* - * 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 Path from 'path'; -import Fs from 'fs'; - -import multimatch from 'multimatch'; -import isPathInside from 'is-path-inside'; - -import { resolveDepsForProject, YarnLock } from './yarn_lock'; -import { Log } from './log'; -import { ProjectMap, getProjects, includeTransitiveProjects } from './projects'; -import { Project } from './project'; -import { getProjectPaths } from '../config'; - -/** - * Helper class for dealing with a set of projects as children of - * the Kibana project. The kbn/pm is currently implemented to be - * more generic, where everything is an operation of generic projects, - * but that leads to exceptions where we need the kibana project and - * do things like `project.get('kibana')!`. - * - * Using this helper we can restructre the generic list of projects - * as a Kibana object which encapulates all the projects in the - * workspace and knows about the root Kibana project. - */ -export class Kibana { - static async loadFrom(rootPath: string) { - return new Kibana(await getProjects(rootPath, getProjectPaths({ rootPath }))); - } - - public readonly kibanaProject: Project; - - constructor(private readonly allWorkspaceProjects: ProjectMap) { - const kibanaProject = allWorkspaceProjects.get('kibana'); - - if (!kibanaProject) { - throw new TypeError( - 'Unable to create Kibana object without all projects, including the Kibana project.' - ); - } - - this.kibanaProject = kibanaProject; - } - - /** make an absolute path by resolving subPath relative to the kibana repo */ - getAbsolute(...subPath: string[]) { - return Path.resolve(this.kibanaProject.path, ...subPath); - } - - /** convert an absolute path to a relative path, relative to the kibana repo */ - getRelative(absolute: string) { - return Path.relative(this.kibanaProject.path, absolute); - } - - /** get a copy of the map of all projects in the kibana workspace */ - getAllProjects() { - return new Map(this.allWorkspaceProjects); - } - - /** determine if a project with the given name exists */ - hasProject(name: string) { - return this.allWorkspaceProjects.has(name); - } - - /** get a specific project, throws if the name is not known (use hasProject() first) */ - getProject(name: string) { - const project = this.allWorkspaceProjects.get(name); - - if (!project) { - throw new Error(`No package with name "${name}" in the workspace`); - } - - return project; - } - - /** get a project and all of the projects it depends on in a ProjectMap */ - getProjectAndDeps(name: string) { - const project = this.getProject(name); - return includeTransitiveProjects([project], this.allWorkspaceProjects); - } - - /** filter the projects to just those matching certain paths/include/exclude tags */ - getFilteredProjects(options: { - skipKibanaPlugins: boolean; - ossOnly: boolean; - exclude: string[]; - include: string[]; - }) { - const allProjects = this.getAllProjects(); - const filteredProjects: ProjectMap = new Map(); - - const pkgJsonPaths = Array.from(allProjects.values()).map((p) => p.packageJsonLocation); - const filteredPkgJsonGlobs = getProjectPaths({ - ...options, - rootPath: this.kibanaProject.path, - }).map((g) => Path.resolve(g, 'package.json')); - const matchingPkgJsonPaths = multimatch(pkgJsonPaths, filteredPkgJsonGlobs); - - for (const project of allProjects.values()) { - const pathMatches = matchingPkgJsonPaths.includes(project.packageJsonLocation); - const notExcluded = !options.exclude.includes(project.name); - const isIncluded = !options.include.length || options.include.includes(project.name); - - if (pathMatches && notExcluded && isIncluded) { - filteredProjects.set(project.name, project); - } - } - - return filteredProjects; - } - - isPartOfRepo(project: Project) { - return ( - project.path === this.kibanaProject.path || - isPathInside(project.path, this.kibanaProject.path) - ); - } - - isOutsideRepo(project: Project) { - return !this.isPartOfRepo(project); - } - - resolveAllProductionDependencies(yarnLock: YarnLock, log: Log) { - const kibanaDeps = resolveDepsForProject({ - project: this.kibanaProject, - yarnLock, - kbn: this, - includeDependentProject: true, - productionDepsOnly: true, - log, - })!; - - const xpackDeps = resolveDepsForProject({ - project: this.getProject('x-pack')!, - yarnLock, - kbn: this, - includeDependentProject: true, - productionDepsOnly: true, - log, - })!; - - return new Map([...kibanaDeps.entries(), ...xpackDeps.entries()]); - } - - getUuid() { - try { - return Fs.readFileSync(this.getAbsolute('data/uuid'), 'utf-8').trim(); - } catch (error) { - if (error.code === 'ENOENT') { - return undefined; - } - - throw error; - } - } -} diff --git a/packages/kbn-pm/src/utils/link_project_executables.test.ts b/packages/kbn-pm/src/utils/link_project_executables.test.ts deleted file mode 100644 index 5045474321ce5..0000000000000 --- a/packages/kbn-pm/src/utils/link_project_executables.test.ts +++ /dev/null @@ -1,114 +0,0 @@ -/* - * 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. - */ - -/* eslint-disable @typescript-eslint/no-var-requires */ - -jest.mock('./fs'); - -import { resolve } from 'path'; - -import { ToolingLogCollectingWriter } from '@kbn/tooling-log'; - -import { absolutePathSnapshotSerializer, stripAnsiSnapshotSerializer } from '../test_helpers'; -import { linkProjectExecutables } from './link_project_executables'; -import { Project } from './project'; -import { buildProjectGraph } from './projects'; -import { log } from './log'; - -const logWriter = new ToolingLogCollectingWriter(); -log.setWriters([logWriter]); -beforeEach(() => { - logWriter.messages.length = 0; -}); - -const projectsByName = new Map([ - [ - 'foo', - new Project( - { - dependencies: { - bar: 'link:../bar', - }, - name: 'foo', - }, - resolve(__dirname, 'foo') - ), - ], - [ - 'bar', - new Project( - { - bin: 'bin/bar.js', - name: 'bar', - }, - resolve(__dirname, 'bar') - ), - ], - [ - 'baz', - new Project( - { - devDependencies: { - bar: 'link:../bar', - }, - name: 'baz', - }, - resolve(__dirname, 'baz') - ), - ], -]); -(projectsByName.get('bar') as Project).isSinglePackageJsonProject = true; - -const projectGraph = buildProjectGraph(projectsByName); - -function getFsMockCalls() { - const fs = require('./fs'); - const fsMockCalls: { [key: string]: any[][] } = {}; - Object.keys(fs).map((key) => { - if (jest.isMockFunction(fs[key])) { - fsMockCalls[key] = fs[key].mock.calls; - } - }); - return fsMockCalls; -} - -expect.addSnapshotSerializer(absolutePathSnapshotSerializer); -expect.addSnapshotSerializer(stripAnsiSnapshotSerializer); - -afterEach(() => { - jest.resetAllMocks(); - jest.restoreAllMocks(); -}); - -describe('bin script points nowhere', () => { - test('does not try to create symlink on node_modules/.bin for that bin script', async () => { - const fs = require('./fs'); - fs.isFile.mockReturnValue(false); - fs.isDirectory.mockReturnValue(true); - - await linkProjectExecutables(projectsByName, projectGraph); - expect(getFsMockCalls()).toMatchSnapshot('fs module calls'); - }); -}); - -describe('bin script points to a file', () => { - test('creates a symlink for the project bin into the roots project node_modules/.bin directory as well as node_modules/.bin directory symlink into the roots one', async () => { - const fs = require('./fs'); - fs.isFile.mockReturnValue(true); - fs.isDirectory.mockReturnValue(false); - - await linkProjectExecutables(projectsByName, projectGraph); - - expect(getFsMockCalls()).toMatchSnapshot('fs module calls'); - expect(logWriter.messages).toMatchInlineSnapshot(` - Array [ - debg Linking package executables, - ] - `); - }); -}); diff --git a/packages/kbn-pm/src/utils/link_project_executables.ts b/packages/kbn-pm/src/utils/link_project_executables.ts deleted file mode 100644 index 59179d06ac7f6..0000000000000 --- a/packages/kbn-pm/src/utils/link_project_executables.ts +++ /dev/null @@ -1,70 +0,0 @@ -/* - * 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 { dirname, relative, resolve, sep } from 'path'; - -import { chmod, createSymlink, isFile, mkdirp } from './fs'; -import { log } from './log'; -import { ProjectGraph, ProjectMap } from './projects'; - -/** - * Yarn does not link the executables from dependencies that are installed - * using `link:` https://github.com/yarnpkg/yarn/pull/5046 - * - * We simulate this functionality by walking through each project's project - * dependencies, and manually linking their executables if defined. The logic - * for linking was mostly adapted from lerna: https://github.com/lerna/lerna/blob/1d7eb9eeff65d5a7de64dea73613b1bf6bfa8d57/src/PackageUtilities.js#L348 - */ -export async function linkProjectExecutables( - projectsByName: ProjectMap, - projectGraph: ProjectGraph -) { - log.debug(`Linking package executables`); - - // Find root and generate executables from dependencies for it - let rootProject = null; - let rootProjectDeps = [] as any; - for (const [projectName, projectDeps] of projectGraph) { - const project = projectsByName.get(projectName)!; - if (project.isSinglePackageJsonProject) { - rootProject = projectsByName.get(projectName); - rootProjectDeps = projectDeps; - break; - } - } - - if (!rootProject) { - throw new Error('Could not finding root project while linking package executables'); - } - - // Prepare root project node_modules/.bin - const rootBinsDir = resolve(rootProject.nodeModulesLocation, '.bin'); - for (const rootProjectDep of rootProjectDeps) { - const executables = rootProjectDep.getExecutables(); - for (const name of Object.keys(executables)) { - const srcPath = executables[name]; - - // existing logic from lerna -- ensure that the bin we are going to - // point to exists or ignore it - if (!(await isFile(srcPath))) { - continue; - } - - const dest = resolve(rootBinsDir, name); - - // Get relative project path with normalized path separators. - const rootProjectRelativePath = relative(rootProject.path, srcPath).split(sep).join('/'); - - log.debug(`[${rootProject.name}] ${name} -> ${rootProjectRelativePath}`); - - await mkdirp(dirname(dest)); - await createSymlink(srcPath, dest, 'exec'); - await chmod(dest, '755'); - } - } -} diff --git a/packages/kbn-pm/src/utils/log.ts b/packages/kbn-pm/src/utils/log.ts deleted file mode 100644 index a70f967adc400..0000000000000 --- a/packages/kbn-pm/src/utils/log.ts +++ /dev/null @@ -1,42 +0,0 @@ -/* - * 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 { - ToolingLog, - ToolingLogTextWriter, - LogLevel, - parseLogLevel, - ParsedLogLevel, -} from '@kbn/tooling-log'; - -class Log extends ToolingLog { - private logLevel!: ParsedLogLevel; - - constructor() { - super(); - this.setLogLevel('info'); - } - - setLogLevel(level: LogLevel) { - this.logLevel = parseLogLevel(level); - this.setWriters([ - new ToolingLogTextWriter({ - level: this.logLevel.name, - writeTo: process.stdout, - }), - ]); - } - - wouldLogLevel(level: LogLevel) { - return this.logLevel.flags[level]; - } -} - -export const log = new Log(); -export type { LogLevel }; -export { Log }; diff --git a/packages/kbn-pm/src/utils/package_json.ts b/packages/kbn-pm/src/utils/package_json.ts deleted file mode 100644 index e8ed8d0a7f8f5..0000000000000 --- a/packages/kbn-pm/src/utils/package_json.ts +++ /dev/null @@ -1,30 +0,0 @@ -/* - * 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 readPkg from 'read-pkg'; -import writePkg from 'write-pkg'; - -export interface IPackageJson { - [key: string]: any; -} -export interface IPackageDependencies { - [key: string]: string; -} -export interface IPackageScripts { - [key: string]: string; -} - -export function readPackageJson(cwd: string): IPackageJson { - return readPkg({ cwd, normalize: false }); -} - -export function writePackageJson(path: string, json: IPackageJson) { - return writePkg(path, json); -} - -export const isLinkDependency = (depVersion: string) => depVersion.startsWith('link:'); diff --git a/packages/kbn-pm/src/utils/parallelize.test.ts b/packages/kbn-pm/src/utils/parallelize.test.ts deleted file mode 100644 index 2694838ae727a..0000000000000 --- a/packages/kbn-pm/src/utils/parallelize.test.ts +++ /dev/null @@ -1,122 +0,0 @@ -/* - * 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 { parallelizeBatches } from './parallelize'; - -// As promises resolve async, we use this helper to wait for all promises that -// have been resolved to complete (aka call `then`). -const tick = () => - new Promise((resolve) => { - setTimeout(resolve, 0); - }); - -test('parallelizes batches', async () => { - const foo = createPromiseWithResolve(); - const bar = createPromiseWithResolve(); - const baz = createPromiseWithResolve(); - - const batches = [[foo, bar], [baz]]; - const parallelize = parallelizeBatches(batches, async (obj) => { - obj.called = true; - await obj.promise; - }); - - const completed: string[] = []; - parallelize.then(() => { - completed.push('parallelizeBatches'); - }); - foo.promise.then(() => { - completed.push('foo'); - }); - bar.promise.then(() => { - completed.push('bar'); - }); - baz.promise.then(() => { - completed.push('baz'); - }); - - expect(foo.called).toBe(true); - expect(bar.called).toBe(true); - expect(baz.called).toBe(false); - expect(completed).toEqual([]); - - bar.resolve(); - await tick(); - - expect(completed).toEqual(['bar']); - expect(baz.called).toBe(false); - - foo.resolve(); - await tick(); - - expect(completed).toEqual(['bar', 'foo']); - expect(baz.called).toBe(true); - - baz.resolve(); - await tick(); - - expect(completed).toEqual(['bar', 'foo', 'baz', 'parallelizeBatches']); -}); - -test('schedules at most 4 calls at the same time (concurrency)', async () => { - const foo = createPromiseWithResolve(); - const bar = createPromiseWithResolve(); - const baz = createPromiseWithResolve(); - const quux = createPromiseWithResolve(); - const foobar = createPromiseWithResolve(); - - const batches = [[foo, bar, baz, quux, foobar]]; - const parallelize = parallelizeBatches(batches, async (obj) => { - obj.called = true; - await obj.promise; - }); - - expect(foo.called).toBe(true); - expect(bar.called).toBe(true); - expect(baz.called).toBe(true); - expect(quux.called).toBe(true); - expect(foobar.called).toBe(false); - - foo.resolve(); - await tick(); - - expect(foobar.called).toBe(true); - - bar.resolve(); - baz.resolve(); - quux.resolve(); - foobar.resolve(); - await tick(); - - await expect(parallelize).resolves.toBe(undefined); -}); - -test('rejects if any promise rejects', async () => { - const foo = createPromiseWithResolve(); - const bar = createPromiseWithResolve(); - const baz = createPromiseWithResolve(); - - const batches = [[foo, bar], [baz]]; - const parallelize = parallelizeBatches(batches, async (obj) => { - await obj.promise; - }); - - foo.reject(new Error('foo failed')); - - await expect(parallelize).rejects.toThrow('foo failed'); -}); - -function createPromiseWithResolve() { - let resolve: (val?: any) => void; - let reject: (err?: any) => void; - const promise = new Promise((res, rej) => { - resolve = res; - reject = rej; - }); - return { promise, resolve: resolve!, reject: reject!, called: false }; -} diff --git a/packages/kbn-pm/src/utils/parallelize.ts b/packages/kbn-pm/src/utils/parallelize.ts deleted file mode 100644 index afd953fdcccb7..0000000000000 --- a/packages/kbn-pm/src/utils/parallelize.ts +++ /dev/null @@ -1,49 +0,0 @@ -/* - * 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. - */ - -export async function parallelizeBatches(batches: T[][], fn: (item: T) => Promise) { - for (const batch of batches) { - // We need to make sure the entire batch has completed before we can move on - // to the next batch - await parallelize(batch, fn); - } -} - -export async function parallelize(items: T[], fn: (item: T) => Promise, concurrency = 4) { - if (items.length === 0) { - return; - } - - return new Promise((resolve, reject) => { - let activePromises = 0; - const values = items.slice(0); - - async function scheduleItem(item: T) { - activePromises++; - - try { - await fn(item); - - activePromises--; - - if (values.length > 0) { - // We have more work to do, so we schedule the next promise - scheduleItem(values.shift()!); - } else if (activePromises === 0) { - // We have no more values left, and all items have completed, so we've - // completed all the work. - resolve(); - } - } catch (error) { - reject(error); - } - } - - values.splice(0, concurrency).map(scheduleItem); - }); -} diff --git a/packages/kbn-pm/src/utils/project.test.ts b/packages/kbn-pm/src/utils/project.test.ts deleted file mode 100644 index 389dbf123cd52..0000000000000 --- a/packages/kbn-pm/src/utils/project.test.ts +++ /dev/null @@ -1,88 +0,0 @@ -/* - * 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 { join, resolve } from 'path'; - -import { IPackageJson } from './package_json'; -import { Project } from './project'; - -const rootPath = resolve(`${__dirname}/__fixtures__/kibana`); - -const createProjectWith = (packageJson: IPackageJson, path = '') => - new Project( - { - name: 'kibana', - version: '1.0.0', - ...packageJson, - }, - join(rootPath, path) - ); - -describe('fromPath', () => { - test('reads project.json at path and constructs Project', async () => { - const kibana = await Project.fromPath(rootPath); - - expect(kibana.name).toBe('kibana'); - }); -}); - -test('fields', async () => { - const kibana = createProjectWith({ - dependencies: { - foo: '1.2.3', - }, - scripts: { - test: 'jest', - }, - }); - - expect(kibana.name).toBe('kibana'); - - expect(kibana.hasDependencies()).toBe(true); - expect(kibana.allDependencies).toEqual({ foo: '1.2.3' }); - - expect(kibana.hasScript('test')).toBe(true); - expect(kibana.hasScript('build')).toBe(false); -}); - -describe('#getExecutables()', () => { - test('converts bin:string to an object with absolute paths', () => { - const project = createProjectWith({ - bin: './bin/script.js', - }); - - expect(project.getExecutables()).toEqual({ - kibana: resolve(rootPath, 'bin/script.js'), - }); - }); - - test('resolves absolute paths when bin is an object', () => { - const project = createProjectWith({ - bin: { - script1: 'bin/script1.js', - script2: './bin/script2.js', - }, - }); - - expect(project.getExecutables()).toEqual({ - script1: resolve(rootPath, 'bin/script1.js'), - script2: resolve(rootPath, 'bin/script2.js'), - }); - }); - - test('returns empty object when bin is missing, or falsy', () => { - expect(createProjectWith({}).getExecutables()).toEqual({}); - expect(createProjectWith({ bin: null }).getExecutables()).toEqual({}); - expect(createProjectWith({ bin: false }).getExecutables()).toEqual({}); - expect(createProjectWith({ bin: 0 }).getExecutables()).toEqual({}); - }); - - test('throws CliError when bin is something strange', () => { - expect(() => createProjectWith({ bin: 1 }).getExecutables()).toThrowErrorMatchingSnapshot(); - }); -}); diff --git a/packages/kbn-pm/src/utils/project.ts b/packages/kbn-pm/src/utils/project.ts deleted file mode 100644 index 842f828543116..0000000000000 --- a/packages/kbn-pm/src/utils/project.ts +++ /dev/null @@ -1,166 +0,0 @@ -/* - * 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 Fs from 'fs'; -import Path from 'path'; -import { inspect } from 'util'; - -import { CliError } from './errors'; -import { log } from './log'; -import { - IPackageDependencies, - IPackageJson, - IPackageScripts, - isLinkDependency, - readPackageJson, -} from './package_json'; -import { runScriptInPackage, runScriptInPackageStreaming } from './scripts'; - -interface BuildConfig { - skip?: boolean; - oss?: boolean; -} - -interface CleanConfig { - extraPatterns?: string[]; -} - -export class Project { - public static async fromPath(path: string) { - const pkgJson = await readPackageJson(path); - return new Project(pkgJson, path); - } - - /** parsed package.json */ - public readonly json: IPackageJson; - /** absolute path to the package.json file in the project */ - public readonly packageJsonLocation: string; - /** absolute path to the node_modules in the project (might not actually exist) */ - public readonly nodeModulesLocation: string; - /** absolute path to the target directory in the project (might not actually exist) */ - public readonly targetLocation: string; - /** absolute path to the directory containing the project */ - public readonly path: string; - /** the version of the project */ - public readonly version: string; - /** merged set of dependencies of the project, [name => version range] */ - public readonly allDependencies: IPackageDependencies; - /** regular dependencies of the project, [name => version range] */ - public readonly productionDependencies: IPackageDependencies; - /** development dependencies of the project, [name => version range] */ - public readonly devDependencies: IPackageDependencies; - /** scripts defined in the package.json file for the project [name => body] */ - public readonly scripts: IPackageScripts; - /** states if this project is a Bazel package */ - public readonly bazelPackage: boolean; - - public isSinglePackageJsonProject = false; - - constructor(packageJson: IPackageJson, projectPath: string) { - this.json = Object.freeze(packageJson); - this.path = projectPath; - - this.packageJsonLocation = Path.resolve(this.path, 'package.json'); - this.nodeModulesLocation = Path.resolve(this.path, 'node_modules'); - this.targetLocation = Path.resolve(this.path, 'target'); - - this.version = this.json.version; - this.productionDependencies = this.json.dependencies || {}; - this.devDependencies = this.json.devDependencies || {}; - this.allDependencies = { - ...this.devDependencies, - ...this.productionDependencies, - }; - this.isSinglePackageJsonProject = this.json.name === 'kibana'; - - this.scripts = this.json.scripts || {}; - - this.bazelPackage = - !this.isSinglePackageJsonProject && Fs.existsSync(Path.resolve(this.path, 'BUILD.bazel')); - } - - public get name(): string { - return this.json.name; - } - - public getBuildConfig(): BuildConfig { - return (this.json.kibana && this.json.kibana.build) || {}; - } - - public getCleanConfig(): CleanConfig { - return (this.json.kibana && this.json.kibana.clean) || {}; - } - - public isBazelPackage() { - return this.bazelPackage; - } - - public isFlaggedAsDevOnly() { - return !!(this.json.kibana && this.json.kibana.devOnly); - } - - public hasScript(name: string) { - return name in this.scripts; - } - - public getExecutables(): { [key: string]: string } { - const raw = this.json.bin; - - if (!raw) { - return {}; - } - - if (typeof raw === 'string') { - return { - [this.name]: Path.resolve(this.path, raw), - }; - } - - if (typeof raw === 'object') { - const binsConfig: { [k: string]: string } = {}; - for (const binName of Object.keys(raw)) { - binsConfig[binName] = Path.resolve(this.path, raw[binName]); - } - return binsConfig; - } - - throw new CliError( - `[${this.name}] has an invalid "bin" field in its package.json, ` + - `expected an object or a string`, - { - binConfig: inspect(raw), - package: `${this.name} (${this.packageJsonLocation})`, - } - ); - } - - public async runScript(scriptName: string, args: string[] = []) { - log.info(`Running script [${scriptName}] in [${this.name}]:`); - return runScriptInPackage(scriptName, args, this); - } - - public runScriptStreaming( - scriptName: string, - options: { args?: string[]; debug?: boolean } = {} - ) { - return runScriptInPackageStreaming({ - script: scriptName, - args: options.args || [], - pkg: this, - debug: options.debug, - }); - } - - public hasDependencies() { - return Object.keys(this.allDependencies).length > 0; - } - - public isEveryDependencyLocal() { - return Object.values(this.allDependencies).every((dep) => isLinkDependency(dep)); - } -} diff --git a/packages/kbn-pm/src/utils/projects.test.ts b/packages/kbn-pm/src/utils/projects.test.ts deleted file mode 100644 index c87876642cf0b..0000000000000 --- a/packages/kbn-pm/src/utils/projects.test.ts +++ /dev/null @@ -1,254 +0,0 @@ -/* - * 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 { mkdir, symlink } from 'fs'; -import { join, resolve } from 'path'; -import del from 'del'; -import { promisify } from 'util'; - -import { getProjectPaths } from '../config'; -import { Project } from './project'; -import { - buildProjectGraph, - getProjects, - includeTransitiveProjects, - ProjectGraph, - ProjectMap, - topologicallyBatchProjects, -} from './projects'; - -const rootPath = resolve(__dirname, '__fixtures__/kibana'); -const rootPlugins = join(rootPath, 'plugins'); - -describe('#getProjects', () => { - beforeAll(async () => { - await promisify(mkdir)(rootPlugins); - - await promisify(symlink)( - join(__dirname, '__fixtures__/symlinked-plugins/corge'), - join(rootPlugins, 'corge') - ); - }); - - afterAll(async () => await del(rootPlugins)); - - test('find all packages in the packages directory', async () => { - const projects = await getProjects(rootPath, ['packages/*']); - - const expectedProjects = ['bar', 'foo']; - - expect(projects.size).toBe(2); - expect([...projects.keys()]).toEqual(expect.arrayContaining(expectedProjects)); - }); - - test('can specify root as a separate project', async () => { - const projects = await getProjects(rootPath, ['.']); - - expect(projects.size).toBe(1); - expect([...projects.keys()]).toEqual(['kibana']); - }); - - test('handles packages outside root', async () => { - const projects = await getProjects(rootPath, ['../plugins/*']); - - const expectedProjects = ['baz', 'quux', 'zorge']; - - expect(projects.size).toBe(3); - expect([...projects.keys()]).toEqual(expect.arrayContaining(expectedProjects)); - }); - - test('throws if multiple projects has the same name', async () => { - await expect( - getProjects(rootPath, ['../plugins/*', '../other-plugins/*']) - ).rejects.toHaveProperty('message', 'There are multiple projects with the same name [baz]'); - }); - - test('includes additional projects in package.json', async () => { - const projectPaths = getProjectPaths({ rootPath }); - const projects = await getProjects(rootPath, projectPaths); - - const expectedProjects = [ - 'kibana', - 'bar', - 'foo', - 'with-additional-projects', - 'quux', - 'baz', - 'bar', - ]; - - expect([...projects.keys()]).toEqual(expect.arrayContaining(expectedProjects)); - expect(projects.size).toBe(expectedProjects.length); - }); - - describe('with exclude/include filters', () => { - let projectPaths: string[]; - beforeEach(() => { - projectPaths = getProjectPaths({ rootPath }); - }); - - test('excludes projects specified in `exclude` filter', async () => { - const projects = await getProjects(rootPath, projectPaths, { - exclude: ['foo', 'bar', 'baz'], - }); - - expect([...projects.keys()].sort()).toEqual([ - 'corge', - 'kibana', - 'quux', - 'with-additional-projects', - ]); - }); - - test('ignores unknown projects specified in `exclude` filter', async () => { - const projects = await getProjects(rootPath, projectPaths, { - exclude: ['unknown-foo', 'bar', 'unknown-baz'], - }); - - expect([...projects.keys()].sort()).toEqual([ - 'baz', - 'corge', - 'foo', - 'kibana', - 'quux', - 'with-additional-projects', - ]); - }); - - test('includes only projects specified in `include` filter', async () => { - const projects = await getProjects(rootPath, projectPaths, { - include: ['foo', 'bar'], - }); - - expect([...projects.keys()].sort()).toEqual(['bar', 'foo']); - }); - - test('ignores unknown projects specified in `include` filter', async () => { - const projects = await getProjects(rootPath, projectPaths, { - include: ['unknown-foo', 'bar', 'unknown-baz'], - }); - - expect([...projects.keys()].sort()).toEqual(['bar']); - }); - - test('respects both `include` and `exclude` filters if specified at the same time', async () => { - const projects = await getProjects(rootPath, projectPaths, { - exclude: ['bar'], - include: ['foo', 'bar', 'baz'], - }); - - expect([...projects.keys()].sort()).toEqual(['baz', 'foo']); - }); - - test('does not return any project if wrong `include` filter is specified', async () => { - const projects = await getProjects(rootPath, projectPaths, { - include: ['unknown-foo', 'unknown-bar'], - }); - - expect(projects.size).toBe(0); - }); - - test('does not return any project if `exclude` filter is specified for all projects', async () => { - const projects = await getProjects(rootPath, projectPaths, { - exclude: ['kibana', 'bar', 'corge', 'foo', 'with-additional-projects', 'quux', 'baz'], - }); - - expect(projects.size).toBe(0); - }); - - test('does not return any project if `exclude` and `include` filters are mutually exclusive', async () => { - const projects = await getProjects(rootPath, projectPaths, { - exclude: ['foo', 'bar'], - include: ['foo', 'bar'], - }); - - expect(projects.size).toBe(0); - }); - }); -}); - -describe('#buildProjectGraph', () => { - test('builds full project graph', async () => { - const allProjects = await getProjects(rootPath, ['.', 'packages/*', '../plugins/*']); - const graph = buildProjectGraph(allProjects); - - const expected: { [k: string]: string[] } = {}; - for (const [projectName, projects] of graph.entries()) { - expected[projectName] = projects.map((project: Project) => project.name); - } - - expect(expected).toMatchSnapshot(); - }); -}); - -describe('#topologicallyBatchProjects', () => { - let projects: ProjectMap; - let graph: ProjectGraph; - beforeEach(async () => { - projects = await getProjects(rootPath, ['.', 'packages/*', '../plugins/*']); - graph = buildProjectGraph(projects); - }); - - test('batches projects topologically based on their project dependencies', async () => { - const batches = topologicallyBatchProjects(projects, graph); - - const expectedBatches = batches.map((batch) => batch.map((project) => project.name)); - - expect(expectedBatches).toMatchSnapshot(); - }); - - test('batches projects topologically even if graph contains projects not presented in the project map', async () => { - // Make sure that the project we remove really existed in the projects map. - expect(projects.delete('foo')).toBe(true); - - const batches = topologicallyBatchProjects(projects, graph); - - const expectedBatches = batches.map((batch) => batch.map((project) => project.name)); - - expect(expectedBatches).toMatchSnapshot(); - }); -}); - -describe('#includeTransitiveProjects', () => { - test('includes transitive dependencies for Kibana package', async () => { - const projects = await getProjects(rootPath, ['.', 'packages/*']); - - const kibana = projects.get('kibana')!; - const withTransitive = includeTransitiveProjects([kibana], projects); - - expect([...withTransitive.keys()]).toEqual(['kibana', 'foo']); - }); - - test('handles multiple projects with same transitive dep', async () => { - const projects = await getProjects(rootPath, ['.', 'packages/*']); - - const kibana = projects.get('kibana')!; - const bar = projects.get('bar')!; - const withTransitive = includeTransitiveProjects([kibana, bar], projects); - - expect([...withTransitive.keys()]).toEqual(['kibana', 'bar', 'foo']); - }); - - test('handles projects with no deps', async () => { - const projects = await getProjects(rootPath, ['.', 'packages/*']); - - const foo = projects.get('foo')!; - const withTransitive = includeTransitiveProjects([foo], projects); - - expect([...withTransitive.keys()]).toEqual(['foo']); - }); - - test('includes dependencies of dependencies', async () => { - const projects = await getProjects(rootPath, ['.', 'packages/*', '../plugins/*']); - - const quux = projects.get('quux')!; - const withTransitive = includeTransitiveProjects([quux], projects); - - expect([...withTransitive.keys()]).toEqual(['quux']); - }); -}); diff --git a/packages/kbn-pm/src/utils/projects.ts b/packages/kbn-pm/src/utils/projects.ts deleted file mode 100644 index e30dfc9f4c876..0000000000000 --- a/packages/kbn-pm/src/utils/projects.ts +++ /dev/null @@ -1,214 +0,0 @@ -/* - * 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 globSync from 'glob'; -import path from 'path'; -import { promisify } from 'util'; - -import { CliError } from './errors'; -import { log } from './log'; -import { Project } from './project'; - -const glob = promisify(globSync); - -/** a Map of project names to Project instances */ -export type ProjectMap = Map; -export type ProjectGraph = Map; -export interface IProjectsOptions { - include?: string[]; - exclude?: string[]; -} - -export async function getProjects( - rootPath: string, - projectsPathsPatterns: string[], - { include = [], exclude = [] }: IProjectsOptions = {}, - bazelOnly: boolean = false -) { - const projects: ProjectMap = new Map(); - - for (const pattern of projectsPathsPatterns) { - const pathsToProcess = await packagesFromGlobPattern({ pattern, rootPath }); - - for (const filePath of pathsToProcess) { - const projectConfigPath = normalize(filePath); - const projectDir = path.dirname(projectConfigPath); - const project = await Project.fromPath(projectDir); - - const excludeProject = - exclude.includes(project.name) || - (include.length > 0 && !include.includes(project.name)) || - (bazelOnly && !project.isBazelPackage()); - - if (excludeProject) { - continue; - } - - if (projects.has(project.name)) { - throw new CliError(`There are multiple projects with the same name [${project.name}]`, { - name: project.name, - paths: [project.path, projects.get(project.name)!.path], - }); - } - - projects.set(project.name, project); - } - } - - return projects; -} - -export async function getNonBazelProjectsOnly(projects: ProjectMap) { - const bazelProjectsOnly: ProjectMap = new Map(); - - for (const project of projects.values()) { - if (!project.isBazelPackage()) { - bazelProjectsOnly.set(project.name, project); - } - } - - return bazelProjectsOnly; -} - -export async function getBazelProjectsOnly(projects: ProjectMap) { - const bazelProjectsOnly: ProjectMap = new Map(); - - for (const project of projects.values()) { - if (project.isBazelPackage()) { - bazelProjectsOnly.set(project.name, project); - } - } - - return bazelProjectsOnly; -} - -function packagesFromGlobPattern({ pattern, rootPath }: { pattern: string; rootPath: string }) { - const globOptions = { - cwd: rootPath, - - // Should throw in case of unusual errors when reading the file system - strict: true, - - // Always returns absolute paths for matched files - absolute: true, - - // Do not match ** against multiple filenames - // (This is only specified because we currently don't have a need for it.) - noglobstar: true, - }; - - return glob(path.join(pattern, 'package.json'), globOptions); -} - -// https://github.com/isaacs/node-glob/blob/master/common.js#L104 -// glob always returns "\\" as "/" in windows, so everyone -// gets normalized because we can't have nice things. -function normalize(dir: string) { - return path.normalize(dir); -} - -export function buildProjectGraph(projects: ProjectMap) { - const projectGraph: ProjectGraph = new Map(); - - for (const project of projects.values()) { - const projectDeps: Project[] = []; - const dependencies = project.allDependencies; - - if (!project.isSinglePackageJsonProject && Object.keys(dependencies).length > 0) { - log.warning( - `${project.name} is not allowed to hold local dependencies and they will be discarded. Please declare them at the root package.json` - ); - } - - if (!project.isSinglePackageJsonProject) { - projectGraph.set(project.name, projectDeps); - continue; - } - - for (const depName of Object.keys(dependencies)) { - if (projects.has(depName)) { - const dep = projects.get(depName)!; - projectDeps.push(dep); - } - } - - projectGraph.set(project.name, projectDeps); - } - - return projectGraph; -} - -export function topologicallyBatchProjects( - projectsToBatch: ProjectMap, - projectGraph: ProjectGraph -) { - // We're going to be chopping stuff out of this list, so copy it. - const projectsLeftToBatch = new Set(projectsToBatch.keys()); - const batches = []; - - while (projectsLeftToBatch.size > 0) { - // Get all projects that have no remaining dependencies within the repo - // that haven't yet been picked. - const batch = []; - for (const projectName of projectsLeftToBatch) { - const projectDeps = projectGraph.get(projectName)!; - const needsDependenciesBatched = projectDeps.some((dep) => projectsLeftToBatch.has(dep.name)); - - if (!needsDependenciesBatched) { - batch.push(projectsToBatch.get(projectName)!); - } - } - - // If we weren't able to find a project with no remaining dependencies, - // then we've encountered a cycle in the dependency graph. - const hasCycles = batch.length === 0; - if (hasCycles) { - const cycleProjectNames = [...projectsLeftToBatch]; - const message = - 'Encountered a cycle in the dependency graph. Projects in cycle are:\n' + - cycleProjectNames.join(', '); - - throw new CliError(message); - } - - batches.push(batch); - - batch.forEach((project) => projectsLeftToBatch.delete(project.name)); - } - - return batches; -} - -export function includeTransitiveProjects( - subsetOfProjects: Project[], - allProjects: ProjectMap, - { onlyProductionDependencies = false } = {} -) { - const projectsWithDependents: ProjectMap = new Map(); - - // the current list of packages we are expanding using breadth-first-search - const toProcess = [...subsetOfProjects]; - - while (toProcess.length > 0) { - const project = toProcess.shift()!; - - const dependencies = onlyProductionDependencies - ? project.productionDependencies - : project.allDependencies; - - Object.keys(dependencies).forEach((dep) => { - if (allProjects.has(dep)) { - toProcess.push(allProjects.get(dep)!); - } - }); - - projectsWithDependents.set(project.name, project); - } - - return projectsWithDependents; -} diff --git a/packages/kbn-pm/src/utils/projects_tree.test.ts b/packages/kbn-pm/src/utils/projects_tree.test.ts deleted file mode 100644 index 73626b2429867..0000000000000 --- a/packages/kbn-pm/src/utils/projects_tree.test.ts +++ /dev/null @@ -1,40 +0,0 @@ -/* - * 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 { resolve } from 'path'; - -import { getProjectPaths } from '../config'; -import { stripAnsiSnapshotSerializer } from '../test_helpers'; -import { getProjects } from './projects'; -import { renderProjectsTree } from './projects_tree'; - -const rootPath = resolve(`${__dirname}/__fixtures__/kibana`); - -expect.addSnapshotSerializer(stripAnsiSnapshotSerializer); - -test('handles projects with root folder', async () => { - const projects = await getProjects(rootPath, ['.', 'packages/*']); - - const tree = await renderProjectsTree(rootPath, projects); - expect(tree).toMatchSnapshot(); -}); - -test('handles projects outside root folder', async () => { - const projects = await getProjects(rootPath, ['.', 'packages/*', '../plugins/*']); - - const tree = await renderProjectsTree(rootPath, projects); - expect(tree).toMatchSnapshot(); -}); - -test('handles projects within projects outside root folder', async () => { - const projectPaths = getProjectPaths({ rootPath }); - const projects = await getProjects(rootPath, projectPaths); - - const tree = await renderProjectsTree(rootPath, projects); - expect(tree).toMatchSnapshot(); -}); diff --git a/packages/kbn-pm/src/utils/projects_tree.ts b/packages/kbn-pm/src/utils/projects_tree.ts deleted file mode 100644 index 8eded35e063ae..0000000000000 --- a/packages/kbn-pm/src/utils/projects_tree.ts +++ /dev/null @@ -1,150 +0,0 @@ -/* - * 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 chalk from 'chalk'; -import path from 'path'; - -import { Project } from './project'; - -const projectKey = Symbol('__project'); - -export function renderProjectsTree(rootPath: string, projects: Map) { - const projectsTree = buildProjectsTree(rootPath, projects); - return treeToString(createTreeStructure(projectsTree)); -} - -export interface ITree { - name?: string; - children?: ITreeChildren; -} -// eslint-disable-next-line @typescript-eslint/no-empty-interface -interface ITreeChildren extends Array {} - -type DirOrProjectName = string | typeof projectKey; - -// eslint-disable-next-line @typescript-eslint/no-empty-interface -interface IProjectsTree extends Map {} - -export function treeToString(tree: ITree) { - return [tree.name].concat(childrenToStrings(tree.children, '')).join('\n'); -} - -function childrenToStrings(tree: ITreeChildren | undefined, treePrefix: string) { - if (tree === undefined) { - return []; - } - - let strings: string[] = []; - tree.forEach((node, index) => { - const isLastNode = tree.length - 1 === index; - const nodePrefix = isLastNode ? '└── ' : '├── '; - const childPrefix = isLastNode ? ' ' : '│ '; - const childrenPrefix = treePrefix + childPrefix; - - strings.push(`${treePrefix}${nodePrefix}${node.name}`); - strings = strings.concat(childrenToStrings(node.children, childrenPrefix)); - }); - return strings; -} - -function createTreeStructure(tree: IProjectsTree): ITree { - let name: string | undefined; - const children: ITreeChildren = []; - - for (const [dir, project] of tree.entries()) { - // This is a leaf node (aka a project) - if (typeof project === 'string') { - name = chalk.green(project); - continue; - } - - // If there's only one project and the key indicates it's a leaf node, we - // know that we're at a package folder that contains a package.json, so we - // "inline it" so we don't get unnecessary levels, i.e. we'll just see - // `foo` instead of `foo -> foo`. - if (project.size === 1 && project.has(projectKey)) { - const projectName = project.get(projectKey)! as string; - children.push({ - children: [], - name: dirOrProjectName(dir, projectName), - }); - continue; - } - - const subtree = createTreeStructure(project); - - // If the name is specified, we know there's a package at the "root" of the - // subtree itself. - if (subtree.name !== undefined) { - const projectName = subtree.name; - - children.push({ - children: subtree.children, - name: dirOrProjectName(dir, projectName), - }); - continue; - } - - // Special-case whenever we have one child, so we don't get unnecessary - // folders in the output. E.g. instead of `foo -> bar -> baz` we get - // `foo/bar/baz` instead. - if (subtree.children && subtree.children.length === 1) { - const child = subtree.children[0]; - const newName = chalk.dim(path.join(dir.toString(), child.name!)); - - children.push({ - children: child.children, - name: newName, - }); - continue; - } - - children.push({ - children: subtree.children, - name: chalk.dim(dir.toString()), - }); - } - - return { name, children }; -} - -function dirOrProjectName(dir: DirOrProjectName, projectName: string) { - return dir === projectName - ? chalk.green(dir) - : chalk`{dim ${dir.toString()} ({reset.green ${projectName}})}`; -} - -function buildProjectsTree(rootPath: string, projects: Map) { - const tree: IProjectsTree = new Map(); - - for (const project of projects.values()) { - if (rootPath === project.path) { - tree.set(projectKey, project.name); - } else { - const relativeProjectPath = path.relative(rootPath, project.path); - addProjectToTree(tree, relativeProjectPath.split(path.sep), project); - } - } - - return tree; -} - -function addProjectToTree(tree: IProjectsTree, pathParts: string[], project: Project) { - if (pathParts.length === 0) { - tree.set(projectKey, project.name); - } else { - const [currentDir, ...rest] = pathParts; - - if (!tree.has(currentDir)) { - tree.set(currentDir, new Map()); - } - - const subtree = tree.get(currentDir) as IProjectsTree; - addProjectToTree(subtree, rest, project); - } -} diff --git a/packages/kbn-pm/src/utils/regenerate_synthetic_package_map.ts b/packages/kbn-pm/src/utils/regenerate_synthetic_package_map.ts deleted file mode 100644 index c502e11f1a3c8..0000000000000 --- a/packages/kbn-pm/src/utils/regenerate_synthetic_package_map.ts +++ /dev/null @@ -1,33 +0,0 @@ -/* - * 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 Fs from 'fs/promises'; -import Path from 'path'; - -import normalizePath from 'normalize-path'; -import { KibanaPlatformPlugin } from '@kbn/plugin-discovery'; -import { convertPluginIdToPackageId } from './convert_plugin_id_to_package_id'; - -export async function regenerateSyntheticPackageMap( - plugins: KibanaPlatformPlugin[], - repoRoot: string -) { - const entries: Array<[string, string]> = [['@kbn/core', 'src/core']]; - - for (const plugin of plugins) { - entries.push([ - convertPluginIdToPackageId(plugin.manifest.id), - normalizePath(Path.relative(repoRoot, plugin.directory)), - ]); - } - - await Fs.writeFile( - Path.resolve(repoRoot, 'packages/kbn-synthetic-package-map/synthetic-packages.json'), - JSON.stringify(entries, null, 2) - ); -} diff --git a/packages/kbn-pm/src/utils/scripts.ts b/packages/kbn-pm/src/utils/scripts.ts deleted file mode 100644 index fff2b4ca77a14..0000000000000 --- a/packages/kbn-pm/src/utils/scripts.ts +++ /dev/null @@ -1,47 +0,0 @@ -/* - * 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 { spawn, spawnStreaming } from './child_process'; -import { Project } from './project'; - -const YARN_EXEC = process.env.npm_execpath || 'yarn'; - -/** - * Run script in the given directory - */ -export async function runScriptInPackage(script: string, args: string[], pkg: Project) { - const execOpts = { - cwd: pkg.path, - }; - - await spawn(YARN_EXEC, ['run', script, ...args], execOpts); -} - -/** - * Run script in the given directory - */ -export function runScriptInPackageStreaming({ - script, - args, - pkg, - debug, -}: { - script: string; - args: string[]; - pkg: Project; - debug?: boolean; -}) { - const execOpts = { - cwd: pkg.path, - }; - - return spawnStreaming(YARN_EXEC, ['run', script, ...args], execOpts, { - prefix: pkg.name, - debug, - }); -} diff --git a/packages/kbn-pm/src/utils/validate_dependencies.ts b/packages/kbn-pm/src/utils/validate_dependencies.ts deleted file mode 100644 index dc8c51682d75e..0000000000000 --- a/packages/kbn-pm/src/utils/validate_dependencies.ts +++ /dev/null @@ -1,201 +0,0 @@ -/* - * 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. - */ - -// @ts-expect-error published types are useless -import { stringify as stringifyLockfile } from '@yarnpkg/lockfile'; -import dedent from 'dedent'; -import chalk from 'chalk'; -import { sep } from 'path'; - -import { writeFile } from './fs'; -import { Kibana } from './kibana'; -import { YarnLock } from './yarn_lock'; -import { log } from './log'; -import { Project } from './project'; -import { isLinkDependency } from './package_json'; -import { ITree, treeToString } from './projects_tree'; - -export async function validateDependencies(kbn: Kibana, yarnLock: YarnLock) { - // look through all of the packages in the yarn.lock file to see if - // we have accidentally installed multiple lodash v4 versions - const lodash4Versions = new Set(); - const lodash4Reqs = new Set(); - for (const [req, dep] of Object.entries(yarnLock)) { - if (req.startsWith('lodash@') && dep.version.startsWith('4.')) { - lodash4Reqs.add(req); - lodash4Versions.add(dep.version); - } - } - - // if we find more than one lodash v4 version installed then delete - // lodash v4 requests from the yarn.lock file and prompt the user to - // retry bootstrap so that a single v4 version will be installed - if (lodash4Versions.size > 1) { - for (const req of lodash4Reqs) { - delete yarnLock[req]; - } - - await writeFile(kbn.getAbsolute('yarn.lock'), stringifyLockfile(yarnLock), 'utf8'); - - log.error(dedent` - - Multiple version of lodash v4 were detected, so they have been removed - from the yarn.lock file. Please rerun yarn kbn bootstrap to coalese the - lodash versions installed. - - If you still see this error when you re-bootstrap then you might need - to force a new dependency to use the latest version of lodash via the - "resolutions" field in package.json. - - If you have questions about this please reach out to the operations team. - - `); - - process.exit(1); - } - - // look through all the dependencies of production packages and production - // dependencies of those packages to determine if we're shipping any versions - // of lodash v3 in the distributable - const prodDependencies = kbn.resolveAllProductionDependencies(yarnLock, log); - const lodash3Versions = new Set(); - for (const dep of prodDependencies.values()) { - if (dep.name === 'lodash' && dep.version.startsWith('3.')) { - lodash3Versions.add(dep.version); - } - } - - // if any lodash v3 packages were found we abort and tell the user to fix things - if (lodash3Versions.size) { - log.error(dedent` - - Due to changes in the yarn.lock file and/or package.json files a version of - lodash 3 is now included in the production dependencies. To reduce the size of - our distributable and especially our front-end bundles we have decided to - prevent adding any new instances of lodash 3. - - Please inspect the changes to yarn.lock or package.json files to identify where - the lodash 3 version is coming from and remove it. - - If you have questions about this please reack out to the operations team. - - `); - - process.exit(1); - } - - // TODO: remove this once we move into a single package.json - // look through all the package.json files to find packages which have mismatched version ranges - const depRanges = new Map>(); - for (const project of kbn.getAllProjects().values()) { - // Skip if this is an external plugin - if (project.path.includes(`${kbn.kibanaProject?.path}${sep}plugins`)) { - continue; - } - - for (const [dep, range] of Object.entries(project.allDependencies)) { - const existingDep = depRanges.get(dep); - if (!existingDep) { - depRanges.set(dep, [ - { - range, - projects: [project], - }, - ]); - continue; - } - - const existingRange = existingDep.find((existing) => existing.range === range); - if (!existingRange) { - existingDep.push({ - range, - projects: [project], - }); - continue; - } - - existingRange.projects.push(project); - } - } - - const duplicateRanges = Array.from(depRanges.entries()) - .filter( - ([, ranges]) => ranges.length > 1 && !ranges.every((rng) => isLinkDependency(rng.range)) - ) - .reduce( - (acc: string[], [dep, ranges]) => [ - ...acc, - dep, - ...ranges.map( - ({ range, projects }) => ` ${range} => ${projects.map((p) => p.name).join(', ')}` - ), - ], - [] - ) - .join('\n '); - - if (duplicateRanges) { - log.error(dedent` - - [single_version_dependencies] Multiple version ranges for the same dependency - were found declared across different package.json files. Please consolidate - those to match across all package.json files. Different versions for the - same dependency is not supported. - - If you have questions about this please reach out to the operations team. - - The conflicting dependencies are: - - ${duplicateRanges} - `); - - process.exit(1); - } - - // look for packages that have the the `kibana.devOnly` flag in their package.json - // and make sure they aren't included in the production dependencies of Kibana - const devOnlyProjectsInProduction = getDevOnlyProductionDepsTree(kbn, 'kibana'); - if (devOnlyProjectsInProduction) { - log.error(dedent` - Some of the packages in the production dependency chain for Kibana and X-Pack are - flagged with "kibana.devOnly" in their package.json. Please check changes made to - packages and their dependencies to ensure they don't end up in production. - - The devOnly dependencies that are being dependend on in production are: - - ${treeToString(devOnlyProjectsInProduction).split('\n').join('\n ')} - `); - - process.exit(1); - } - - log.success('yarn.lock analysis completed without any issues'); -} - -function getDevOnlyProductionDepsTree(kbn: Kibana, projectName: string) { - const project = kbn.getProject(projectName); - const childProjectNames = [ - ...Object.keys(project.productionDependencies).filter((name) => kbn.hasProject(name)), - ...(projectName === 'kibana' ? ['x-pack'] : []), - ]; - - const children = childProjectNames - .map((n) => getDevOnlyProductionDepsTree(kbn, n)) - .filter((t): t is ITree => !!t); - - if (!children.length && !project.isFlaggedAsDevOnly()) { - return; - } - - const tree: ITree = { - name: project.isFlaggedAsDevOnly() ? chalk.red.bold(projectName) : projectName, - children, - }; - - return tree; -} diff --git a/packages/kbn-pm/src/utils/watch.ts b/packages/kbn-pm/src/utils/watch.ts deleted file mode 100644 index 0b4b1c2956080..0000000000000 --- a/packages/kbn-pm/src/utils/watch.ts +++ /dev/null @@ -1,102 +0,0 @@ -/* - * 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 * as Rx from 'rxjs'; -import { catchError, delay, finalize, first, map, mapTo, mergeMap, timeout } from 'rxjs/operators'; - -/** - * Number of milliseconds we wait before we fall back to the default watch handler. - */ -const defaultHandlerDelay = 3000; - -/** - * If default watch handler is used, then it's the number of milliseconds we wait for - * any build output before we consider watch task ready. - */ -const defaultHandlerReadinessTimeout = 2000; - -/** - * Describes configurable watch options. - */ -interface IWatchOptions { - /** - * Number of milliseconds to wait before we fall back to default watch handler. - */ - handlerDelay?: number; - - /** - * Number of milliseconds that default watch handler waits for any build output before - * it considers initial build completed. If build process outputs anything in a given - * time span, the timeout is restarted. - */ - handlerReadinessTimeout?: number; -} - -function getWatchHandlers( - buildOutput$: Rx.Observable, - { - handlerDelay = defaultHandlerDelay, - handlerReadinessTimeout = defaultHandlerReadinessTimeout, - }: IWatchOptions -) { - const typescriptHandler = buildOutput$.pipe( - first((data) => data.includes('$ tsc')), - map(() => - buildOutput$.pipe( - first((data) => data.includes('Compilation complete.')), - mapTo('tsc') - ) - ) - ); - - const webpackHandler = buildOutput$.pipe( - first((data) => data.includes('$ webpack')), - map(() => - buildOutput$.pipe( - first((data) => data.includes('Chunk Names')), - mapTo('webpack') - ) - ) - ); - - const defaultHandler = Rx.of(undefined).pipe( - delay(handlerReadinessTimeout), - map(() => - buildOutput$.pipe( - timeout(handlerDelay), - catchError(() => Rx.of('timeout')) - ) - ) - ); - - return [typescriptHandler, webpackHandler, defaultHandler]; -} - -export function waitUntilWatchIsReady(stream: NodeJS.EventEmitter, opts: IWatchOptions = {}) { - const buildOutput$ = new Rx.Subject(); - const onDataListener = (data: Buffer) => buildOutput$.next(data.toString('utf-8')); - const onEndListener = () => buildOutput$.complete(); - const onErrorListener = (e: Error) => buildOutput$.error(e); - - stream.once('end', onEndListener); - stream.once('error', onErrorListener); - stream.on('data', onDataListener); - - return Rx.firstValueFrom( - Rx.race(getWatchHandlers(buildOutput$, opts)).pipe( - mergeMap((whenReady) => whenReady), - finalize(() => { - stream.removeListener('data', onDataListener); - stream.removeListener('end', onEndListener); - stream.removeListener('error', onErrorListener); - - buildOutput$.complete(); - }) - ) - ); -} diff --git a/packages/kbn-pm/src/utils/yarn_lock.ts b/packages/kbn-pm/src/utils/yarn_lock.ts deleted file mode 100644 index ce1e3ddae4843..0000000000000 --- a/packages/kbn-pm/src/utils/yarn_lock.ts +++ /dev/null @@ -1,133 +0,0 @@ -/* - * 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. - */ - -// @ts-expect-error published types are worthless -import { parse as parseLockfile } from '@yarnpkg/lockfile'; - -import { readFile } from './fs'; -import { Kibana } from './kibana'; -import { Project } from './project'; -import { Log } from './log'; - -export interface YarnLock { - /** a simple map of name@versionrange tags to metadata about a package */ - [key: string]: { - /** resolved version installed for this pacakge */ - version: string; - /** resolved url for this pacakge */ - resolved: string; - /** yarn calculated integrity value for this package */ - integrity: string; - dependencies?: { - /** name => versionRange dependencies listed in package's manifest */ - [key: string]: string; - }; - optionalDependencies?: { - /** name => versionRange dependencies listed in package's manifest */ - [key: string]: string; - }; - }; -} - -export async function readYarnLock(kbn: Kibana): Promise { - try { - const contents = await readFile(kbn.getAbsolute('yarn.lock'), 'utf8'); - const yarnLock = parseLockfile(contents); - - if (yarnLock.type === 'success') { - return yarnLock.object; - } - - throw new Error('unable to read yarn.lock file, please run `yarn kbn bootstrap`'); - } catch (error) { - if (error.code !== 'ENOENT') { - throw error; - } - } - - return {}; -} - -/** - * Get a list of the absolute dependencies of this project, as resolved - * in the yarn.lock file, does not include other projects in the workspace - * or their dependencies - */ -export function resolveDepsForProject({ - project: rootProject, - yarnLock, - kbn, - log, - productionDepsOnly, - includeDependentProject, -}: { - project: Project; - yarnLock: YarnLock; - kbn: Kibana; - log: Log; - productionDepsOnly: boolean; - includeDependentProject: boolean; -}) { - /** map of [name@range, { name, version }] */ - const resolved = new Map(); - - const seenProjects = new Set(); - const projectQueue: Project[] = [rootProject]; - const depQueue: Array<[string, string]> = []; - - while (projectQueue.length) { - const project = projectQueue.shift()!; - if (seenProjects.has(project)) { - continue; - } - seenProjects.add(project); - - const projectDeps = Object.entries( - productionDepsOnly ? project.productionDependencies : project.allDependencies - ); - for (const [name, versionRange] of projectDeps) { - depQueue.push([name, versionRange]); - } - - while (depQueue.length) { - const [name, versionRange] = depQueue.shift()!; - const req = `${name}@${versionRange}`; - - if (resolved.has(req)) { - continue; - } - - if (includeDependentProject && kbn.hasProject(name)) { - projectQueue.push(kbn.getProject(name)!); - } - - if (!kbn.hasProject(name)) { - const pkg = yarnLock[req]; - if (!pkg) { - log.warning( - 'yarn.lock file is out of date, please run `yarn kbn bootstrap` to re-enable caching' - ); - return; - } - - resolved.set(req, { name, version: pkg.version }); - - const allDepsEntries = [ - ...Object.entries(pkg.dependencies || {}), - ...Object.entries(pkg.optionalDependencies || {}), - ]; - - for (const [childName, childVersionRange] of allDepsEntries) { - depQueue.push([childName, childVersionRange]); - } - } - } - } - - return resolved; -} diff --git a/packages/kbn-pm/tsconfig.json b/packages/kbn-pm/tsconfig.json deleted file mode 100644 index f12e49fe28d45..0000000000000 --- a/packages/kbn-pm/tsconfig.json +++ /dev/null @@ -1,14 +0,0 @@ -{ - "extends": "../../tsconfig.bazel.json", - "compilerOptions": { - "outDir": "target/types", - "types": [ - "jest", - "node" - ] - }, - "include": [ - "./index.d.ts", - "./src/**/*.ts" - ] -} diff --git a/packages/kbn-pm/webpack.config.js b/packages/kbn-pm/webpack.config.js deleted file mode 100644 index 60059ac038e79..0000000000000 --- a/packages/kbn-pm/webpack.config.js +++ /dev/null @@ -1,81 +0,0 @@ -/* - * 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. - */ - -const path = require('path'); - -module.exports = { - mode: 'none', - entry: { - index: './src/index.ts', - }, - target: 'node', - - output: { - path: path.resolve(__dirname, 'dist'), - filename: '[name].js', - libraryTarget: 'commonjs2', - }, - - resolve: { - extensions: ['.ts', '.js'], - symlinks: false, - }, - - module: { - rules: [ - { - test: /\.ts$/, - use: [ - { - loader: 'babel-loader', - }, - ], - exclude: /node_modules/, - }, - // In order to make it work with Node 10 we had the need to upgrade - // the package cpy to a version >= 7.0.0. In this version cpy is - // using the new globby that relies in the fast-glob which relies - // in the new micromatch. The micromatch (use and class-utils) dependencies having a require - // that uses the lazy-cache which cannot be correctly extracted by webpack. - // According to the documentation we should use the unlazy-loader to solve - // this situation: https://github.com/jonschlinkert/lazy-cache#heads-up - // We can also found some issues arround this who also used unlazy-loader - // to solve this: https://github.com/micromatch/micromatch/issues/55 - { - test: /node_modules\/(use|class-utils)\/utils\.js$/, - use: { - loader: 'unlazy-loader', - }, - }, - ], - }, - - node: { - // Don't replace built-in globals - __filename: false, - __dirname: false, - }, - - externals: { - worker_threads: { - commonjs: 'worker_threads', - }, - }, - - watchOptions: { - ignored: [/node_modules/, /vendor/], - }, - - optimization: { - moduleIds: 'named', - nodeEnv: 'production', - usedExports: true, - sideEffects: true, - minimize: false, - }, -}; diff --git a/packages/kbn-some-dev-log/BUILD.bazel b/packages/kbn-some-dev-log/BUILD.bazel new file mode 100644 index 0000000000000..da84f8e76211f --- /dev/null +++ b/packages/kbn-some-dev-log/BUILD.bazel @@ -0,0 +1,116 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "kbn-some-dev-log" +PKG_REQUIRE_NAME = "@kbn/some-dev-log" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +# In this array place runtime dependencies, including other packages and NPM packages +# which must be available for this code to run. +# +# To reference other packages use: +# "//repo/relative/path/to/package" +# eg. "//packages/kbn-utils" +# +# To reference a NPM package use: +# "@npm//name-of-package" +# eg. "@npm//lodash" +RUNTIME_DEPS = [ +] + +# In this array place dependencies necessary to build the types, which will include the +# :npm_module_types target of other packages and packages from NPM, including @types/* +# packages. +# +# To reference the types for another package use: +# "//repo/relative/path/to/package:npm_module_types" +# eg. "//packages/kbn-utils:npm_module_types" +# +# References to NPM packages work the same as RUNTIME_DEPS +TYPES_DEPS = [ + "@npm//@types/node", + "@npm//@types/jest", +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/kbn-some-dev-log/README.mdx b/packages/kbn-some-dev-log/README.mdx new file mode 100644 index 0000000000000..3e5b9a7375d8b --- /dev/null +++ b/packages/kbn-some-dev-log/README.mdx @@ -0,0 +1,19 @@ +--- +id: kibDevDocsOpsSomeDevLog +slug: /kibana-dev-docs/ops/kbn-some-dev-log +title: "@kbn/some-dev-log" +description: 'LCD types for several dev-focused loggers' +date: 2022-07-14 +tags: ['kibana', 'dev', 'contributor', 'operations', 'packages', 'scripts', 'logging'] +--- + +`@kbn/some-dev-log` implements lowest-common denominator types for several loggers that we use in development tooling. In order for commonly used tools to accept either log instance we need a common interface for them to implement which gives enough functionality to get the job done but doesn't require implementing a bunch of fancy features in all loggers. + +The interface mostly follows the `console.log()` interface, allowing you to pass a string as the first argument and then anything afterwards. The arguments are converted to a string by all loggers using [`util.format()`](https://nodejs.org/api/util.html#utilformatformat-args) from the standard library. + +Currently, the loggers implementing this type are: + + - : The majority of dev tasks should use this log and it is automatically provided by the common dev-task wrapper provided by . + - `Log` class: `@kbn/pm` runs before the repository is bootstrapped and needs a logger to use before other packages are available, so we have a separate and simple log implementation that code which implements the `SomeDevLog` class. Other code in the repository should rarely need to use this class or even know of it's existance. + +Unless your package needs to be used by `@kbn/pm` there is little reason you should need to use this type, but it might be a good idea to use this type if there's a chance we might need to use your package in the future. diff --git a/packages/kbn-pm/jest.config.js b/packages/kbn-some-dev-log/jest.config.js similarity index 82% rename from packages/kbn-pm/jest.config.js rename to packages/kbn-some-dev-log/jest.config.js index 4502d42043d46..f4ba48ad7a21b 100644 --- a/packages/kbn-pm/jest.config.js +++ b/packages/kbn-some-dev-log/jest.config.js @@ -7,7 +7,7 @@ */ module.exports = { - preset: '@kbn/test', + preset: '@kbn/test/jest_node', rootDir: '../..', - roots: ['/packages/kbn-pm'], + roots: ['/packages/kbn-some-dev-log'], }; diff --git a/packages/kbn-some-dev-log/package.json b/packages/kbn-some-dev-log/package.json new file mode 100644 index 0000000000000..f075d74b65359 --- /dev/null +++ b/packages/kbn-some-dev-log/package.json @@ -0,0 +1,10 @@ +{ + "name": "@kbn/some-dev-log", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0", + "kibana": { + "devOnly": true + } +} diff --git a/packages/kbn-bazel-runner/src/index.ts b/packages/kbn-some-dev-log/src/index.ts similarity index 84% rename from packages/kbn-bazel-runner/src/index.ts rename to packages/kbn-some-dev-log/src/index.ts index fb88a9744f522..e3f11d373ca66 100644 --- a/packages/kbn-bazel-runner/src/index.ts +++ b/packages/kbn-some-dev-log/src/index.ts @@ -6,4 +6,4 @@ * Side Public License, v 1. */ -export * from './bazel_runner'; +export type { SomeDevLog, SomeLogLevel } from './some_dev_log'; diff --git a/packages/kbn-some-dev-log/src/some_dev_log.ts b/packages/kbn-some-dev-log/src/some_dev_log.ts new file mode 100644 index 0000000000000..94e5e7f5d6d18 --- /dev/null +++ b/packages/kbn-some-dev-log/src/some_dev_log.ts @@ -0,0 +1,45 @@ +/* + * 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. + */ + +/** + * Basic set of log-level flags, the common levels implemented between + * the ToolingLog and the kbn_pm logger + */ +export type SomeLogLevel = 'verbose' | 'debug' | 'info' | 'quiet'; + +/** + * Generic interface that is implemented by the ToolingLog and the logger + * used by kbn_pm, which is responsible for running before the repo is + * bootstrapped and therefore can't use the ToolingLog. + */ +export interface SomeDevLog { + /** + * Log an info message + */ + info(msg: string, ...rest: any[]): void; + /** + * Log a warning message + */ + warning(msg: string, ...rest: any[]): void; + /** + * Log an error message + */ + error(msg: string, ...rest: any[]): void; + /** + * Log a success message + */ + success(msg: string, ...rest: any[]): void; + /** + * Log a debug message. Only printed to the terminal when --debug or --verbose are passed + */ + debug(msg: string, ...rest: any[]): void; + /** + * Log a verbose message. Only printed to the terminal when --verbose is passed + */ + verbose(msg: string, ...rest: any[]): void; +} diff --git a/packages/kbn-some-dev-log/tsconfig.json b/packages/kbn-some-dev-log/tsconfig.json new file mode 100644 index 0000000000000..789c6b3111115 --- /dev/null +++ b/packages/kbn-some-dev-log/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/packages/kbn-tooling-log/BUILD.bazel b/packages/kbn-tooling-log/BUILD.bazel index 3acf9108010f9..791757e8ac4b7 100644 --- a/packages/kbn-tooling-log/BUILD.bazel +++ b/packages/kbn-tooling-log/BUILD.bazel @@ -54,7 +54,8 @@ TYPES_DEPS = [ "@npm//tslib", "@npm//@types/node", "@npm//@types/jest", - "//packages/kbn-jest-serializers:npm_module_types" # needed for windows development, only used in tests + "//packages/kbn-some-dev-log:npm_module_types", + "//packages/kbn-jest-serializers:npm_module_types", # needed for windows development, only used in tests ] jsts_transpiler( diff --git a/packages/kbn-tooling-log/src/tooling_log.ts b/packages/kbn-tooling-log/src/tooling_log.ts index 727f71f85abc4..bef4320be2356 100644 --- a/packages/kbn-tooling-log/src/tooling_log.ts +++ b/packages/kbn-tooling-log/src/tooling_log.ts @@ -7,6 +7,7 @@ */ import * as Rx from 'rxjs'; +import { SomeDevLog } from '@kbn/some-dev-log'; import { ToolingLogTextWriter, ToolingLogTextWriterConfig } from './tooling_log_text_writer'; import { Writer } from './writer'; @@ -26,7 +27,7 @@ export interface ToolingLogOptions { parent?: ToolingLog; } -export class ToolingLog { +export class ToolingLog implements SomeDevLog { private indentWidth$: Rx.BehaviorSubject; private writers$: Rx.BehaviorSubject; private readonly written$: Rx.Subject; diff --git a/packages/kbn-utils/src/package_json/index.ts b/packages/kbn-utils/src/package_json/index.ts index fbd554c8c2c04..fada3e15b97d6 100644 --- a/packages/kbn-utils/src/package_json/index.ts +++ b/packages/kbn-utils/src/package_json/index.ts @@ -7,12 +7,46 @@ */ import Path from 'path'; +import Fs from 'fs'; + import { REPO_ROOT } from '../repo_root'; -export const kibanaPackageJson = { - ...require(Path.resolve(REPO_ROOT, 'package.json')), -}; +interface KibanaPackageJson { + name: string; + version: string; + branch: string; + build: { + number: number; + sha: string; + distributable?: boolean; + }; + dependencies: { + [dep: string]: string; + }; + devDependencies: { + [dep: string]: string; + }; + engines?: { + [name: string]: string | undefined; + }; + [key: string]: unknown; +} + +function parseKibanaPackageJson() { + const path = Path.resolve(REPO_ROOT, 'package.json'); + const json = Fs.readFileSync(path, 'utf8'); + let pkg; + try { + pkg = JSON.parse(json); + } catch (error) { + throw new Error(`unable to parse kibana's package.json file: ${error.message}`); + } + + return pkg as KibanaPackageJson; +} + +export const kibanaPackageJson = parseKibanaPackageJson(); export const isKibanaDistributable = () => { - return kibanaPackageJson.build && kibanaPackageJson.build.distributable === true; + return kibanaPackageJson.build.distributable === true; }; diff --git a/packages/kbn-yarn-lock-validator/BUILD.bazel b/packages/kbn-yarn-lock-validator/BUILD.bazel new file mode 100644 index 0000000000000..29b52958b58ac --- /dev/null +++ b/packages/kbn-yarn-lock-validator/BUILD.bazel @@ -0,0 +1,121 @@ +load("@npm//@bazel/typescript:index.bzl", "ts_config") +load("@build_bazel_rules_nodejs//:index.bzl", "js_library") +load("//src/dev/bazel:index.bzl", "jsts_transpiler", "pkg_npm", "pkg_npm_types", "ts_project") + +PKG_DIRNAME = "kbn-yarn-lock-validator" +PKG_REQUIRE_NAME = "@kbn/yarn-lock-validator" + +SOURCE_FILES = glob( + [ + "src/**/*.ts", + ], + exclude = [ + "**/*.test.*", + "**/*.stories.*", + ], +) + +SRCS = SOURCE_FILES + +filegroup( + name = "srcs", + srcs = SRCS, +) + +NPM_MODULE_EXTRA_FILES = [ + "package.json", +] + +# In this array place runtime dependencies, including other packages and NPM packages +# which must be available for this code to run. +# +# To reference other packages use: +# "//repo/relative/path/to/package" +# eg. "//packages/kbn-utils" +# +# To reference a NPM package use: +# "@npm//name-of-package" +# eg. "@npm//lodash" +RUNTIME_DEPS = [ +] + +# In this array place dependencies necessary to build the types, which will include the +# :npm_module_types target of other packages and packages from NPM, including @types/* +# packages. +# +# To reference the types for another package use: +# "//repo/relative/path/to/package:npm_module_types" +# eg. "//packages/kbn-utils:npm_module_types" +# +# References to NPM packages work the same as RUNTIME_DEPS +TYPES_DEPS = [ + "@npm//@types/dedent", + "@npm//@types/node", + "@npm//@types/jest", + "@npm//tslib", + "//packages/kbn-utils:npm_module_types", + "//packages/kbn-bazel-packages:npm_module_types", + "//packages/kbn-some-dev-log:npm_module_types", +] + +jsts_transpiler( + name = "target_node", + srcs = SRCS, + build_pkg_name = package_name(), +) + +ts_config( + name = "tsconfig", + src = "tsconfig.json", + deps = [ + "//:tsconfig.base.json", + "//:tsconfig.bazel.json", + ], +) + +ts_project( + name = "tsc_types", + args = ['--pretty'], + srcs = SRCS, + deps = TYPES_DEPS, + declaration = True, + declaration_map = True, + emit_declaration_only = True, + out_dir = "target_types", + root_dir = "src", + tsconfig = ":tsconfig", +) + +js_library( + name = PKG_DIRNAME, + srcs = NPM_MODULE_EXTRA_FILES, + deps = RUNTIME_DEPS + [":target_node"], + package_name = PKG_REQUIRE_NAME, + visibility = ["//visibility:public"], +) + +pkg_npm( + name = "npm_module", + deps = [":" + PKG_DIRNAME], +) + +filegroup( + name = "build", + srcs = [":npm_module"], + visibility = ["//visibility:public"], +) + +pkg_npm_types( + name = "npm_module_types", + srcs = SRCS, + deps = [":tsc_types"], + package_name = PKG_REQUIRE_NAME, + tsconfig = ":tsconfig", + visibility = ["//visibility:public"], +) + +filegroup( + name = "build_types", + srcs = [":npm_module_types"], + visibility = ["//visibility:public"], +) diff --git a/packages/kbn-yarn-lock-validator/README.mdx b/packages/kbn-yarn-lock-validator/README.mdx new file mode 100644 index 0000000000000..5fd8ce0731afe --- /dev/null +++ b/packages/kbn-yarn-lock-validator/README.mdx @@ -0,0 +1,17 @@ +--- +id: kibDevDocsOpsKbnYarnLockValidator +slug: /kibana-dev-docs/ops/kbn-yarn-lock-validator +title: "@kbn/yarn-lock-validator" +description: 'A tool for validating specific conditions for our dependency chain' +date: 2022-07-14 +tags: ['kibana', 'dev', 'contributor', 'operations', 'packages', 'scripts', 'yarn'] +--- + +`@kbn/yarn-lock-validator` provides yarn.lock validation logic for the Kibana project. It is loaded up by after bootstrap and validates that we haven't accidentally re-introduced specific dependencies or version-combination scenarios detailed below: + +## validation scenarios + + - Only a single version of lodash@4 is installed + - No lodash@3 versions installed + - None of the bazel packages in `"dependencies"`, and none of the transient dependencies of those packages, are marked as `"devOnly": true` + diff --git a/packages/kbn-yarn-lock-validator/jest.config.js b/packages/kbn-yarn-lock-validator/jest.config.js new file mode 100644 index 0000000000000..98bd882c6666e --- /dev/null +++ b/packages/kbn-yarn-lock-validator/jest.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test/jest_node', + rootDir: '../..', + roots: ['/packages/kbn-yarn-lock-validator'], +}; diff --git a/packages/kbn-yarn-lock-validator/package.json b/packages/kbn-yarn-lock-validator/package.json new file mode 100644 index 0000000000000..e7d0c00269ac7 --- /dev/null +++ b/packages/kbn-yarn-lock-validator/package.json @@ -0,0 +1,10 @@ +{ + "name": "@kbn/yarn-lock-validator", + "private": true, + "version": "1.0.0", + "main": "./target_node/index.js", + "license": "SSPL-1.0 OR Elastic License 2.0", + "kibana": { + "devOnly": true + } +} diff --git a/packages/kbn-yarn-lock-validator/src/find_production_dependencies.ts b/packages/kbn-yarn-lock-validator/src/find_production_dependencies.ts new file mode 100644 index 0000000000000..59166bef39e7d --- /dev/null +++ b/packages/kbn-yarn-lock-validator/src/find_production_dependencies.ts @@ -0,0 +1,53 @@ +/* + * 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 { SomeDevLog } from '@kbn/some-dev-log'; +import { kibanaPackageJson } from '@kbn/utils'; + +import { YarnLock } from './yarn_lock'; + +/** + * Get a list of the all production dependencies for Kibana by starting with the + * dependencies listed in package.json and then traversing deeply into the transitive + * dependencies as declared by the yarn.lock file. + */ +export function findProductionDependencies(log: SomeDevLog, yarnLock: YarnLock) { + const resolved = new Map(); + + // queue of dependencies entries, we will add the transitive dependencies to + // this queue as we itterate + const depQueue = Object.entries(kibanaPackageJson.dependencies); + + for (const [name, versionRange] of depQueue) { + const key = `${name}@${versionRange}`; + + // ignore `link:` deps to our own packages and deps we have already seen + if (resolved.has(key) || versionRange.startsWith('link:')) { + continue; + } + + const pkg = yarnLock[key]; + if (!pkg) { + log.warning('yarn.lock file is out of date, please re-run `yarn kbn bootstrap`'); + process.exit(1); + } + + resolved.set(key, { name, version: pkg.version }); + + const allDepsEntries = [ + ...Object.entries(pkg.dependencies || {}), + ...Object.entries(pkg.optionalDependencies || {}), + ]; + + for (const [childName, childVersionRange] of allDepsEntries) { + depQueue.push([childName, childVersionRange]); + } + } + + return resolved; +} diff --git a/packages/kbn-plugin-discovery/src/index.ts b/packages/kbn-yarn-lock-validator/src/index.ts similarity index 70% rename from packages/kbn-plugin-discovery/src/index.ts rename to packages/kbn-yarn-lock-validator/src/index.ts index a382b45515e53..70658cc0133dc 100644 --- a/packages/kbn-plugin-discovery/src/index.ts +++ b/packages/kbn-yarn-lock-validator/src/index.ts @@ -6,6 +6,6 @@ * Side Public License, v 1. */ -export * from './parse_kibana_platform_plugin'; -export * from './plugin_search_paths'; -export * from './simple_kibana_platform_plugin_discovery'; +export { readYarnLock } from './yarn_lock'; +export type { YarnLock } from './yarn_lock'; +export { validateDependencies } from './validate_yarn_lock'; diff --git a/packages/kbn-yarn-lock-validator/src/validate_yarn_lock.ts b/packages/kbn-yarn-lock-validator/src/validate_yarn_lock.ts new file mode 100644 index 0000000000000..923a0f11fcbf6 --- /dev/null +++ b/packages/kbn-yarn-lock-validator/src/validate_yarn_lock.ts @@ -0,0 +1,115 @@ +/* + * 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 Path from 'path'; +import Fsp from 'fs/promises'; + +import dedent from 'dedent'; + +import { REPO_ROOT, kibanaPackageJson } from '@kbn/utils'; +import { SomeDevLog } from '@kbn/some-dev-log'; +import { discoverBazelPackages } from '@kbn/bazel-packages'; + +import { YarnLock, stringifyLockFile } from './yarn_lock'; +import { findProductionDependencies } from './find_production_dependencies'; + +/** + * Validates the passed yarn.lock file to ensure that we aren't accidentally reproducing + * specific scenarios we have tried to remove from the codebase. + */ +export async function validateDependencies(log: SomeDevLog, yarnLock: YarnLock) { + // look through all of the packages in the yarn.lock file to see if + // we have accidentally installed multiple lodash v4 versions + const lodash4Versions = new Set(); + const lodash4Reqs = new Set(); + for (const [req, dep] of Object.entries(yarnLock)) { + if (req.startsWith('lodash@') && dep.version.startsWith('4.')) { + lodash4Reqs.add(req); + lodash4Versions.add(dep.version); + } + } + + // if we find more than one lodash v4 version installed then delete + // lodash v4 requests from the yarn.lock file and prompt the user to + // retry bootstrap so that a single v4 version will be installed + if (lodash4Versions.size > 1) { + for (const req of lodash4Reqs) { + delete yarnLock[req]; + } + + await Fsp.writeFile(Path.resolve(REPO_ROOT, 'yarn.lock'), stringifyLockFile(yarnLock), 'utf8'); + + log.error(dedent` + + Multiple version of lodash v4 were detected, so they have been removed + from the yarn.lock file. Please rerun yarn kbn bootstrap to coalese the + lodash versions installed. + + If you still see this error when you re-bootstrap then you might need + to force a new dependency to use the latest version of lodash via the + "resolutions" field in package.json. + + If you have questions about this please reach out to the operations team. + + `); + + process.exit(1); + } + + // look through all the dependencies of production packages and production + // dependencies of those packages to determine if we're shipping any versions + // of lodash v3 in the distributable + const prodDependencies = findProductionDependencies(log, yarnLock); + const lodash3Versions = new Set(); + for (const dep of prodDependencies.values()) { + if (dep.name === 'lodash' && dep.version.startsWith('3.')) { + lodash3Versions.add(dep.version); + } + } + // if any lodash v3 packages were found we abort and tell the user to fix things + if (lodash3Versions.size) { + log.error(dedent` + + Due to changes in the yarn.lock file and/or package.json files a version of + lodash 3 is now included in the production dependencies. To reduce the size of + our distributable and especially our front-end bundles we have decided to + prevent adding any new instances of lodash 3. + + Please inspect the changes to yarn.lock or package.json files to identify where + the lodash 3 version is coming from and remove it. + + If you have questions about this please reack out to the operations team. + + `); + + process.exit(1); + } + + // look for packages that have the the `kibana.devOnly` flag in their package.json + // and make sure they aren't included in the production dependencies of Kibana + const bazelPackages = await discoverBazelPackages(REPO_ROOT); + const devOnlyPackagesInProduction = bazelPackages + .filter((p) => p.isDevOnly() && Object.hasOwn(kibanaPackageJson.dependencies, p.pkg.name)) + .map((p) => p.pkg.name); + + if (devOnlyPackagesInProduction.length) { + log.error(dedent` + Some of the packages in the production dependency chain for Kibana and X-Pack are + flagged with "kibana.devOnly" in their package.json. Please check changes made to + packages and their dependencies to ensure they don't end up in production. + + The devOnly dependencies that are being dependend on in production are: + + - ${devOnlyPackagesInProduction.join('\n - ')} + `); + + process.exit(1); + } + + log.success('yarn.lock analysis completed without any issues'); +} diff --git a/packages/kbn-yarn-lock-validator/src/yarn_lock.ts b/packages/kbn-yarn-lock-validator/src/yarn_lock.ts new file mode 100644 index 0000000000000..383dcbe09ceee --- /dev/null +++ b/packages/kbn-yarn-lock-validator/src/yarn_lock.ts @@ -0,0 +1,73 @@ +/* + * 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 Fsp from 'fs/promises'; +import Path from 'path'; + +import { REPO_ROOT } from '@kbn/utils'; +// @ts-expect-error published types are worthless +import * as YarnLockFile from '@yarnpkg/lockfile'; + +/** + * Parsed yarn.lock file contents mapping `name@versionRange` strings to information from + * the yarn.lock file that is used to satisfy that request. + */ +export interface YarnLock { + /** a simple map of `name@versionrange` tags to metadata about a package */ + [key: string]: { + /** resolved version installed for this pacakge */ + version: string; + /** resolved url for this pacakge */ + resolved: string; + /** yarn calculated integrity value for this package */ + integrity: string; + dependencies?: { + /** name => versionRange dependencies listed in package's manifest */ + [key: string]: string; + }; + optionalDependencies?: { + /** name => versionRange dependencies listed in package's manifest */ + [key: string]: string; + }; + }; +} + +/** + * Parse any yarn.lock content into a YarnLock map + */ +export function parseLockfile(content: string): YarnLock { + const result = YarnLockFile.parse(content); + if (result.type === 'success') { + return result.object; + } + + throw new Error('unable to read yarn.lock file, please run `yarn kbn bootstrap`'); +} + +/** + * Convert a parsed yarn.lock file back to a string + */ +export function stringifyLockFile(yarnLock: YarnLock): string { + return YarnLockFile.stringify(yarnLock); +} + +/** + * Parse any yarn.lock content into a YarnLock map + */ +export async function readYarnLock(): Promise { + try { + const contents = await Fsp.readFile(Path.resolve(REPO_ROOT, 'yarn.lock'), 'utf8'); + return parseLockfile(contents); + } catch (error) { + if (error.code === 'ENOENT') { + return {}; + } + + throw error; + } +} diff --git a/packages/kbn-yarn-lock-validator/tsconfig.json b/packages/kbn-yarn-lock-validator/tsconfig.json new file mode 100644 index 0000000000000..789c6b3111115 --- /dev/null +++ b/packages/kbn-yarn-lock-validator/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../tsconfig.bazel.json", + "compilerOptions": { + "declaration": true, + "declarationMap": true, + "emitDeclarationOnly": true, + "outDir": "target_types", + "rootDir": "src", + "stripInternal": false, + "types": [ + "jest", + "node" + ] + }, + "include": [ + "src/**/*" + ] +} diff --git a/scripts/kbn.js b/scripts/kbn.js index 459c590ddf8cc..264150fcf9364 100644 --- a/scripts/kbn.js +++ b/scripts/kbn.js @@ -8,4 +8,7 @@ require('../src/setup_node_env/ensure_node_preserve_symlinks'); require('../src/setup_node_env/node_version_validator'); -require('../packages/kbn-pm/dist').run(process.argv.slice(2)); +import('../kbn_pm/src/cli.mjs').catch(function (error) { + console.error('UNHANDLED EXCEPTION:', error.stack); + process.exit(1); +}); diff --git a/src/dev/build/lib/config.test.ts b/src/dev/build/lib/config.test.ts index 0e373bb8794c3..4d5393f03f558 100644 --- a/src/dev/build/lib/config.test.ts +++ b/src/dev/build/lib/config.test.ts @@ -46,7 +46,7 @@ describe('#getKibanaPkg()', () => { describe('#getNodeVersion()', () => { it('returns the node version from the kibana package.json', async () => { const config = await setup(); - expect(config.getNodeVersion()).toEqual(kibanaPackageJson.engines.node); + expect(config.getNodeVersion()).toEqual(kibanaPackageJson.engines?.node); }); }); diff --git a/src/dev/build/tasks/build_packages_task.ts b/src/dev/build/tasks/build_packages_task.ts index 62baf74559a2a..bae1807f1f4c3 100644 --- a/src/dev/build/tasks/build_packages_task.ts +++ b/src/dev/build/tasks/build_packages_task.ts @@ -20,10 +20,7 @@ export const BuildBazelPackages: Task = { const packages = (await discoverBazelPackages()).filter((pkg) => !pkg.isDevOnly()); log.info(`Preparing Bazel projects production build non-devOnly packages`); - await runBazel({ - log, - bazelArgs: ['build', '//packages:build'], - }); + await runBazel(['build', '//packages:build']); for (const pkg of packages) { log.info(`Copying build of`, pkg.pkg.name, 'into build'); diff --git a/src/dev/typescript/projects.ts b/src/dev/typescript/projects.ts index 1c25e53aad184..a104b5a171d78 100644 --- a/src/dev/typescript/projects.ts +++ b/src/dev/typescript/projects.ts @@ -32,6 +32,7 @@ export const PROJECTS = [ createProject('x-pack/test/tsconfig.json', { name: 'x-pack/test' }), createProject('src/core/tsconfig.json'), createProject('.buildkite/tsconfig.json'), + createProject('kbn_pm/tsconfig.json'), createProject('x-pack/plugins/drilldowns/url_drilldown/tsconfig.json', { name: 'security_solution/cypress', diff --git a/src/dev/typescript/run_type_check_cli.ts b/src/dev/typescript/run_type_check_cli.ts index f59e6c47242bf..ad766a595b83b 100644 --- a/src/dev/typescript/run_type_check_cli.ts +++ b/src/dev/typescript/run_type_check_cli.ts @@ -35,14 +35,16 @@ export async function runTypeCheckCli() { return !p.disableTypeCheck && (!projectFilter || p.tsConfigPath === projectFilter); }); - const { failed } = await buildTsRefs({ - log, - procRunner, - verbose: !!flags.verbose, - project: projects.length === 1 ? projects[0] : undefined, - }); - if (failed) { - throw createFailError('Unable to build TS project refs'); + if (projects.length > 1 || projects[0].isCompositeProject()) { + const { failed } = await buildTsRefs({ + log, + procRunner, + verbose: !!flags.verbose, + project: projects.length === 1 ? projects[0] : undefined, + }); + if (failed) { + throw createFailError('Unable to build TS project refs'); + } } if (!projects.length) { diff --git a/test/scripts/checks/kbn_pm_dist.sh b/test/scripts/checks/kbn_pm_dist.sh deleted file mode 100644 index 3116404280cca..0000000000000 --- a/test/scripts/checks/kbn_pm_dist.sh +++ /dev/null @@ -1,19 +0,0 @@ -#!/usr/bin/env bash - -source src/dev/ci_setup/setup_env.sh - -### -### rebuild kbn-pm distributable to ensure it's not out of date -### -echo " -- building kbn-pm distributable" -yarn kbn run build -i @kbn/pm - -### -### verify no git modifications -### -GIT_CHANGES="$(git ls-files --modified)" -if [ "$GIT_CHANGES" ]; then - echo -e "\n${RED}ERROR: 'yarn kbn run build -i @kbn/pm' caused changes to the following files:${C_RESET}\n" - echo -e "$GIT_CHANGES\n" - exit 1 -fi diff --git a/test/scripts/checks/test_projects.sh b/test/scripts/checks/test_projects.sh index be3fe4c4be9d0..ee74616a958fa 100755 --- a/test/scripts/checks/test_projects.sh +++ b/test/scripts/checks/test_projects.sh @@ -3,4 +3,4 @@ source src/dev/ci_setup/setup_env.sh checks-reporter-with-killswitch "Test Projects" \ - yarn kbn run test --exclude kibana --oss --skip-kibana-plugins --skip-missing + yarn kbn run-in-packages test diff --git a/x-pack/plugins/fleet/scripts/install_all_packages/install_all_packages.ts b/x-pack/plugins/fleet/scripts/install_all_packages/install_all_packages.ts index d9998d235a46e..e07ff9f5a1808 100644 --- a/x-pack/plugins/fleet/scripts/install_all_packages/install_all_packages.ts +++ b/x-pack/plugins/fleet/scripts/install_all_packages/install_all_packages.ts @@ -6,15 +6,15 @@ */ import fetch from 'node-fetch'; +import { kibanaPackageJson } from '@kbn/utils'; import { ToolingLog } from '@kbn/tooling-log'; -import ReadPackage from 'read-pkg'; const REGISTRY_URL = 'https://epr-snapshot.elastic.co'; const KIBANA_URL = 'http://localhost:5601'; const KIBANA_USERNAME = 'elastic'; const KIBANA_PASSWORD = 'changeme'; -const KIBANA_VERSION = ReadPackage.sync().version; +const KIBANA_VERSION = kibanaPackageJson.version; const SKIP_PACKAGES: string[] = []; diff --git a/yarn.lock b/yarn.lock index 8f1b5730031dd..d64e2e61e0fb9 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3527,10 +3527,6 @@ version "0.0.0" uid "" -"@kbn/pm@link:packages/kbn-pm": - version "0.0.0" - uid "" - "@kbn/react-field@link:bazel-bin/packages/kbn-react-field": version "0.0.0" uid "" @@ -3659,6 +3655,10 @@ version "0.0.0" uid "" +"@kbn/some-dev-log@link:bazel-bin/packages/kbn-some-dev-log": + version "0.0.0" + uid "" + "@kbn/sort-package-json@link:bazel-bin/packages/kbn-sort-package-json": version "0.0.0" uid "" @@ -3755,6 +3755,10 @@ version "0.0.0" uid "" +"@kbn/yarn-lock-validator@link:bazel-bin/packages/kbn-yarn-lock-validator": + version "0.0.0" + uid "" + "@loaders.gl/core@2.3.1", "@loaders.gl/core@^2.3.1": version "2.3.1" resolved "https://registry.yarnpkg.com/@loaders.gl/core/-/core-2.3.1.tgz#147037e17b014528dce00187aac0ec6ccb05938b" @@ -6094,11 +6098,6 @@ resolved "https://registry.yarnpkg.com/@types/clone/-/clone-2.1.1.tgz#9b880d0ce9b1f209b5e0bd6d9caa38209db34024" integrity sha512-BZIU34bSYye0j/BFcPraiDZ5ka6MJADjcDVELGf7glr9K+iE8NYVjFslJFVWzskSxkLLyCrSPScE82/UUoBSvg== -"@types/cmd-shim@^2.0.0": - version "2.0.0" - resolved "https://registry.yarnpkg.com/@types/cmd-shim/-/cmd-shim-2.0.0.tgz#c3d81d3c2a51af3c65c19b4f1d493a75abf07a5c" - integrity sha512-WuV5bOQTGxqzewPnJbrDe51I5mnX2wTRYy+PduRuIvSuBWZlxDYD6Qt/f1m5sezxx1yyE9+1wHJ/0sRuNIoFaQ== - "@types/color-convert@*", "@types/color-convert@^2.0.0": version "2.0.0" resolved "https://registry.yarnpkg.com/@types/color-convert/-/color-convert-2.0.0.tgz#8f5ee6b9e863dcbee5703f5a517ffb13d3ea4e22" @@ -7318,6 +7317,10 @@ version "0.0.0" uid "" +"@types/kbn__some-dev-log@link:bazel-bin/packages/kbn-some-dev-log/npm_module_types": + version "0.0.0" + uid "" + "@types/kbn__sort-package-json@link:bazel-bin/packages/kbn-sort-package-json/npm_module_types": version "0.0.0" uid "" @@ -7390,6 +7393,10 @@ version "0.0.0" uid "" +"@types/kbn__yarn-lock-validator@link:bazel-bin/packages/kbn-yarn-lock-validator/npm_module_types": + version "0.0.0" + uid "" + "@types/keyv@*": version "3.1.1" resolved "https://registry.yarnpkg.com/@types/keyv/-/keyv-3.1.1.tgz#e45a45324fca9dab716ab1230ee249c9fb52cfa7" @@ -7521,7 +7528,7 @@ resolved "https://registry.yarnpkg.com/@types/mime/-/mime-2.0.1.tgz#dc488842312a7f075149312905b5e3c0b054c79d" integrity sha512-FwI9gX75FgVBJ7ywgnq/P7tw+/o1GUbtP0KzbtusLigAOgIgNISRK0ZPl4qertvXSIE8YbsVJueQ90cDt9YYyw== -"@types/minimatch@*", "@types/minimatch@^3.0.3": +"@types/minimatch@*": version "3.0.3" resolved "https://registry.yarnpkg.com/@types/minimatch/-/minimatch-3.0.3.tgz#3dca0e3f33b200fc7d1139c0cd96c1268cadfd9d" integrity sha512-tHq6qdbT9U1IRSGf14CL0pUlULksvY9OZ+5eEgl1N7t+OA3tGvNpxJCzuKQlsNgCVwbAs670L1vcVQi8j9HjnA== @@ -7574,13 +7581,6 @@ resolved "https://registry.yarnpkg.com/@types/mustache/-/mustache-0.8.31.tgz#7c86cbf74f7733f9e3bdc28817623927eb386616" integrity sha512-72flCZJkEJHPwhmpHgg4a0ZBLssMhg5NB0yltRblRlZMo4py3B/u/d7icevc4EeN9MPQUo/dPtuVOoVy9ih6cQ== -"@types/ncp@^2.0.1": - version "2.0.1" - resolved "https://registry.yarnpkg.com/@types/ncp/-/ncp-2.0.1.tgz#749432511f6ad747d04e98837b18cca9045567fb" - integrity sha512-TeiJ7uvv/92ugSqZ0v9l0eNXzutlki0aK+R1K5bfA5SYUil46ITlxLW4iNTCf55P4L5weCmaOdtxGeGWvudwPg== - dependencies: - "@types/node" "*" - "@types/nock@^10.0.3": version "10.0.3" resolved "https://registry.yarnpkg.com/@types/nock/-/nock-10.0.3.tgz#dab1d18ffbccfbf2db811dab9584304eeb6e1c4c" @@ -7622,7 +7622,7 @@ dependencies: "@types/node" "*" -"@types/normalize-package-data@*", "@types/normalize-package-data@^2.4.0": +"@types/normalize-package-data@^2.4.0": version "2.4.0" resolved "https://registry.yarnpkg.com/@types/normalize-package-data/-/normalize-package-data-2.4.0.tgz#e486d0d97396d79beedd0a6e33f4534ff6b4973e" integrity sha512-f5j5b/Gf71L+dbqxIpQ4Z2WlmI/mPJ0fOkGGmFgtb6sAu97EPczzbS3/tJKxmcYDj55OX6ssqwDAWOHIYDRDGA== @@ -7936,13 +7936,6 @@ "@types/scheduler" "*" csstype "^3.0.2" -"@types/read-pkg@^4.0.0": - version "4.0.0" - resolved "https://registry.yarnpkg.com/@types/read-pkg/-/read-pkg-4.0.0.tgz#773457698f405b53a73471538e76e433e04cb786" - integrity sha512-mnQ7ukQhFGkbErwioo+ahHhkdIhw/llqW97ijWi6l3JYKXAokElLZxlEOtlYYmPKLUJxRKhplOa514n2TyVxjg== - dependencies: - "@types/normalize-package-data" "*" - "@types/recompose@^0.30.6": version "0.30.6" resolved "https://registry.yarnpkg.com/@types/recompose/-/recompose-0.30.6.tgz#f6ffae2008b84df916ed6633751f9287f344ea3e" @@ -8089,13 +8082,6 @@ dependencies: strip-ansi "*" -"@types/strong-log-transformer@^1.0.0": - version "1.0.0" - resolved "https://registry.yarnpkg.com/@types/strong-log-transformer/-/strong-log-transformer-1.0.0.tgz#47b0c9fe1f0c997ed4239746e633e8e36fc836ac" - integrity sha512-ljpD7pfMwsQuzpnXxAb3xAkD/eM3jm3T5GdVcwZISpuPZRg1qwpitjzl6Du4mIl7Eeaqu89uyIgOnZadZTy5Xg== - dependencies: - "@types/node" "*" - "@types/styled-components@^5.1.0": version "5.1.0" resolved "https://registry.yarnpkg.com/@types/styled-components/-/styled-components-5.1.0.tgz#24d3412ba5395aa06e14fbc93c52f9454cebd0d6" @@ -8287,11 +8273,6 @@ anymatch "^3.0.0" source-map "^0.6.0" -"@types/write-pkg@^3.1.0": - version "3.1.0" - resolved "https://registry.yarnpkg.com/@types/write-pkg/-/write-pkg-3.1.0.tgz#f58767f4fb9a6a3ad8e95d3e9cd1f2d026ceab26" - integrity sha512-JRGsPEPCrYqTXU0Cr+Yu7esPBE2yvH7ucOHr+JuBy0F59kglPvO5gkmtyEvf3P6dASSkScvy/XQ6SC1QEBFDuA== - "@types/ws@*": version "8.5.3" resolved "https://registry.yarnpkg.com/@types/ws/-/ws-8.5.3.tgz#7d25a1ffbecd3c4f2d35068d0b283c037003274d" @@ -9305,11 +9286,6 @@ arr-union@^3.1.0: resolved "https://registry.yarnpkg.com/arr-union/-/arr-union-3.1.0.tgz#e39b09aea9def866a8f206e288af63919bae39c4" integrity sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ= -array-differ@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/array-differ/-/array-differ-3.0.0.tgz#3cbb3d0f316810eafcc47624734237d6aee4ae6b" - integrity sha512-THtfYS6KtME/yIAhKjZ2ul7XI96lQGHRputJQHO80LAWQnuGP4iCIN8vdMRboGbIEYBwU33q8Tch1os2+X0kMg== - array-each@^1.0.0, array-each@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/array-each/-/array-each-1.0.1.tgz#a794af0c05ab1752846ee753a1f211a05ba0c44f" @@ -11344,14 +11320,6 @@ clsx@^1.0.1, clsx@^1.1.1: resolved "https://registry.yarnpkg.com/clsx/-/clsx-1.1.1.tgz#98b3134f9abbdf23b2663491ace13c5c03a73188" integrity sha512-6/bPho624p3S2pMyvP5kKBPXnI3ufHLObBFCfgx+LkeR5lg2XYy2hqZqUf45ypD8COn2bhgGJSUE+l5dhNBieA== -cmd-shim@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/cmd-shim/-/cmd-shim-2.1.0.tgz#e59a08d4248dda3bb502044083a4db4ac890579a" - integrity sha512-A5C0Cyf2H8sKsHqX0tvIWRXw5/PK++3Dc0lDbsugr90nOECLLuSPahVQBG8pgmgiXgm/TzBWMqI2rWdZwHduAw== - dependencies: - graceful-fs "^4.1.2" - mkdirp "~0.5.0" - co@^4.6.0: version "4.6.0" resolved "https://registry.yarnpkg.com/co/-/co-4.6.0.tgz#6ea6bdf3d853ae54ccb8e47bfa0bf3f9031fb184" @@ -13348,11 +13316,6 @@ detect-file@^1.0.0: resolved "https://registry.yarnpkg.com/detect-file/-/detect-file-1.0.0.tgz#f0d66d03672a825cb1b73bdb3fe62310c8e552b7" integrity sha1-8NZtA2cqglyxtzvbP+YjEMjlUrc= -detect-indent@^5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/detect-indent/-/detect-indent-5.0.0.tgz#3871cc0a6a002e8c3e5b3cf7f336264675f06b9d" - integrity sha1-OHHMCmoALow+Wzz38zYmRnXwa50= - detect-indent@^6.0.0: version "6.1.0" resolved "https://registry.yarnpkg.com/detect-indent/-/detect-indent-6.1.0.tgz#592485ebbbf6b3b1ab2be175c8393d04ca0d57e6" @@ -13764,11 +13727,6 @@ duplexer3@^0.1.4: resolved "https://registry.yarnpkg.com/duplexer3/-/duplexer3-0.1.4.tgz#ee01dd1cac0ed3cbc7fdbea37dc0a8f1ce002ce2" integrity sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI= -duplexer@^0.1.1: - version "0.1.1" - resolved "https://registry.yarnpkg.com/duplexer/-/duplexer-0.1.1.tgz#ace6ff808c1ce66b57d1ebf97977acb02334cfc1" - integrity sha1-rOb/gIwc5mtX0ev5eXessCM0z8E= - duplexer@^0.1.2: version "0.1.2" resolved "https://registry.yarnpkg.com/duplexer/-/duplexer-0.1.2.tgz#3abe43aef3835f8ae077d136ddce0f276b0400e6" @@ -18134,7 +18092,7 @@ is-plain-obj@2.1.0, is-plain-obj@^2.0.0, is-plain-obj@^2.1.0: resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-2.1.0.tgz#45e42e37fccf1f40da8e5f76ee21515840c09287" integrity sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA== -is-plain-obj@^1.0.0, is-plain-obj@^1.1.0: +is-plain-obj@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-1.1.0.tgz#71a50c8429dfca773c92a390a4a03b39fcd51d3e" integrity sha1-caUMhCnfync8kqOQpKA7OfzVHT4= @@ -21104,7 +21062,7 @@ mkdirp-classic@^0.5.2, mkdirp-classic@^0.5.3: resolved "https://registry.yarnpkg.com/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz#fa10c9115cc6d8865be221ba47ee9bed78601113" integrity sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A== -mkdirp@^0.5.0, mkdirp@^0.5.1, mkdirp@^0.5.3, mkdirp@~0.5.0, mkdirp@~0.5.1: +mkdirp@^0.5.0, mkdirp@^0.5.1, mkdirp@^0.5.3, mkdirp@~0.5.1: version "0.5.4" resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.4.tgz#fd01504a6797ec5c9be81ff43d204961ed64a512" integrity sha512-iG9AK/dJLtJ0XNgTuDbSyNS3zECqDlAhnQW4CsNxBG3LQJBbHmRX1egw39DmtOdCAqY+dKXV+sgPgilNWUKMVw== @@ -21343,17 +21301,6 @@ multicast-dns@^6.0.1: dns-packet "^1.3.1" thunky "^1.0.2" -multimatch@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/multimatch/-/multimatch-4.0.0.tgz#8c3c0f6e3e8449ada0af3dd29efb491a375191b3" - integrity sha512-lDmx79y1z6i7RNx0ZGCPq1bzJ6ZoDDKbvh7jxr9SJcWLkShMzXrHbYVpTdnhNM5MXpDUxCQ4DgqVttVXlBgiBQ== - dependencies: - "@types/minimatch" "^3.0.3" - array-differ "^3.0.0" - array-union "^2.1.0" - arrify "^2.0.1" - minimatch "^3.0.4" - murmurhash-js@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/murmurhash-js/-/murmurhash-js-1.0.0.tgz#b06278e21fc6c37fa5313732b0412bcb6ae15f51" @@ -21453,11 +21400,6 @@ natural-compare@^1.4.0: resolved "https://registry.yarnpkg.com/natural-compare/-/natural-compare-1.4.0.tgz#4abebfeed7541f2c27acfb29bdbbd15c8d5ba4f7" integrity sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc= -ncp@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/ncp/-/ncp-2.0.0.tgz#195a21d6c46e361d2fb1281ba38b91e9df7bdbb3" - integrity sha1-GVoh1sRuNh0vsSgbo4uR6d9727M= - ndarray-ops@^1.2.2: version "1.2.2" resolved "https://registry.yarnpkg.com/ndarray-ops/-/ndarray-ops-1.2.2.tgz#59e88d2c32a7eebcb1bc690fae141579557a614e" @@ -25791,11 +25733,6 @@ requires-port@^1.0.0: resolved "https://registry.yarnpkg.com/requires-port/-/requires-port-1.0.0.tgz#925d2601d39ac485e091cf0da5c6e694dc3dcaff" integrity sha1-kl0mAdOaxIXgkc8NpcbmlNw9yv8= -requires-regex@^0.3.3: - version "0.3.3" - resolved "https://registry.yarnpkg.com/requires-regex/-/requires-regex-0.3.3.tgz#60309eaabbfd5ca8259e090b8b5a94b2144eb0dd" - integrity sha1-YDCeqrv9XKglngkLi1qUshROsN0= - reselect@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/reselect/-/reselect-4.0.0.tgz#f2529830e5d3d0e021408b246a206ef4ea4437f7" @@ -26840,13 +26777,6 @@ sonic-boom@^2.6.0: dependencies: atomic-sleep "^1.0.0" -sort-keys@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/sort-keys/-/sort-keys-2.0.0.tgz#658535584861ec97d730d6cf41822e1f56684128" - integrity sha1-ZYU1WEhh7JfXMNbPQYIuH1ZoQSg= - dependencies: - is-plain-obj "^1.0.0" - sort-object-keys@^1.1.3: version "1.1.3" resolved "https://registry.yarnpkg.com/sort-object-keys/-/sort-object-keys-1.1.3.tgz#bff833fe85cab147b34742e45863453c1e190b45" @@ -27595,15 +27525,6 @@ strip-json-comments@~2.0.1: resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-2.0.1.tgz#3c531942e908c2697c0ec344858c286c7ca0a60a" integrity sha1-PFMZQukIwml8DsNEhYwobHygpgo= -strong-log-transformer@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/strong-log-transformer/-/strong-log-transformer-2.1.0.tgz#0f5ed78d325e0421ac6f90f7f10e691d6ae3ae10" - integrity sha512-B3Hgul+z0L9a236FAUC9iZsL+nVHgoCJnqCbN588DjYxvGXaXaaFbfmQ/JhvKjZwsOukuR72XbHv71Qkug0HxA== - dependencies: - duplexer "^0.1.1" - minimist "^1.2.0" - through "^2.3.4" - style-it@^2.1.3: version "2.1.3" resolved "https://registry.yarnpkg.com/style-it/-/style-it-2.1.3.tgz#ab6b5e109a1e946d58639f8cd05aa52df7ef1ab1" @@ -28692,11 +28613,6 @@ type-fest@^0.3.1: resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.3.1.tgz#63d00d204e059474fe5e1b7c011112bbd1dc29e1" integrity sha512-cUGJnCdr4STbePCgqNFbpVNCepa+kAVohJs1sLhxzdH+gnEoOd8VhbYa7pD3zZYGiURWM2xzEII3fQcRizDkYQ== -type-fest@^0.4.1: - version "0.4.1" - resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.4.1.tgz#8bdf77743385d8a4f13ba95f610f5ccd68c728f8" - integrity sha512-IwzA/LSfD2vC1/YDYMv/zHP4rDF1usCwllsDpbolT3D4fUepIO7f9K70jjmUewU/LmGUKJcwcVtDCpnKk4BPMw== - type-fest@^0.5.2: version "0.5.2" resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.5.2.tgz#d6ef42a0356c6cd45f49485c3b6281fc148e48a2" @@ -29156,13 +29072,6 @@ universalify@^2.0.0: resolved "https://registry.yarnpkg.com/universalify/-/universalify-2.0.0.tgz#75a4984efedc4b08975c5aeb73f530d02df25717" integrity sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ== -unlazy-loader@^0.1.3: - version "0.1.3" - resolved "https://registry.yarnpkg.com/unlazy-loader/-/unlazy-loader-0.1.3.tgz#2efdf05c489da311055586bf3cfca0c541dd8fa5" - integrity sha512-INqQZxgx399Y8Eo5gihKBmlHvvcacaYMXI9HMtb2c6JbZLJkgdf0s/gkxqJbo2pl+rtxzPtmf7tj7vHlRx+K/g== - dependencies: - requires-regex "^0.3.3" - unload@2.2.0: version "2.2.0" resolved "https://registry.yarnpkg.com/unload/-/unload-2.2.0.tgz#ccc88fdcad345faa06a92039ec0f80b488880ef7" @@ -30628,15 +30537,6 @@ write-file-atomic@^1.1.2: imurmurhash "^0.1.4" slide "^1.1.5" -write-file-atomic@^2.4.2: - version "2.4.3" - resolved "https://registry.yarnpkg.com/write-file-atomic/-/write-file-atomic-2.4.3.tgz#1fd2e9ae1df3e75b8d8c367443c692d4ca81f481" - integrity sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ== - dependencies: - graceful-fs "^4.1.11" - imurmurhash "^0.1.4" - signal-exit "^3.0.2" - write-file-atomic@^3.0.0, write-file-atomic@^3.0.3: version "3.0.3" resolved "https://registry.yarnpkg.com/write-file-atomic/-/write-file-atomic-3.0.3.tgz#56bd5c5a5c70481cd19c571bd39ab965a5de56e8" @@ -30647,27 +30547,6 @@ write-file-atomic@^3.0.0, write-file-atomic@^3.0.3: signal-exit "^3.0.2" typedarray-to-buffer "^3.1.5" -write-json-file@^3.2.0: - version "3.2.0" - resolved "https://registry.yarnpkg.com/write-json-file/-/write-json-file-3.2.0.tgz#65bbdc9ecd8a1458e15952770ccbadfcff5fe62a" - integrity sha512-3xZqT7Byc2uORAatYiP3DHUUAVEkNOswEWNs9H5KXiicRTvzYzYqKjYc4G7p+8pltvAw641lVByKVtMpf+4sYQ== - dependencies: - detect-indent "^5.0.0" - graceful-fs "^4.1.15" - make-dir "^2.1.0" - pify "^4.0.1" - sort-keys "^2.0.0" - write-file-atomic "^2.4.2" - -write-pkg@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/write-pkg/-/write-pkg-4.0.0.tgz#675cc04ef6c11faacbbc7771b24c0abbf2a20039" - integrity sha512-v2UQ+50TNf2rNHJ8NyWttfm/EJUBWMJcx6ZTYZr6Qp52uuegWw/lBkCtCbnYZEmPRNL61m+u67dAmGxo+HTULA== - dependencies: - sort-keys "^2.0.0" - type-fest "^0.4.1" - write-json-file "^3.2.0" - ws@7.4.6, ws@^7.2.3: version "7.4.6" resolved "https://registry.yarnpkg.com/ws/-/ws-7.4.6.tgz#5654ca8ecdeee47c33a9a4bf6d28e2be2980377c" From a07fb3063b13ed0990a06fd8d3a68ce8b466dbae Mon Sep 17 00:00:00 2001 From: Spencer Date: Mon, 18 Jul 2022 10:49:22 -0500 Subject: [PATCH 104/111] [cli-dev-mode/base-path-proxy] switch to integration tests (#136545) --- packages/kbn-cli-dev-mode/jest.config.js | 2 +- .../kbn-cli-dev-mode/jest.integration.config.js | 13 +++++++++++++ .../base_path_proxy_server.test.ts | 6 +++--- 3 files changed, 17 insertions(+), 4 deletions(-) create mode 100644 packages/kbn-cli-dev-mode/jest.integration.config.js rename packages/kbn-cli-dev-mode/src/{ => integration_tests}/base_path_proxy_server.test.ts (99%) diff --git a/packages/kbn-cli-dev-mode/jest.config.js b/packages/kbn-cli-dev-mode/jest.config.js index d04dc571ef2a0..463170417d609 100644 --- a/packages/kbn-cli-dev-mode/jest.config.js +++ b/packages/kbn-cli-dev-mode/jest.config.js @@ -7,7 +7,7 @@ */ module.exports = { - preset: '@kbn/test', + preset: '@kbn/test/jest_node', rootDir: '../..', roots: ['/packages/kbn-cli-dev-mode'], }; diff --git a/packages/kbn-cli-dev-mode/jest.integration.config.js b/packages/kbn-cli-dev-mode/jest.integration.config.js new file mode 100644 index 0000000000000..a6ee6e92a5c47 --- /dev/null +++ b/packages/kbn-cli-dev-mode/jest.integration.config.js @@ -0,0 +1,13 @@ +/* + * 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. + */ + +module.exports = { + preset: '@kbn/test/jest_integration_node', + rootDir: '../..', + roots: ['/packages/kbn-cli-dev-mode'], +}; diff --git a/packages/kbn-cli-dev-mode/src/base_path_proxy_server.test.ts b/packages/kbn-cli-dev-mode/src/integration_tests/base_path_proxy_server.test.ts similarity index 99% rename from packages/kbn-cli-dev-mode/src/base_path_proxy_server.test.ts rename to packages/kbn-cli-dev-mode/src/integration_tests/base_path_proxy_server.test.ts index 34c6be02847a7..663f4f8b04b97 100644 --- a/packages/kbn-cli-dev-mode/src/base_path_proxy_server.test.ts +++ b/packages/kbn-cli-dev-mode/src/integration_tests/base_path_proxy_server.test.ts @@ -18,9 +18,9 @@ import { } from '@kbn/server-http-tools'; import { ByteSizeValue } from '@kbn/config-schema'; -import { BasePathProxyServer, BasePathProxyServerOptions } from './base_path_proxy_server'; -import { DevConfig } from './config/dev_config'; -import { TestLog } from './log'; +import { BasePathProxyServer, BasePathProxyServerOptions } from '../base_path_proxy_server'; +import { DevConfig } from '../config/dev_config'; +import { TestLog } from '../log'; describe('BasePathProxyServer', () => { let server: Server; From f0325b2f7dd36898e89c86348627a5dacaf7cbce Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Patryk=20Kopyci=C5=84ski?= Date: Mon, 18 Jul 2022 17:57:28 +0200 Subject: [PATCH 105/111] Renovate react-query (#136480) --- package.json | 2 +- renovate.json | 15 +++++++++++++++ yarn.lock | 8 ++++---- 3 files changed, 20 insertions(+), 5 deletions(-) diff --git a/package.json b/package.json index 2ec9bb79fd254..2f0113b0714ef 100644 --- a/package.json +++ b/package.json @@ -458,7 +458,7 @@ "react-moment-proptypes": "^1.7.0", "react-monaco-editor": "^0.41.2", "react-popper-tooltip": "^2.10.1", - "react-query": "^3.34.7", + "react-query": "^3.39.1", "react-redux": "^7.2.0", "react-resizable": "^1.7.5", "react-resize-detector": "^4.2.0", diff --git a/renovate.json b/renovate.json index 34ef1ea5bc0cf..49337a00d7246 100644 --- a/renovate.json +++ b/renovate.json @@ -165,6 +165,21 @@ "matchPackagePatterns": ["^@storybook"], "labels": ["Team:Operations", "release_note:skip"], "enabled": true + }, + { + "groupName": "react-query", + "packageNames": ["react-query"], + "reviewers": [ + "team:response-ops", + "team:kibana-cloud-security-posture", + "team:security-asset-management", + "team:fleet", + "team:awp-platform", + "team:security-onboarding-and-lifecycle-mgt" + ], + "matchBaseBranches": ["main"], + "labels": ["release_note:skip", "backport:skip", "ci:all-cypress-suites"], + "enabled": true } ] } diff --git a/yarn.lock b/yarn.lock index d64e2e61e0fb9..10d92952cb525 100644 --- a/yarn.lock +++ b/yarn.lock @@ -24614,10 +24614,10 @@ react-popper@^2.2.4: react-fast-compare "^3.0.1" warning "^4.0.2" -react-query@^3.34.7: - version "3.34.7" - resolved "https://registry.yarnpkg.com/react-query/-/react-query-3.34.7.tgz#e3d71318f510ea354794cd188b351bb57f577cb9" - integrity sha512-Q8+H2DgpoZdGUpwW2Z9WAbSrIE+yOdZiCUokHjlniOOmlcsfqNLgvHF5i7rtuCmlw3hv5OAhtpS7e97/DvgpWw== +react-query@^3.39.1: + version "3.39.1" + resolved "https://registry.yarnpkg.com/react-query/-/react-query-3.39.1.tgz#3876c0fdac7a3b5a84e195534e5fa8fbdd628847" + integrity sha512-qYKT1bavdDiQZbngWZyPotlBVzcBjDYEJg5RQLBa++5Ix5jjfbEYJmHSZRZD+USVHUSvl/ey9Hu+QfF1QAK80A== dependencies: "@babel/runtime" "^7.5.5" broadcast-channel "^3.4.1" From 5c56102bf02bae89696d8b59ccab904890c5fd42 Mon Sep 17 00:00:00 2001 From: Giorgos Bamparopoulos Date: Mon, 18 Jul 2022 18:57:54 +0300 Subject: [PATCH 106/111] Top erroneous transactions (#134929) * Add table for top erroneous transactions in error detail page * Add table for top errors in transaction details page * Add top errors to a new row on small viewports Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../src/lib/apm/transaction.ts | 1 + .../errors/error_details.spec.ts | 9 + .../transaction_details.spec.ts | 58 +++++ .../app/error_group_details/index.tsx | 110 +++++---- .../top_erroneous_transactions/index.tsx | 208 +++++++++++++++++ .../service_dependencies_breakdown_chart.tsx | 1 + .../service_overview_errors_table/index.tsx | 2 +- .../transaction_details/top_errors/index.tsx | 204 +++++++++++++++++ .../shared/charts/breakdown_chart/index.tsx | 9 +- .../transaction_breakdown_chart/index.tsx | 1 + .../charts/transaction_charts/index.tsx | 127 +++++++---- .../errors_table}/get_columns.tsx | 126 ++++++----- .../get_top_erroneous_transactions.ts | 196 ++++++++++++++++ .../get_error_group_detailed_statistics.ts | 11 +- .../get_error_group_main_statistics.ts | 20 +- .../plugins/apm/server/routes/errors/route.ts | 116 ++++++++++ .../translations/translations/fr-FR.json | 4 - .../translations/translations/ja-JP.json | 4 - .../translations/translations/zh-CN.json | 4 - .../generate_data.ts | 71 ++++++ .../top_erroneous_transactions.spec.ts | 211 ++++++++++++++++++ .../generate_data.ts | 74 ++++++ .../top_errors_main_stats.spec.ts | 111 +++++++++ 23 files changed, 1512 insertions(+), 166 deletions(-) create mode 100644 x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/transaction_details/transaction_details.spec.ts create mode 100644 x-pack/plugins/apm/public/components/app/error_group_details/top_erroneous_transactions/index.tsx create mode 100644 x-pack/plugins/apm/public/components/app/transaction_details/top_errors/index.tsx rename x-pack/plugins/apm/public/components/{app/service_overview/service_overview_errors_table => shared/errors_table}/get_columns.tsx (53%) create mode 100644 x-pack/plugins/apm/server/routes/errors/erroneous_transactions/get_top_erroneous_transactions.ts create mode 100644 x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/generate_data.ts create mode 100644 x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/top_erroneous_transactions.spec.ts create mode 100644 x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/generate_data.ts create mode 100644 x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/top_errors_main_stats.spec.ts diff --git a/packages/elastic-apm-synthtrace/src/lib/apm/transaction.ts b/packages/elastic-apm-synthtrace/src/lib/apm/transaction.ts index 47924e49e9b84..7ca376824b638 100644 --- a/packages/elastic-apm-synthtrace/src/lib/apm/transaction.ts +++ b/packages/elastic-apm-synthtrace/src/lib/apm/transaction.ts @@ -40,6 +40,7 @@ export class Transaction extends BaseSpan { errors.forEach((error) => { error.fields['trace.id'] = this.fields['trace.id']; error.fields['transaction.id'] = this.fields['transaction.id']; + error.fields['transaction.name'] = this.fields['transaction.name']; error.fields['transaction.type'] = this.fields['transaction.type']; }); diff --git a/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/errors/error_details.spec.ts b/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/errors/error_details.spec.ts index 1911f86791cae..59c0d87029517 100644 --- a/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/errors/error_details.spec.ts +++ b/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/errors/error_details.spec.ts @@ -71,6 +71,15 @@ describe('Error details', () => { cy.get('[data-test-subj="errorDistribution"]').contains('Occurrences'); }); + it('shows top erroneous transactions table', () => { + cy.visit(errorDetailsPageHref); + cy.contains('Top 5 affected transactions'); + cy.get('[data-test-subj="topErroneousTransactionsTable"]') + .contains('a', 'GET /apple 🍎') + .click(); + cy.url().should('include', 'opbeans-java/transactions/view'); + }); + it('shows a Stacktrace and Metadata tabs', () => { cy.visit(errorDetailsPageHref); cy.contains('button', 'Exception stack trace'); diff --git a/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/transaction_details/transaction_details.spec.ts b/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/transaction_details/transaction_details.spec.ts new file mode 100644 index 0000000000000..c5eeda6645ce8 --- /dev/null +++ b/x-pack/plugins/apm/ftr_e2e/cypress/integration/read_only_user/transaction_details/transaction_details.spec.ts @@ -0,0 +1,58 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { synthtrace } from '../../../../synthtrace'; +import { opbeans } from '../../../fixtures/synthtrace/opbeans'; + +const start = '2021-10-10T00:00:00.000Z'; +const end = '2021-10-10T00:15:00.000Z'; + +const timeRange = { + rangeFrom: start, + rangeTo: end, +}; + +describe('Transaction details', () => { + before(async () => { + await synthtrace.index( + opbeans({ + from: new Date(start).getTime(), + to: new Date(end).getTime(), + }) + ); + }); + + after(async () => { + await synthtrace.clean(); + }); + + beforeEach(() => { + cy.loginAsViewerUser(); + cy.visit( + `/app/apm/services/opbeans-java/transactions/view?${new URLSearchParams({ + ...timeRange, + transactionName: 'GET /api/product', + })}` + ); + }); + + it('shows transaction name and transaction charts', () => { + cy.contains('h2', 'GET /api/product'); + cy.get('[data-test-subj="latencyChart"]'); + cy.get('[data-test-subj="throughput"]'); + cy.get('[data-test-subj="transactionBreakdownChart"]'); + cy.get('[data-test-subj="errorRate"]'); + }); + + it('shows top errors table', () => { + cy.contains('Top 5 errors'); + cy.get('[data-test-subj="topErrorsForTransactionTable"]') + .contains('a', '[MockError] Foo') + .click(); + cy.url().should('include', 'opbeans-java/errors'); + }); +}); diff --git a/x-pack/plugins/apm/public/components/app/error_group_details/index.tsx b/x-pack/plugins/apm/public/components/app/error_group_details/index.tsx index bac23d55099a5..7dfaf13e42901 100644 --- a/x-pack/plugins/apm/public/components/app/error_group_details/index.tsx +++ b/x-pack/plugins/apm/public/components/app/error_group_details/index.tsx @@ -13,6 +13,7 @@ import { EuiSpacer, EuiText, EuiTitle, + EuiHorizontalRule, } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; import React from 'react'; @@ -29,6 +30,7 @@ import { useTimeRange } from '../../../hooks/use_time_range'; import type { APIReturnType } from '../../../services/rest/create_call_apm_api'; import { DetailView } from './detail_view'; import { ErrorDistribution } from './distribution'; +import { TopErroneousTransactions } from './top_erroneous_transactions'; const Titles = euiStyled.div` margin-bottom: ${({ theme }) => theme.eui.euiSizeL}; @@ -49,6 +51,7 @@ const Message = euiStyled.div` const Culprit = euiStyled.div` font-family: ${({ theme }) => theme.eui.euiCodeFontFamily}; + margin-bottom: ${({ theme }) => theme.eui.euiSizeS}; `; type ErrorDistributionAPIResponse = @@ -194,52 +197,69 @@ export function ErrorGroupDetails() { - - {showDetails && ( - - - {logMessage && ( - <> - - {logMessage} - + {showDetails && ( + + + {logMessage && ( + <> + + {logMessage} + + )} + - - )} - - + + {excMessage || NOT_AVAILABLE_LABEL} + + {culprit || NOT_AVAILABLE_LABEL} + + + {errorGroupData.occurrencesCount} + + + + )} + + + + + + + + + + + + {showDetails && ( ; + +interface Props { + serviceName: string; +} + +const INITIAL_STATE: ErroneousTransactions = { + topErroneousTransactions: [], +}; + +export function TopErroneousTransactions({ serviceName }: Props) { + const { + query, + path: { groupId }, + } = useApmParams('/services/{serviceName}/errors/{groupId}'); + + const { rangeFrom, rangeTo, environment, kuery, offset, comparisonEnabled } = + query; + + const { start, end } = useTimeRange({ rangeFrom, rangeTo }); + + const { data = INITIAL_STATE, status } = useFetcher( + (callApmApi) => { + if (start && end) { + return callApmApi( + 'GET /internal/apm/services/{serviceName}/errors/{groupId}/top_erroneous_transactions', + { + params: { + path: { + serviceName, + groupId, + }, + query: { + environment, + kuery, + start, + end, + numBuckets: 20, + offset: + comparisonEnabled && isTimeComparison(offset) + ? offset + : undefined, + }, + }, + } + ); + } + }, + [ + environment, + kuery, + serviceName, + start, + end, + groupId, + comparisonEnabled, + offset, + ] + ); + + const loading = + status === FETCH_STATUS.LOADING || status === FETCH_STATUS.NOT_INITIATED; + + const columns: Array< + EuiBasicTableColumn< + ValuesType + > + > = [ + { + field: 'transactionName', + width: '60%', + name: i18n.translate( + 'xpack.apm.errorGroupTopTransactions.column.transactionName', + { + defaultMessage: 'Transaction name', + } + ), + render: (_, { transactionName, transactionType }) => { + return ( + + {transactionName} + + } + /> + ); + }, + }, + { + field: 'occurrences', + name: i18n.translate( + 'xpack.apm.errorGroupTopTransactions.column.occurrences', + { + defaultMessage: 'Error occurrences', + } + ), + align: RIGHT_ALIGNMENT, + dataType: 'number', + render: ( + _, + { occurrences, currentPeriodTimeseries, previousPeriodTimeseries } + ) => { + const { currentPeriodColor, previousPeriodColor } = getTimeSeriesColor( + ChartType.FAILED_TRANSACTION_RATE + ); + + return ( + + ); + }, + }, + ]; + + return ( + <> + +

    + {i18n.translate('xpack.apm.errorGroupTopTransactions.title', { + defaultMessage: 'Top 5 affected transactions', + })} +

    +
    + + + + ); +} diff --git a/x-pack/plugins/apm/public/components/app/service_dependencies/service_dependencies_breakdown_chart.tsx b/x-pack/plugins/apm/public/components/app/service_dependencies/service_dependencies_breakdown_chart.tsx index 85f56a10399b6..93876d1df6004 100644 --- a/x-pack/plugins/apm/public/components/app/service_dependencies/service_dependencies_breakdown_chart.tsx +++ b/x-pack/plugins/apm/public/components/app/service_dependencies/service_dependencies_breakdown_chart.tsx @@ -66,6 +66,7 @@ export function ServiceDependenciesBreakdownChart({ annotations={[]} timeseries={timeseries} yAxisType="duration" + id="serviceDependenciesBreakdownChart" /> ); } diff --git a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_errors_table/index.tsx b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_errors_table/index.tsx index 602bfaa811c3c..340dc4f80da84 100644 --- a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_errors_table/index.tsx +++ b/x-pack/plugins/apm/public/components/app/service_overview/service_overview_errors_table/index.tsx @@ -20,7 +20,7 @@ import { FETCH_STATUS, useFetcher } from '../../../../hooks/use_fetcher'; import { APIReturnType } from '../../../../services/rest/create_call_apm_api'; import { ErrorOverviewLink } from '../../../shared/links/apm/error_overview_link'; import { OverviewTableContainer } from '../../../shared/overview_table_container'; -import { getColumns } from './get_columns'; +import { getColumns } from '../../../shared/errors_table/get_columns'; import { useApmParams } from '../../../../hooks/use_apm_params'; import { useTimeRange } from '../../../../hooks/use_time_range'; diff --git a/x-pack/plugins/apm/public/components/app/transaction_details/top_errors/index.tsx b/x-pack/plugins/apm/public/components/app/transaction_details/top_errors/index.tsx new file mode 100644 index 0000000000000..a2413277c1d13 --- /dev/null +++ b/x-pack/plugins/apm/public/components/app/transaction_details/top_errors/index.tsx @@ -0,0 +1,204 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { + EuiBasicTable, + EuiFlexGroup, + EuiFlexItem, + EuiTitle, +} from '@elastic/eui'; +import { i18n } from '@kbn/i18n'; +import React from 'react'; +import uuid from 'uuid'; +import { isTimeComparison } from '../../../shared/time_comparison/get_comparison_options'; +import { FETCH_STATUS, useFetcher } from '../../../../hooks/use_fetcher'; +import { APIReturnType } from '../../../../services/rest/create_call_apm_api'; +import { getColumns } from '../../../shared/errors_table/get_columns'; +import { useApmParams } from '../../../../hooks/use_apm_params'; +import { useTimeRange } from '../../../../hooks/use_time_range'; + +type ErrorGroupMainStatisticsByTransactionName = + APIReturnType<'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics_by_transaction_name'>; + +type ErrorGroupDetailedStatistics = + APIReturnType<'POST /internal/apm/services/{serviceName}/errors/groups/detailed_statistics'>; + +const INITIAL_STATE_MAIN_STATISTICS: { + items: ErrorGroupMainStatisticsByTransactionName['errorGroups']; + requestId?: string; +} = { + items: [], + requestId: undefined, +}; + +const INITIAL_STATE_DETAILED_STATISTICS: ErrorGroupDetailedStatistics = { + currentPeriod: {}, + previousPeriod: {}, +}; + +export function TopErrors() { + const { + query, + path: { serviceName }, + } = useApmParams('/services/{serviceName}/transactions/view'); + + const { + environment, + kuery, + rangeFrom, + rangeTo, + offset, + comparisonEnabled, + transactionName, + transactionType, + } = query; + + const { start, end } = useTimeRange({ rangeFrom, rangeTo }); + + const { data = INITIAL_STATE_MAIN_STATISTICS, status } = useFetcher( + (callApmApi) => { + if (start && end && transactionType) { + return callApmApi( + 'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics_by_transaction_name', + { + params: { + path: { serviceName }, + query: { + environment, + kuery, + start, + end, + transactionName, + transactionType, + maxNumberOfErrorGroups: 5, + }, + }, + } + ).then((response) => { + return { + // Everytime the main statistics is refetched, updates the requestId making the comparison API to be refetched. + requestId: uuid(), + items: response.errorGroups, + }; + }); + } + }, + // eslint-disable-next-line react-hooks/exhaustive-deps + [ + environment, + kuery, + start, + end, + serviceName, + transactionName, + transactionType, + // not used, but needed to trigger an update when offset is changed either manually by user or when time range is changed + offset, + // not used, but needed to trigger an update when comparison feature is disabled/enabled by user + comparisonEnabled, + ] + ); + + const { requestId, items } = data; + + const { + data: errorGroupDetailedStatistics = INITIAL_STATE_DETAILED_STATISTICS, + status: errorGroupDetailedStatisticsStatus, + } = useFetcher( + (callApmApi) => { + if (requestId && items.length && start && end) { + return callApmApi( + 'POST /internal/apm/services/{serviceName}/errors/groups/detailed_statistics', + { + params: { + path: { serviceName }, + query: { + environment, + kuery, + start, + end, + numBuckets: 20, + offset: + comparisonEnabled && isTimeComparison(offset) + ? offset + : undefined, + }, + body: { + groupIds: JSON.stringify( + items.map(({ groupId: groupId }) => groupId).sort() + ), + }, + }, + } + ); + } + }, + // only fetches agg results when requestId changes + // eslint-disable-next-line react-hooks/exhaustive-deps + [requestId], + { preservePreviousData: false } + ); + + const errorGroupDetailedStatisticsLoading = + errorGroupDetailedStatisticsStatus === FETCH_STATUS.LOADING; + + const columns = getColumns({ + serviceName, + errorGroupDetailedStatisticsLoading, + errorGroupDetailedStatistics, + comparisonEnabled, + query, + showErrorType: false, + }); + + return ( + + + +

    + {i18n.translate('xpack.apm.transactionDetails.topErrors.title', { + defaultMessage: 'Top 5 errors', + })} +

    +
    +
    + + + +
    + ); +} diff --git a/x-pack/plugins/apm/public/components/shared/charts/breakdown_chart/index.tsx b/x-pack/plugins/apm/public/components/shared/charts/breakdown_chart/index.tsx index 6f2fd1072fad0..30353516b6222 100644 --- a/x-pack/plugins/apm/public/components/shared/charts/breakdown_chart/index.tsx +++ b/x-pack/plugins/apm/public/components/shared/charts/breakdown_chart/index.tsx @@ -54,6 +54,7 @@ interface Props { annotations: Annotation[]; timeseries?: Array>; yAxisType: 'duration' | 'percentage'; + id?: string; } const asPercentBound = (y: number | null) => asPercent(y, 1); @@ -65,6 +66,7 @@ export function BreakdownChart({ annotations, timeseries, yAxisType, + id, }: Props) { const history = useHistory(); const chartTheme = useChartTheme(); @@ -94,7 +96,12 @@ export function BreakdownChart({ const timeZone = getTimeZone(core.uiSettings); return ( - + diff --git a/x-pack/plugins/apm/public/components/shared/charts/transaction_charts/index.tsx b/x-pack/plugins/apm/public/components/shared/charts/transaction_charts/index.tsx index c126249d65131..dca71ab547d40 100644 --- a/x-pack/plugins/apm/public/components/shared/charts/transaction_charts/index.tsx +++ b/x-pack/plugins/apm/public/components/shared/charts/transaction_charts/index.tsx @@ -5,7 +5,13 @@ * 2.0. */ -import { EuiFlexGrid, EuiFlexItem, EuiPanel, EuiSpacer } from '@elastic/eui'; +import { + EuiFlexGrid, + EuiFlexItem, + EuiPanel, + EuiSpacer, + EuiFlexGroup, +} from '@elastic/eui'; import React from 'react'; import { AnnotationsContextProvider } from '../../../../context/annotations/annotations_context'; import { ChartPointerEventContextProvider } from '../../../../context/chart_pointer_event/chart_pointer_event_context'; @@ -14,6 +20,8 @@ import { LatencyChart } from '../latency_chart'; import { TransactionBreakdownChart } from '../transaction_breakdown_chart'; import { TransactionColdstartRateChart } from '../transaction_coldstart_rate_chart'; import { FailedTransactionRateChart } from '../failed_transaction_rate_chart'; +import { TopErrors } from '../../../app/transaction_details/top_errors'; +import { useBreakpoints } from '../../../../hooks/use_breakpoints'; export function TransactionCharts({ kuery, @@ -34,6 +42,49 @@ export function TransactionCharts({ comparisonEnabled?: boolean; offset?: string; }) { + // The default EuiFlexGroup breaks at 768, but we want to break at 1200 + const { isLarge } = useBreakpoints(); + const rowDirection = isLarge ? 'column' : 'row'; + + const latencyChart = ( + + + + + + ); + + const serviceOverviewThroughputChart = ( + + + + ); + + const coldStartRateOrBreakdownChart = isServerlessContext ? ( + + + + ) : ( + + + + ); + + const failedTransactionRateChart = ( + + + + ); + return ( <> - - - - - - - - - - - - - - - - - - - {isServerlessContext ? ( - - - - ) : ( - - - - )} - + {transactionName ? ( + <> + + {latencyChart} + {serviceOverviewThroughputChart} + {coldStartRateOrBreakdownChart} + + + + {failedTransactionRateChart} + + + + + + + + ) : ( + <> + + {latencyChart} + {serviceOverviewThroughputChart} + + + + {failedTransactionRateChart} + {coldStartRateOrBreakdownChart} + + + )} diff --git a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_errors_table/get_columns.tsx b/x-pack/plugins/apm/public/components/shared/errors_table/get_columns.tsx similarity index 53% rename from x-pack/plugins/apm/public/components/app/service_overview/service_overview_errors_table/get_columns.tsx rename to x-pack/plugins/apm/public/components/shared/errors_table/get_columns.tsx index 0af05ead4fb24..3a6913688498b 100644 --- a/x-pack/plugins/apm/public/components/app/service_overview/service_overview_errors_table/get_columns.tsx +++ b/x-pack/plugins/apm/public/components/shared/errors_table/get_columns.tsx @@ -5,32 +5,38 @@ * 2.0. */ -import { EuiBasicTableColumn, RIGHT_ALIGNMENT } from '@elastic/eui'; +import { + EuiBasicTableColumn, + RIGHT_ALIGNMENT, + CENTER_ALIGNMENT, +} from '@elastic/eui'; import { i18n } from '@kbn/i18n'; import { TypeOf } from '@kbn/typed-react-router-config'; import React from 'react'; import { euiStyled } from '@kbn/kibana-react-plugin/common'; -import { isTimeComparison } from '../../../shared/time_comparison/get_comparison_options'; -import { asInteger } from '../../../../../common/utils/formatters'; -import { APIReturnType } from '../../../../services/rest/create_call_apm_api'; -import { truncate } from '../../../../utils/style'; -import { SparkPlot } from '../../../shared/charts/spark_plot'; -import { ErrorDetailLink } from '../../../shared/links/apm/error_detail_link'; -import { ErrorOverviewLink } from '../../../shared/links/apm/error_overview_link'; -import { TimestampTooltip } from '../../../shared/timestamp_tooltip'; -import { TruncateWithTooltip } from '../../../shared/truncate_with_tooltip'; +import { isTimeComparison } from '../time_comparison/get_comparison_options'; +import { asInteger } from '../../../../common/utils/formatters'; +import { APIReturnType } from '../../../services/rest/create_call_apm_api'; +import { truncate } from '../../../utils/style'; +import { SparkPlot } from '../charts/spark_plot'; +import { ErrorDetailLink } from '../links/apm/error_detail_link'; +import { ErrorOverviewLink } from '../links/apm/error_overview_link'; +import { TimestampTooltip } from '../timestamp_tooltip'; +import { TruncateWithTooltip } from '../truncate_with_tooltip'; import { ChartType, getTimeSeriesColor, -} from '../../../shared/charts/helper/get_timeseries_color'; -import { ApmRoutes } from '../../../routing/apm_route_config'; +} from '../charts/helper/get_timeseries_color'; +import { ApmRoutes } from '../../routing/apm_route_config'; const ErrorLink = euiStyled(ErrorOverviewLink)` ${truncate('100%')}; `; -type ErrorGroupMainStatistics = - APIReturnType<'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics'>; +type ErrorGroupMainStatistics = APIReturnType< + | 'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics' + | 'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics_by_transaction_name' +>; type ErrorGroupDetailedStatistics = APIReturnType<'POST /internal/apm/services/{serviceName}/errors/groups/detailed_statistics'>; @@ -40,41 +46,50 @@ export function getColumns({ errorGroupDetailedStatistics, comparisonEnabled, query, + showErrorType = true, }: { serviceName: string; errorGroupDetailedStatisticsLoading: boolean; errorGroupDetailedStatistics: ErrorGroupDetailedStatistics; comparisonEnabled?: boolean; query: TypeOf['query']; + showErrorType?: boolean; }): Array> { const { offset } = query; return [ - { - name: i18n.translate('xpack.apm.errorsTable.typeColumnLabel', { - defaultMessage: 'Type', - }), - field: 'type', - sortable: false, - render: (_, { type }) => { - return ( - ['query'] - } - > - {type} - - ); - }, - }, + ...(showErrorType + ? [ + { + name: i18n.translate('xpack.apm.errorsTable.typeColumnLabel', { + defaultMessage: 'Type', + }), + field: 'type', + sortable: false, + render: (_, { type }) => { + return ( + ['query'] + } + > + {type} + + ); + }, + } as EuiBasicTableColumn, + ] + : []), { field: 'name', - name: i18n.translate('xpack.apm.serviceOverview.errorsTableColumnName', { + name: i18n.translate('xpack.apm.errorsTable.columnName', { defaultMessage: 'Name', }), render: (_, { name, groupId: errorGroupId }) => { @@ -95,13 +110,10 @@ export function getColumns({ }, { field: 'lastSeen', - name: i18n.translate( - 'xpack.apm.serviceOverview.errorsTableColumnLastSeen', - { - defaultMessage: 'Last seen', - } - ), - align: RIGHT_ALIGNMENT, + name: i18n.translate('xpack.apm.errorsTable.columnLastSeen', { + defaultMessage: 'Last seen', + }), + align: showErrorType ? RIGHT_ALIGNMENT : CENTER_ALIGNMENT, render: (_, { lastSeen }) => { return ( @@ -112,12 +124,9 @@ export function getColumns({ }, { field: 'occurrences', - name: i18n.translate( - 'xpack.apm.serviceOverview.errorsTableColumnOccurrences', - { - defaultMessage: 'Occurrences', - } - ), + name: i18n.translate('xpack.apm.errorsTable.columnOccurrences', { + defaultMessage: 'Occurrences', + }), align: RIGHT_ALIGNMENT, render: (_, { occurrences, groupId: errorGroupId }) => { const currentPeriodTimeseries = @@ -135,15 +144,12 @@ export function getColumns({ color={currentPeriodColor} isLoading={errorGroupDetailedStatisticsLoading} series={currentPeriodTimeseries} - valueLabel={i18n.translate( - 'xpack.apm.serviceOveriew.errorsTableOccurrences', - { - defaultMessage: `{occurrences} occ.`, - values: { - occurrences: asInteger(occurrences), - }, - } - )} + valueLabel={i18n.translate('xpack.apm.errorsTable.occurrences', { + defaultMessage: `{occurrences} occ.`, + values: { + occurrences: asInteger(occurrences), + }, + })} comparisonSeries={ comparisonEnabled && isTimeComparison(offset) ? previousPeriodTimeseries diff --git a/x-pack/plugins/apm/server/routes/errors/erroneous_transactions/get_top_erroneous_transactions.ts b/x-pack/plugins/apm/server/routes/errors/erroneous_transactions/get_top_erroneous_transactions.ts new file mode 100644 index 0000000000000..6017ad75c1230 --- /dev/null +++ b/x-pack/plugins/apm/server/routes/errors/erroneous_transactions/get_top_erroneous_transactions.ts @@ -0,0 +1,196 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { + rangeQuery, + kqlQuery, + termQuery, +} from '@kbn/observability-plugin/server'; +import { keyBy } from 'lodash'; +import { + ERROR_GROUP_ID, + SERVICE_NAME, + TRANSACTION_NAME, + TRANSACTION_TYPE, +} from '../../../../common/elasticsearch_fieldnames'; +import { ProcessorEvent } from '../../../../common/processor_event'; +import { environmentQuery } from '../../../../common/utils/environment_query'; +import { Setup } from '../../../lib/helpers/setup_request'; +import { getBucketSize } from '../../../lib/helpers/get_bucket_size'; +import { getOffsetInMs } from '../../../../common/utils/get_offset_in_ms'; + +async function getTopErroneousTransactions({ + environment, + kuery, + serviceName, + groupId, + setup, + start, + end, + numBuckets, + offset, +}: { + environment: string; + kuery: string; + serviceName: string; + groupId: string; + setup: Setup; + start: number; + end: number; + numBuckets: number; + offset?: string; +}) { + const { apmEventClient } = setup; + + const { startWithOffset, endWithOffset, offsetInMs } = getOffsetInMs({ + start, + end, + offset, + }); + + const { intervalString } = getBucketSize({ + start: startWithOffset, + end: endWithOffset, + numBuckets, + }); + + const res = await apmEventClient.search('get_top_erroneous_transactions', { + apm: { + events: [ProcessorEvent.error], + }, + body: { + size: 0, + query: { + bool: { + filter: [ + ...termQuery(SERVICE_NAME, serviceName), + ...termQuery(ERROR_GROUP_ID, groupId), + ...rangeQuery(startWithOffset, endWithOffset), + ...environmentQuery(environment), + ...kqlQuery(kuery), + ], + }, + }, + aggs: { + top_five_transactions: { + terms: { + field: TRANSACTION_NAME, + size: 5, + }, + aggs: { + sample: { + top_hits: { + size: 1, + _source: [TRANSACTION_TYPE], + }, + }, + timeseries: { + date_histogram: { + field: '@timestamp', + fixed_interval: intervalString, + extended_bounds: { + min: startWithOffset, + max: endWithOffset, + }, + }, + }, + }, + }, + }, + }, + }); + + return ( + res.aggregations?.top_five_transactions.buckets.map( + ({ key, doc_count: docCount, sample, timeseries }) => ({ + transactionName: key as string, + transactionType: sample.hits.hits[0]._source.transaction?.type, + occurrences: docCount, + timeseries: timeseries.buckets.map((timeseriesBucket) => { + return { + x: timeseriesBucket.key + offsetInMs, + y: timeseriesBucket.doc_count, + }; + }), + }) + ) ?? [] + ); +} + +export async function getTopErroneousTransactionsPeriods({ + kuery, + serviceName, + setup, + numBuckets, + groupId, + environment, + start, + end, + offset, +}: { + kuery: string; + serviceName: string; + setup: Setup; + numBuckets: number; + groupId: string; + environment: string; + start: number; + end: number; + offset?: string; +}) { + const [currentPeriod, previousPeriod] = await Promise.all([ + getTopErroneousTransactions({ + environment, + kuery, + serviceName, + setup, + numBuckets, + groupId, + start, + end, + }), + offset + ? getTopErroneousTransactions({ + environment, + kuery, + serviceName, + setup, + numBuckets, + groupId, + start, + end, + offset, + }) + : [], + ]); + + const previousPeriodByTransactionName = keyBy( + previousPeriod, + 'transactionName' + ); + + return { + topErroneousTransactions: currentPeriod.map( + ({ transactionName, timeseries: currentPeriodTimeseries, ...rest }) => { + return { + ...rest, + transactionName, + currentPeriodTimeseries, + previousPeriodTimeseries: + previousPeriodByTransactionName[transactionName]?.timeseries ?? [], + }; + } + ), + }; +} diff --git a/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_detailed_statistics.ts b/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_detailed_statistics.ts index 12d78e529fd74..99fcf1a6c3f8a 100644 --- a/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_detailed_statistics.ts +++ b/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_detailed_statistics.ts @@ -5,7 +5,12 @@ * 2.0. */ import { keyBy } from 'lodash'; -import { rangeQuery, kqlQuery } from '@kbn/observability-plugin/server'; +import { + rangeQuery, + kqlQuery, + termQuery, + termsQuery, +} from '@kbn/observability-plugin/server'; import { offsetPreviousPeriodCoordinates } from '../../../../common/utils/offset_previous_period_coordinate'; import { Coordinate } from '../../../../typings/timeseries'; import { @@ -64,8 +69,8 @@ export async function getErrorGroupDetailedStatistics({ query: { bool: { filter: [ - { terms: { [ERROR_GROUP_ID]: groupIds } }, - { term: { [SERVICE_NAME]: serviceName } }, + ...termsQuery(ERROR_GROUP_ID, ...groupIds), + ...termQuery(SERVICE_NAME, serviceName), ...rangeQuery(startWithOffset, endWithOffset), ...environmentQuery(environment), ...kqlQuery(kuery), diff --git a/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_main_statistics.ts b/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_main_statistics.ts index 4dce3280ec39c..0b6fea5c4c6a4 100644 --- a/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_main_statistics.ts +++ b/x-pack/plugins/apm/server/routes/errors/get_error_groups/get_error_group_main_statistics.ts @@ -6,7 +6,11 @@ */ import { AggregationsTermsAggregationOrder } from '@elastic/elasticsearch/lib/api/types'; -import { kqlQuery, rangeQuery } from '@kbn/observability-plugin/server'; +import { + kqlQuery, + rangeQuery, + termQuery, +} from '@kbn/observability-plugin/server'; import { ERROR_CULPRIT, ERROR_EXC_HANDLED, @@ -15,6 +19,8 @@ import { ERROR_GROUP_ID, ERROR_LOG_MESSAGE, SERVICE_NAME, + TRANSACTION_NAME, + TRANSACTION_TYPE, } from '../../../../common/elasticsearch_fieldnames'; import { ProcessorEvent } from '../../../../common/processor_event'; import { environmentQuery } from '../../../../common/utils/environment_query'; @@ -30,6 +36,9 @@ export async function getErrorGroupMainStatistics({ sortDirection = 'desc', start, end, + maxNumberOfErrorGroups = 500, + transactionName, + transactionType, }: { kuery: string; serviceName: string; @@ -39,6 +48,9 @@ export async function getErrorGroupMainStatistics({ sortDirection?: 'asc' | 'desc'; start: number; end: number; + maxNumberOfErrorGroups?: number; + transactionName?: string; + transactionType?: string; }) { const { apmEventClient } = setup; @@ -62,7 +74,9 @@ export async function getErrorGroupMainStatistics({ query: { bool: { filter: [ - { term: { [SERVICE_NAME]: serviceName } }, + ...termQuery(SERVICE_NAME, serviceName), + ...termQuery(TRANSACTION_NAME, transactionName), + ...termQuery(TRANSACTION_TYPE, transactionType), ...rangeQuery(start, end), ...environmentQuery(environment), ...kqlQuery(kuery), @@ -73,7 +87,7 @@ export async function getErrorGroupMainStatistics({ error_groups: { terms: { field: ERROR_GROUP_ID, - size: 500, + size: maxNumberOfErrorGroups, order, }, aggs: { diff --git a/x-pack/plugins/apm/server/routes/errors/route.ts b/x-pack/plugins/apm/server/routes/errors/route.ts index f49ab9aaca8e0..17faea2765daa 100644 --- a/x-pack/plugins/apm/server/routes/errors/route.ts +++ b/x-pack/plugins/apm/server/routes/errors/route.ts @@ -15,6 +15,7 @@ import { getErrorGroupMainStatistics } from './get_error_groups/get_error_group_ import { getErrorGroupPeriods } from './get_error_groups/get_error_group_detailed_statistics'; import { getErrorGroupSample } from './get_error_groups/get_error_group_sample'; import { offsetRt } from '../../../common/comparison_rt'; +import { getTopErroneousTransactionsPeriods } from './erroneous_transactions/get_top_erroneous_transactions'; const errorsMainStatisticsRoute = createApmServerRoute({ endpoint: @@ -68,6 +69,67 @@ const errorsMainStatisticsRoute = createApmServerRoute({ }, }); +const errorsMainStatisticsByTransactionNameRoute = createApmServerRoute({ + endpoint: + 'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics_by_transaction_name', + params: t.type({ + path: t.type({ + serviceName: t.string, + }), + query: t.intersection([ + t.type({ + transactionType: t.string, + transactionName: t.string, + maxNumberOfErrorGroups: toNumberRt, + }), + environmentRt, + kueryRt, + rangeRt, + ]), + }), + options: { tags: ['access:apm'] }, + handler: async ( + resources + ): Promise<{ + errorGroups: Array<{ + groupId: string; + name: string; + lastSeen: number; + occurrences: number; + culprit: string | undefined; + handled: boolean | undefined; + type: string | undefined; + }>; + }> => { + const { params } = resources; + const setup = await setupRequest(resources); + const { serviceName } = params.path; + const { + environment, + kuery, + start, + end, + transactionName, + transactionType, + maxNumberOfErrorGroups, + } = params.query; + + const errorGroups = await getErrorGroupMainStatistics({ + environment, + kuery, + serviceName, + setup, + start, + end, + maxNumberOfErrorGroups, + transactionName, + transactionType, + }); + + return { errorGroups }; + }, +}); + const errorsDetailedStatisticsRoute = createApmServerRoute({ endpoint: 'POST /internal/apm/services/{serviceName}/errors/groups/detailed_statistics', @@ -205,9 +267,63 @@ const errorDistributionRoute = createApmServerRoute({ }, }); +const topErroneousTransactionsRoute = createApmServerRoute({ + endpoint: + 'GET /internal/apm/services/{serviceName}/errors/{groupId}/top_erroneous_transactions', + params: t.type({ + path: t.type({ + serviceName: t.string, + groupId: t.string, + }), + query: t.intersection([ + environmentRt, + kueryRt, + rangeRt, + offsetRt, + t.type({ + numBuckets: toNumberRt, + }), + ]), + }), + options: { tags: ['access:apm'] }, + handler: async ( + resources + ): Promise<{ + topErroneousTransactions: Array<{ + transactionName: string; + currentPeriodTimeseries: Array<{ x: number; y: number }>; + previousPeriodTimeseries: Array<{ x: number; y: number }>; + transactionType: string | undefined; + occurrences: number; + }>; + }> => { + const { params } = resources; + const setup = await setupRequest(resources); + + const { + path: { serviceName, groupId }, + query: { environment, kuery, numBuckets, start, end, offset }, + } = params; + + return await getTopErroneousTransactionsPeriods({ + environment, + groupId, + kuery, + serviceName, + setup, + start, + end, + numBuckets, + offset, + }); + }, +}); + export const errorsRouteRepository = { ...errorsMainStatisticsRoute, + ...errorsMainStatisticsByTransactionNameRoute, ...errorsDetailedStatisticsRoute, ...errorGroupsRoute, ...errorDistributionRoute, + ...topErroneousTransactionsRoute, }; diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index c2b568b87528b..0f5c4ea5ea800 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -8066,7 +8066,6 @@ "xpack.apm.serviceNodeMetrics.unidentifiedServiceNodesWarningText": "Nous n'avons pas pu déterminer à quelles JVM ces indicateurs correspondent. Cela provient probablement du fait que vous exécutez une version du serveur APM antérieure à 7.5. La mise à niveau du serveur APM vers la version 7.5 ou supérieure devrait résoudre le problème. Pour plus d'informations sur la mise à niveau, consultez {link}. Vous pouvez également utiliser la barre de recherche de Kibana pour filtrer par nom d'hôte, par ID de conteneur ou en fonction d'autres champs.", "xpack.apm.serviceNodeMetrics.unidentifiedServiceNodesWarningTitle": "Impossible d'identifier les JVM", "xpack.apm.serviceNodeNameMissing": "(vide)", - "xpack.apm.serviceOveriew.errorsTableOccurrences": "{occurrences} occ.", "xpack.apm.serviceOverview.coldstartHelp": "Le taux de démarrage à froid indique le pourcentage de demandes qui déclenchent un démarrage à froid d'une fonction sans serveur.", "xpack.apm.serviceOverview.dependenciesTableColumn": "Dépendance", "xpack.apm.serviceOverview.dependenciesTableTabLink": "Afficher les dépendances", @@ -8075,9 +8074,6 @@ "xpack.apm.serviceOverview.errorsTable.errorMessage": "Impossible de récupérer", "xpack.apm.serviceOverview.errorsTable.loading": "Chargement...", "xpack.apm.serviceOverview.errorsTable.noResults": "Aucune erreur trouvée", - "xpack.apm.serviceOverview.errorsTableColumnLastSeen": "Vu en dernier", - "xpack.apm.serviceOverview.errorsTableColumnName": "Nom", - "xpack.apm.serviceOverview.errorsTableColumnOccurrences": "Occurrences", "xpack.apm.serviceOverview.errorsTableLinkText": "Afficher les erreurs", "xpack.apm.serviceOverview.errorsTableTitle": "Erreurs", "xpack.apm.serviceOverview.instancesTable.actionMenus.container.subtitle": "Affichez les logs et les indicateurs de ce conteneur pour plus de détails.", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index 0ddcc7feee2d0..5ecfa373923e5 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -8058,7 +8058,6 @@ "xpack.apm.serviceNodeMetrics.unidentifiedServiceNodesWarningText": "これらのメトリックが所属する JVM を特定できませんでした。7.5 よりも古い APM Server を実行していることが原因である可能性が高いです。この問題は APM Server 7.5 以降にアップグレードすることで解決されます。アップグレードに関する詳細は、{link} をご覧ください。代わりに Kibana クエリバーを使ってホスト名、コンテナー ID、またはその他フィールドでフィルタリングすることもできます。", "xpack.apm.serviceNodeMetrics.unidentifiedServiceNodesWarningTitle": "JVM を特定できませんでした", "xpack.apm.serviceNodeNameMissing": "(空)", - "xpack.apm.serviceOveriew.errorsTableOccurrences": "{occurrences}件", "xpack.apm.serviceOverview.coldstartHelp": "コールドスタート率は、サーバーレス機能のコールドスタートをトリガーするリクエストの割合を示します。", "xpack.apm.serviceOverview.dependenciesTableColumn": "依存関係", "xpack.apm.serviceOverview.dependenciesTableTabLink": "依存関係を表示", @@ -8067,9 +8066,6 @@ "xpack.apm.serviceOverview.errorsTable.errorMessage": "取得できませんでした", "xpack.apm.serviceOverview.errorsTable.loading": "読み込み中...", "xpack.apm.serviceOverview.errorsTable.noResults": "エラーが見つかりません", - "xpack.apm.serviceOverview.errorsTableColumnLastSeen": "前回の認識", - "xpack.apm.serviceOverview.errorsTableColumnName": "名前", - "xpack.apm.serviceOverview.errorsTableColumnOccurrences": "オカレンス", "xpack.apm.serviceOverview.errorsTableLinkText": "エラーを表示", "xpack.apm.serviceOverview.errorsTableTitle": "エラー", "xpack.apm.serviceOverview.instancesTable.actionMenus.container.subtitle": "このコンテナーのログとインデックスを表示し、さらに詳細を確認できます。", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index 5ac4f914cbfe9..4a8dba1ccb061 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -8072,7 +8072,6 @@ "xpack.apm.serviceNodeMetrics.unidentifiedServiceNodesWarningText": "无法识别这些指标属于哪些 JVM。这可能因为运行的 APM Server 版本低于 7.5。如果升级到 APM Server 7.5 或更高版本,应可解决此问题。有关升级的详细信息,请参阅 {link}。或者,也可以使用 Kibana 查询栏按主机名、容器 ID 或其他字段筛选。", "xpack.apm.serviceNodeMetrics.unidentifiedServiceNodesWarningTitle": "找不到 JVM", "xpack.apm.serviceNodeNameMissing": "(空)", - "xpack.apm.serviceOveriew.errorsTableOccurrences": "{occurrences} 次", "xpack.apm.serviceOverview.coldstartHelp": "冷启动速率指示触发无服务器功能冷启动的请求百分比。", "xpack.apm.serviceOverview.dependenciesTableColumn": "依赖项", "xpack.apm.serviceOverview.dependenciesTableTabLink": "查看依赖项", @@ -8081,9 +8080,6 @@ "xpack.apm.serviceOverview.errorsTable.errorMessage": "无法提取", "xpack.apm.serviceOverview.errorsTable.loading": "正在加载……", "xpack.apm.serviceOverview.errorsTable.noResults": "未找到错误", - "xpack.apm.serviceOverview.errorsTableColumnLastSeen": "最后看到时间", - "xpack.apm.serviceOverview.errorsTableColumnName": "名称", - "xpack.apm.serviceOverview.errorsTableColumnOccurrences": "发生次数", "xpack.apm.serviceOverview.errorsTableLinkText": "查看错误", "xpack.apm.serviceOverview.errorsTableTitle": "错误", "xpack.apm.serviceOverview.instancesTable.actionMenus.container.subtitle": "查看此容器的日志和指标以获取进一步详情。", diff --git a/x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/generate_data.ts b/x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/generate_data.ts new file mode 100644 index 0000000000000..e84021771cf9c --- /dev/null +++ b/x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/generate_data.ts @@ -0,0 +1,71 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import { apm, timerange } from '@elastic/apm-synthtrace'; +import type { ApmSynthtraceEsClient } from '@elastic/apm-synthtrace'; + +export const config = { + firstTransaction: { + name: 'GET /apple 🍎 ', + successRate: 75, + failureRate: 25, + }, + secondTransaction: { + name: 'GET /banana 🍌', + successRate: 50, + failureRate: 50, + }, +}; + +export async function generateData({ + synthtraceEsClient, + serviceName, + start, + end, +}: { + synthtraceEsClient: ApmSynthtraceEsClient; + serviceName: string; + start: number; + end: number; +}) { + const serviceGoProdInstance = apm.service(serviceName, 'production', 'go').instance('instance-a'); + + const interval = '1m'; + + const { firstTransaction, secondTransaction } = config; + + const documents = [firstTransaction, secondTransaction].map((transaction) => { + return timerange(start, end) + .interval(interval) + .rate(transaction.successRate) + .generator((timestamp) => + serviceGoProdInstance + .transaction(transaction.name) + .timestamp(timestamp) + .duration(1000) + .success() + ) + .merge( + timerange(start, end) + .interval(interval) + .rate(transaction.failureRate) + .generator((timestamp) => + serviceGoProdInstance + .transaction(transaction.name) + .errors( + serviceGoProdInstance + .error('Error 1', transaction.name, 'Error test') + .timestamp(timestamp) + ) + .duration(1000) + .timestamp(timestamp) + .failure() + ) + ); + }); + + await synthtraceEsClient.index(documents); +} diff --git a/x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/top_erroneous_transactions.spec.ts b/x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/top_erroneous_transactions.spec.ts new file mode 100644 index 0000000000000..8e8078e00ab7a --- /dev/null +++ b/x-pack/test/apm_api_integration/tests/errors/top_erroneous_transactions/top_erroneous_transactions.spec.ts @@ -0,0 +1,211 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import expect from '@kbn/expect'; +import { + APIClientRequestParamsOf, + APIReturnType, +} from '@kbn/apm-plugin/public/services/rest/create_call_apm_api'; +import { RecursivePartial } from '@kbn/apm-plugin/typings/common'; +import { sumBy, first, last } from 'lodash'; +import { isFiniteNumber } from '@kbn/apm-plugin/common/utils/is_finite_number'; +import { FtrProviderContext } from '../../../common/ftr_provider_context'; +import { config, generateData } from './generate_data'; + +type ErroneousTransactions = + APIReturnType<'GET /internal/apm/services/{serviceName}/errors/{groupId}/top_erroneous_transactions'>; + +export default function ApiTest({ getService }: FtrProviderContext) { + const registry = getService('registry'); + const apmApiClient = getService('apmApiClient'); + const synthtraceEsClient = getService('synthtraceEsClient'); + + const serviceName = 'synth-go'; + const start = new Date('2021-01-01T00:00:00.000Z').getTime(); + const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; + + async function callApi( + overrides?: RecursivePartial< + APIClientRequestParamsOf<'GET /internal/apm/services/{serviceName}/errors/{groupId}/top_erroneous_transactions'>['params'] + > + ) { + const response = await apmApiClient.readUser({ + endpoint: + 'GET /internal/apm/services/{serviceName}/errors/{groupId}/top_erroneous_transactions', + params: { + path: { + serviceName, + groupId: 'test', + ...overrides?.path, + }, + query: { + start: new Date(start).toISOString(), + end: new Date(end).toISOString(), + environment: 'ENVIRONMENT_ALL', + kuery: '', + offset: undefined, + numBuckets: 15, + ...overrides?.query, + }, + }, + }); + return response; + } + + registry.when('when data is not loaded', { config: 'basic', archives: [] }, () => { + it('handles the empty state', async () => { + const response = await callApi(); + expect(response.status).to.be(200); + expect(response.body.topErroneousTransactions).to.be.empty(); + }); + }); + + registry.when( + 'when data is loaded', + { config: 'basic', archives: ['apm_mappings_only_8.0.0'] }, + () => { + const { + firstTransaction: { name: firstTransactionName, failureRate: firstTransactionFailureRate }, + secondTransaction: { + name: secondTransactionName, + failureRate: secondTransactionFailureRate, + }, + } = config; + + describe('returns the correct data', () => { + before(async () => { + await generateData({ serviceName, start, end, synthtraceEsClient }); + }); + + after(() => synthtraceEsClient.clean()); + + describe('without comparison', () => { + const numberOfBuckets = 15; + let erroneousTransactions: ErroneousTransactions; + + before(async () => { + const response = await callApi({ + path: { groupId: '0000000000000000000000Error test' }, + }); + erroneousTransactions = response.body; + }); + + it('displays the correct number of occurrences', () => { + const { topErroneousTransactions } = erroneousTransactions; + expect(topErroneousTransactions.length).to.be(2); + + const firstTransaction = topErroneousTransactions.find( + (x) => x.transactionName === firstTransactionName + ); + expect(firstTransaction).to.not.be(undefined); + expect(firstTransaction?.occurrences).to.be( + firstTransactionFailureRate * numberOfBuckets + ); + + const secondTransaction = topErroneousTransactions.find( + (x) => x.transactionName === secondTransactionName + ); + expect(secondTransaction).to.not.be(undefined); + expect(secondTransaction?.occurrences).to.be( + secondTransactionFailureRate * numberOfBuckets + ); + }); + + it('displays the correct number of occurrences in time series', () => { + const { topErroneousTransactions } = erroneousTransactions; + + const firstTransaction = topErroneousTransactions.find( + (x) => x.transactionName === firstTransactionName + ); + const firstErrorCount = sumBy(firstTransaction?.currentPeriodTimeseries, 'y'); + expect(firstErrorCount).to.be(firstTransactionFailureRate * numberOfBuckets); + + const secondTransaction = topErroneousTransactions.find( + (x) => x.transactionName === secondTransactionName + ); + const secondErrorCount = sumBy(secondTransaction?.currentPeriodTimeseries, 'y'); + expect(secondErrorCount).to.be(secondTransactionFailureRate * numberOfBuckets); + }); + }); + + describe('with comparison', () => { + describe('when there are data for the time periods', () => { + let erroneousTransactions: ErroneousTransactions; + + before(async () => { + const fiveMinutes = 5 * 60 * 1000; + const response = await callApi({ + path: { groupId: '0000000000000000000000Error test' }, + query: { + start: new Date(end - fiveMinutes).toISOString(), + end: new Date(end).toISOString(), + offset: '5m', + }, + }); + erroneousTransactions = response.body; + }); + + it('returns some data', () => { + const { topErroneousTransactions } = erroneousTransactions; + + const hasCurrentPeriodData = topErroneousTransactions[0].currentPeriodTimeseries.some( + ({ y }) => isFiniteNumber(y) + ); + + const hasPreviousPeriodData = + topErroneousTransactions[0].previousPeriodTimeseries.some(({ y }) => + isFiniteNumber(y) + ); + + expect(hasCurrentPeriodData).to.be(true); + expect(hasPreviousPeriodData).to.be(true); + }); + + it('has the same start time for both periods', () => { + const { topErroneousTransactions } = erroneousTransactions; + expect(first(topErroneousTransactions[0].currentPeriodTimeseries)?.x).to.be( + first(topErroneousTransactions[0].previousPeriodTimeseries)?.x + ); + }); + + it('has same end time for both periods', () => { + const { topErroneousTransactions } = erroneousTransactions; + expect(last(topErroneousTransactions[0].currentPeriodTimeseries)?.x).to.be( + last(topErroneousTransactions[0].previousPeriodTimeseries)?.x + ); + }); + + it('returns same number of buckets for both periods', () => { + const { topErroneousTransactions } = erroneousTransactions; + expect(topErroneousTransactions[0].currentPeriodTimeseries.length).to.be( + topErroneousTransactions[0].previousPeriodTimeseries.length + ); + }); + }); + + describe('when there are no data for the time period', () => { + it('returns an empty array', async () => { + const response = await callApi({ + path: { groupId: '0000000000000000000000Error test' }, + query: { + start: '2021-01-03T00:00:00.000Z', + end: '2021-01-03T00:15:00.000Z', + offset: '1d', + }, + }); + + const { + body: { topErroneousTransactions }, + } = response; + + expect(topErroneousTransactions).to.be.empty(); + }); + }); + }); + }); + } + ); +} diff --git a/x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/generate_data.ts b/x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/generate_data.ts new file mode 100644 index 0000000000000..ca93406af1770 --- /dev/null +++ b/x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/generate_data.ts @@ -0,0 +1,74 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import { apm, timerange } from '@elastic/apm-synthtrace'; +import type { ApmSynthtraceEsClient } from '@elastic/apm-synthtrace'; + +export const config = { + firstTransaction: { + name: 'GET /apple 🍎', + successRate: 75, + failureRate: 25, + }, + secondTransaction: { + name: 'GET /banana 🍌', + successRate: 50, + failureRate: 50, + }, +}; + +export async function generateData({ + synthtraceEsClient, + serviceName, + start, + end, +}: { + synthtraceEsClient: ApmSynthtraceEsClient; + serviceName: string; + start: number; + end: number; +}) { + const serviceGoProdInstance = apm.service(serviceName, 'production', 'go').instance('instance-a'); + + const interval = '1m'; + + const { firstTransaction, secondTransaction } = config; + + const documents = [firstTransaction, secondTransaction].map((transaction, index) => { + return timerange(start, end) + .interval(interval) + .rate(transaction.successRate) + .generator((timestamp) => + serviceGoProdInstance + .transaction(transaction.name) + .timestamp(timestamp) + .duration(1000) + .success() + ) + .merge( + timerange(start, end) + .interval(interval) + .rate(transaction.failureRate) + .generator((timestamp) => + serviceGoProdInstance + .transaction(transaction.name) + .errors( + serviceGoProdInstance + .error(`Error 1 transaction ${transaction.name}`) + .timestamp(timestamp), + serviceGoProdInstance + .error(`Error 2 transaction ${transaction.name}`) + .timestamp(timestamp) + ) + .duration(1000) + .timestamp(timestamp) + .failure() + ) + ); + }); + + await synthtraceEsClient.index(documents); +} diff --git a/x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/top_errors_main_stats.spec.ts b/x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/top_errors_main_stats.spec.ts new file mode 100644 index 0000000000000..75d3ba0624375 --- /dev/null +++ b/x-pack/test/apm_api_integration/tests/errors/top_errors_for_transaction/top_errors_main_stats.spec.ts @@ -0,0 +1,111 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import expect from '@kbn/expect'; +import { + APIClientRequestParamsOf, + APIReturnType, +} from '@kbn/apm-plugin/public/services/rest/create_call_apm_api'; +import { RecursivePartial } from '@kbn/apm-plugin/typings/common'; +import moment from 'moment'; +import { FtrProviderContext } from '../../../common/ftr_provider_context'; +import { config, generateData } from './generate_data'; + +type ErrorGroups = + APIReturnType<'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics_by_transaction_name'>['errorGroups']; + +export default function ApiTest({ getService }: FtrProviderContext) { + const registry = getService('registry'); + const apmApiClient = getService('apmApiClient'); + const synthtraceEsClient = getService('synthtraceEsClient'); + + const serviceName = 'synth-go'; + const start = new Date('2021-01-01T00:00:00.000Z').getTime(); + const end = new Date('2021-01-01T00:15:00.000Z').getTime() - 1; + + async function callApi( + overrides?: RecursivePartial< + APIClientRequestParamsOf<'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics_by_transaction_name'>['params'] + > + ) { + return await apmApiClient.readUser({ + endpoint: + 'GET /internal/apm/services/{serviceName}/errors/groups/main_statistics_by_transaction_name', + params: { + path: { serviceName, ...overrides?.path }, + query: { + start: new Date(start).toISOString(), + end: new Date(end).toISOString(), + environment: 'ENVIRONMENT_ALL', + kuery: '', + maxNumberOfErrorGroups: 5, + transactionType: 'request', + transactionName: '', + ...overrides?.query, + }, + }, + }); + } + + registry.when('when data is not loaded', { config: 'basic', archives: [] }, () => { + it('handles empty state', async () => { + const response = await callApi(); + expect(response.status).to.be(200); + expect(response.body.errorGroups).to.empty(); + }); + }); + + registry.when( + 'when data is loaded', + { config: 'basic', archives: ['apm_mappings_only_8.0.0'] }, + () => { + describe('top errors for transaction', () => { + const { + firstTransaction: { + name: firstTransactionName, + failureRate: firstTransactionFailureRate, + }, + } = config; + + before(async () => { + await generateData({ serviceName, start, end, synthtraceEsClient }); + }); + + after(() => synthtraceEsClient.clean()); + + describe('returns the correct data', () => { + let errorGroups: ErrorGroups; + before(async () => { + const response = await callApi({ query: { transactionName: firstTransactionName } }); + errorGroups = response.body.errorGroups; + }); + + it('returns correct number of errors and error data', () => { + const numberOfBuckets = 15; + + expect(errorGroups.length).to.equal(2); + + const firstErrorId = `Error 1 transaction ${firstTransactionName}`; + const firstError = errorGroups.find((x) => x.groupId === firstErrorId); + expect(firstError).to.not.be(undefined); + expect(firstError?.groupId).to.be(firstErrorId); + expect(firstError?.name).to.be(firstErrorId); + expect(firstError?.occurrences).to.be(firstTransactionFailureRate * numberOfBuckets); + expect(firstError?.lastSeen).to.be(moment(end).startOf('minute').valueOf()); + + const secondErrorId = `Error 2 transaction ${firstTransactionName}`; + const secondError = errorGroups.find((x) => x.groupId === secondErrorId); + expect(secondError).to.not.be(undefined); + expect(secondError?.groupId).to.be(secondErrorId); + expect(secondError?.name).to.be(secondErrorId); + expect(secondError?.occurrences).to.be(firstTransactionFailureRate * numberOfBuckets); + expect(secondError?.lastSeen).to.be(moment(end).startOf('minute').valueOf()); + }); + }); + }); + } + ); +} From 99a01902ca24a886f1bd5481862e9481809158ed Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 18 Jul 2022 11:07:21 -0500 Subject: [PATCH 107/111] Update dependency core-js to ^3.23.5 (main) (#136489) * Update dependency core-js to ^3.23.5 * dedupe Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Jonathan Budzenski --- package.json | 2 +- yarn.lock | 8 ++++---- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/package.json b/package.json index 2f0113b0714ef..0ac03ee814d60 100644 --- a/package.json +++ b/package.json @@ -328,7 +328,7 @@ "constate": "^1.3.2", "content-disposition": "0.5.3", "copy-to-clipboard": "^3.0.8", - "core-js": "^3.22.8", + "core-js": "^3.23.5", "cronstrue": "^1.51.0", "cytoscape": "^3.10.0", "cytoscape-dagre": "^2.2.2", diff --git a/yarn.lock b/yarn.lock index 10d92952cb525..09706189e02aa 100644 --- a/yarn.lock +++ b/yarn.lock @@ -11835,10 +11835,10 @@ core-js@^2.4.0, core-js@^2.5.0, core-js@^2.6.9: resolved "https://registry.yarnpkg.com/core-js/-/core-js-2.6.9.tgz#6b4b214620c834152e179323727fc19741b084f2" integrity sha512-HOpZf6eXmnl7la+cUdMnLvUxKNqLUzJvgIziQ0DiF3JwSImNphIqdGqzj6hIKyX04MmV0poclQ7+wjWvxQyR2A== -core-js@^3.0.4, core-js@^3.22.8, core-js@^3.6.5, core-js@^3.8.2, core-js@^3.8.3: - version "3.22.8" - resolved "https://registry.yarnpkg.com/core-js/-/core-js-3.22.8.tgz#23f860b1fe60797cc4f704d76c93fea8a2f60631" - integrity sha512-UoGQ/cfzGYIuiq6Z7vWL1HfkE9U9IZ4Ub+0XSiJTCzvbZzgPA69oDF2f+lgJ6dFFLEdjW5O6svvoKzXX23xFkA== +core-js@^3.0.4, core-js@^3.6.5, core-js@^3.8.2, core-js@^3.8.3, core-js@^3.23.5: + version "3.23.5" + resolved "https://registry.yarnpkg.com/core-js/-/core-js-3.23.5.tgz#1f82b0de5eece800827a2f59d597509c67650475" + integrity sha512-7Vh11tujtAZy82da4duVreQysIoO2EvVrur7y6IzZkH1IHPSekuDi8Vuw1+YKjkbfWLRD7Nc9ICQ/sIUDutcyg== core-util-is@1.0.2, core-util-is@^1.0.2, core-util-is@~1.0.0: version "1.0.2" From 0f3e46749b6f8fa9f8d06a0af79ad3ce2aada02b Mon Sep 17 00:00:00 2001 From: Jonathan Buttner <56361221+jonathan-buttner@users.noreply.github.com> Date: Mon, 18 Jul 2022 12:15:09 -0400 Subject: [PATCH 108/111] [Cases][ResponseOps] Add support for deletion sub feature privilege (#135487) * Starting conversion to permissions from userCanCrud * Migrating userCanCrud to context * Fixing tests * Fix type error * Removing missed userCanCrud * Fixing tests and addressing permissions.all feedback * Fixing test * Adding deletion sub feature priv * Fixing type errors * Fixing tests and adding more granular permissions * Trying to get plugin tests to work * Removing unnecessary tests * First pass at fixing tests * Moving createUICapabilities to a normal function * Adding more tests for permissions * Fixing tests * Fixing and adding more tests * Addressing feedback and fixing tests * Reverting permissions.all changes except delete * Revert "Reverting permissions.all changes except delete" This reverts commit 609c150b7d6c1186055a1ba14a84f49f4902bb77. * Fixing test * Adjusting permissions for add to new or existing case * Switching a few all permissions to create and read * check permisions inside of actions menu * Addressing initial feedback * Adding functional tests for deletion * Changing deletion text * Addressing feedback and fixing tests * Fixing deeplinks to allow create when no delete * Addressing feedback Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .github/CODEOWNERS | 1 + x-pack/plugins/cases/common/constants.ts | 14 + x-pack/plugins/cases/common/index.ts | 19 +- x-pack/plugins/cases/common/ui/types.ts | 24 ++ .../cases/common/utils/capabilities.ts | 29 ++ x-pack/plugins/cases/common/utils/index.ts | 1 + .../client/helpers/can_use_cases.test.ts | 141 +++--- .../public/client/helpers/can_use_cases.ts | 60 ++- .../client/helpers/capabilities.test.ts | 104 +++++ .../public/client/helpers/capabilities.ts | 26 +- .../public/common/lib/kibana/hooks.test.tsx | 4 +- .../cases/public/common/lib/kibana/hooks.ts | 11 +- .../common/lib/kibana/kibana_react.mock.ts | 8 +- .../public/common/mock/test_providers.tsx | 60 ++- .../components/add_comment/index.test.tsx | 6 +- .../public/components/add_comment/index.tsx | 2 +- .../all_cases/all_cases_list.test.tsx | 21 +- .../components/all_cases/all_cases_list.tsx | 6 +- .../public/components/all_cases/columns.tsx | 4 +- .../components/all_cases/header.test.tsx | 56 +++ .../public/components/all_cases/header.tsx | 11 +- .../components/all_cases/index.test.tsx | 38 +- .../components/all_cases/nav_buttons.tsx | 57 ++- ..._cases_add_to_existing_case_modal.test.tsx | 7 +- .../public/components/all_cases/table.tsx | 6 +- .../public/components/app/routes.test.tsx | 17 +- .../cases/public/components/app/routes.tsx | 4 +- .../app/use_available_owners.test.ts | 44 +- .../components/app/use_available_owners.ts | 42 +- .../components/app/use_readonly_header.ts | 3 +- .../case_action_bar/actions.test.tsx | 13 +- .../components/case_action_bar/actions.tsx | 28 +- .../components/case_action_bar/index.test.tsx | 62 ++- .../components/case_action_bar/index.tsx | 13 +- .../components/case_view_activity.test.tsx | 30 +- .../components/case_view_activity.tsx | 4 +- .../public/components/cases_context/index.tsx | 7 +- .../components/configure_cases/index.test.tsx | 6 +- .../components/configure_cases/index.tsx | 6 +- .../components/edit_connector/index.test.tsx | 23 + .../components/edit_connector/index.tsx | 6 +- .../editable_title.test.tsx.snap | 4 + .../__snapshots__/index.test.tsx.snap | 4 + .../components/header_page/editable_title.tsx | 2 +- .../recent_cases/no_cases/index.test.tsx | 2 +- .../recent_cases/no_cases/index.tsx | 2 +- .../public/components/tag_list/index.test.tsx | 2 +- .../public/components/tag_list/index.tsx | 2 +- .../use_push_to_service/index.test.tsx | 20 +- .../components/use_push_to_service/index.tsx | 12 +- .../public/components/user_actions/index.tsx | 2 +- .../user_actions/property_actions.test.tsx | 138 ++++-- .../user_actions/property_actions.tsx | 93 ++-- x-pack/plugins/cases/public/mocks.ts | 8 + x-pack/plugins/cases/public/plugin.ts | 2 + x-pack/plugins/cases/public/types.ts | 6 +- .../plugins/cases/public/utils/permissions.ts | 19 + x-pack/plugins/cases/server/features.ts | 112 +++-- .../action_menu/action_menu.test.tsx | 9 + .../exploratory_view.test.tsx | 6 + .../header/add_to_case_action.test.tsx | 16 +- .../header/add_to_case_action.tsx | 5 +- .../hooks/use_alert_bulk_case_actions.ts | 13 +- .../use_get_user_cases_permissions.test.ts | 79 ---- .../hooks/use_get_user_cases_permissions.tsx | 43 +- ...observability_public_plugins_start.mock.ts | 13 +- .../containers/alerts_page/alerts_page.tsx | 5 +- .../alerts_table_t_grid.tsx | 13 +- .../public/pages/cases/cases.tsx | 7 +- .../public/pages/cases/index.tsx | 6 +- .../public/pages/overview/index.tsx | 5 +- .../public/utils/cases_permissions.ts | 15 + x-pack/plugins/observability/server/plugin.ts | 45 +- .../integration/cases/privileges.spec.ts | 26 +- .../cypress/tasks/privileges.ts | 62 +++ .../security_solution/public/app/app.tsx | 5 +- .../public/app/deep_links/index.test.ts | 45 +- .../public/app/deep_links/index.ts | 47 +- .../security_solution/public/cases/links.ts | 11 +- .../public/cases/pages/index.tsx | 5 +- .../public/cases_test_utils.ts | 66 +++ .../event_details/related_cases.test.tsx | 9 +- .../event_details/related_cases.tsx | 4 +- .../index.test.tsx | 22 +- .../visualization_actions/index.test.tsx | 6 +- .../use_add_to_existing_case.test.tsx | 30 +- .../use_add_to_existing_case.tsx | 8 +- .../use_add_to_new_case.test.tsx | 29 +- .../use_add_to_new_case.tsx | 8 +- .../public/common/lib/kibana/hooks.ts | 34 +- .../common/lib/kibana/kibana_react.mock.ts | 12 +- .../public/common/links/links.test.ts | 116 +++++ .../public/common/links/links.ts | 32 +- .../public/common/links/test_utils.ts | 21 + .../public/common/links/types.ts | 15 +- .../alert_context_menu.test.tsx | 6 +- .../use_add_to_case_actions.tsx | 9 +- .../use_bulk_add_to_case_actions.tsx | 13 +- .../take_action_dropdown/index.test.tsx | 3 +- .../security_solution/public/helpers.test.tsx | 37 +- .../components/recent_cases/index.tsx | 5 +- .../components/sidebar/sidebar.test.tsx | 11 +- .../pages/detection_response.test.tsx | 11 +- .../flyout/add_to_case_button/index.tsx | 5 +- .../components/flyout/header/index.test.tsx | 15 +- .../components/flyout/header/index.tsx | 4 +- .../components/flyout/pane/index.test.tsx | 8 + .../side_panel/event_details/index.test.tsx | 6 +- .../components/timeline/index.test.tsx | 8 + .../security_solution/server/features.ts | 111 +++-- .../apis/cases/common/roles.ts | 405 ++++++++++++++++++ .../apis/cases/common/users.ts | 151 +++++++ .../test/api_integration/apis/cases/index.ts | 14 + .../api_integration/apis/cases/privileges.ts | 178 ++++++++ x-pack/test/api_integration/apis/index.ts | 1 + .../apis/security/privileges.ts | 6 +- .../security_solution/cases_privileges.ts | 336 --------------- .../apis/security_solution/index.js | 1 - .../test/functional/services/cases/index.ts | 2 + .../services/cases/single_case_view.ts | 23 + .../apps/cases/common/index.ts | 9 + .../apps/cases/common/roles.ts | 86 ++++ .../apps/cases/common/users.ts | 33 ++ .../apps/cases/deletion.ts | 123 ++++++ .../apps/cases/index.ts | 1 + .../apps/cases/view_case.ts | 6 +- 126 files changed, 2910 insertions(+), 1064 deletions(-) create mode 100644 x-pack/plugins/cases/common/utils/capabilities.ts create mode 100644 x-pack/plugins/cases/public/client/helpers/capabilities.test.ts create mode 100644 x-pack/plugins/cases/public/components/all_cases/header.test.tsx create mode 100644 x-pack/plugins/cases/public/utils/permissions.ts delete mode 100644 x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.test.ts create mode 100644 x-pack/plugins/observability/public/utils/cases_permissions.ts create mode 100644 x-pack/plugins/security_solution/public/cases_test_utils.ts create mode 100644 x-pack/plugins/security_solution/public/common/links/test_utils.ts create mode 100644 x-pack/test/api_integration/apis/cases/common/roles.ts create mode 100644 x-pack/test/api_integration/apis/cases/common/users.ts create mode 100644 x-pack/test/api_integration/apis/cases/index.ts create mode 100644 x-pack/test/api_integration/apis/cases/privileges.ts delete mode 100644 x-pack/test/api_integration/apis/security_solution/cases_privileges.ts create mode 100644 x-pack/test/functional/services/cases/single_case_view.ts create mode 100644 x-pack/test/functional_with_es_ssl/apps/cases/common/index.ts create mode 100644 x-pack/test/functional_with_es_ssl/apps/cases/common/roles.ts create mode 100644 x-pack/test/functional_with_es_ssl/apps/cases/common/users.ts create mode 100644 x-pack/test/functional_with_es_ssl/apps/cases/deletion.ts diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index ba24eeb249155..16f86540a4de2 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -372,6 +372,7 @@ /x-pack/test/cases_api_integration/ @elastic/response-ops /x-pack/test/functional/services/cases/ @elastic/response-ops /x-pack/test/functional_with_es_ssl/apps/cases/ @elastic/response-ops +/x-pack/test/api_integration/apis/cases @elastic/response-ops # Enterprise Search /x-pack/plugins/enterprise_search @elastic/enterprise-search-frontend diff --git a/x-pack/plugins/cases/common/constants.ts b/x-pack/plugins/cases/common/constants.ts index cc2cfb5e873ff..77a5bb8e583da 100644 --- a/x-pack/plugins/cases/common/constants.ts +++ b/x-pack/plugins/cases/common/constants.ts @@ -106,6 +106,7 @@ export const MAX_ALERTS_PER_CASE = 1000 as const; */ export const SECURITY_SOLUTION_OWNER = 'securitySolution' as const; export const OBSERVABILITY_OWNER = 'observability' as const; +export const GENERAL_CASES_OWNER = APP_ID; export const OWNER_INFO = { [SECURITY_SOLUTION_OWNER]: { @@ -116,6 +117,10 @@ export const OWNER_INFO = { label: 'Observability', iconType: 'logoObservability', }, + [GENERAL_CASES_OWNER]: { + label: 'Stack', + iconType: 'casesApp', + }, } as const; /** @@ -150,3 +155,12 @@ export const CASES_TELEMETRY_TASK_NAME = 'cases-telemetry-task'; */ export const CASE_TELEMETRY_SAVED_OBJECT = 'cases-telemetry'; export const CASE_TELEMETRY_SAVED_OBJECT_ID = 'cases-telemetry'; + +/** + * Cases UI Capabilities + */ +export const CREATE_CASES_CAPABILITY = 'create_cases' as const; +export const READ_CASES_CAPABILITY = 'read_cases' as const; +export const UPDATE_CASES_CAPABILITY = 'update_cases' as const; +export const DELETE_CASES_CAPABILITY = 'delete_cases' as const; +export const PUSH_CASES_CAPABILITY = 'push_cases' as const; diff --git a/x-pack/plugins/cases/common/index.ts b/x-pack/plugins/cases/common/index.ts index 79a5aa4eb7ddd..e246c98f71c75 100644 --- a/x-pack/plugins/cases/common/index.ts +++ b/x-pack/plugins/cases/common/index.ts @@ -15,12 +15,27 @@ // For example, constants below could eventually be in a "kbn-cases-constants" instead. // See: https://docs.elastic.dev/kibana-dev-docs/key-concepts/platform-intro#public-plugin-api -export { CASES_URL, SECURITY_SOLUTION_OWNER } from './constants'; +export { + CASES_URL, + SECURITY_SOLUTION_OWNER, + CREATE_CASES_CAPABILITY, + DELETE_CASES_CAPABILITY, + PUSH_CASES_CAPABILITY, + READ_CASES_CAPABILITY, + UPDATE_CASES_CAPABILITY, +} from './constants'; export { CommentType, CaseStatuses, getCasesFromAlertsUrl, throwErrors } from './api'; -export type { Case, Ecs, CasesFeatures, CaseViewRefreshPropInterface } from './ui/types'; +export type { + Case, + Ecs, + CasesFeatures, + CaseViewRefreshPropInterface, + CasesPermissions, +} from './ui/types'; export { StatusAll } from './ui/types'; export { getCreateConnectorUrl, getAllConnectorsUrl } from './utils/connectors_api'; +export { createUICapabilities } from './utils/capabilities'; diff --git a/x-pack/plugins/cases/common/ui/types.ts b/x-pack/plugins/cases/common/ui/types.ts index 65dc8b124c2b1..59ca060bba78e 100644 --- a/x-pack/plugins/cases/common/ui/types.ts +++ b/x-pack/plugins/cases/common/ui/types.ts @@ -6,6 +6,12 @@ */ import type { SavedObjectsResolveResponse } from '@kbn/core/public'; +import { + CREATE_CASES_CAPABILITY, + DELETE_CASES_CAPABILITY, + READ_CASES_CAPABILITY, + UPDATE_CASES_CAPABILITY, +} from '..'; import { CasePatchRequest, CaseStatuses, @@ -24,6 +30,7 @@ import { CommentResponseExternalReferenceType, CommentResponseTypePersistableState, } from '../api'; +import { PUSH_CASES_CAPABILITY } from '../constants'; import { SnakeToCamelCase } from '../types'; type DeepRequired = { [K in keyof T]: DeepRequired } & Required; @@ -229,3 +236,20 @@ export interface Ecs { export type CaseActionConnector = ActionConnector; export type UseFetchAlertData = (alertIds: string[]) => [boolean, Record]; + +export interface CasesPermissions { + all: boolean; + create: boolean; + read: boolean; + update: boolean; + delete: boolean; + push: boolean; +} + +export interface CasesCapabilities { + [CREATE_CASES_CAPABILITY]: boolean; + [READ_CASES_CAPABILITY]: boolean; + [UPDATE_CASES_CAPABILITY]: boolean; + [DELETE_CASES_CAPABILITY]: boolean; + [PUSH_CASES_CAPABILITY]: boolean; +} diff --git a/x-pack/plugins/cases/common/utils/capabilities.ts b/x-pack/plugins/cases/common/utils/capabilities.ts new file mode 100644 index 0000000000000..a508d11201966 --- /dev/null +++ b/x-pack/plugins/cases/common/utils/capabilities.ts @@ -0,0 +1,29 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { + CREATE_CASES_CAPABILITY, + DELETE_CASES_CAPABILITY, + PUSH_CASES_CAPABILITY, + READ_CASES_CAPABILITY, + UPDATE_CASES_CAPABILITY, +} from '../constants'; + +/** + * Return the UI capabilities for each type of operation. These strings must match the values defined in the UI + * here: x-pack/plugins/cases/public/client/helpers/capabilities.ts + */ +export const createUICapabilities = () => ({ + all: [ + CREATE_CASES_CAPABILITY, + READ_CASES_CAPABILITY, + UPDATE_CASES_CAPABILITY, + PUSH_CASES_CAPABILITY, + ] as const, + read: [READ_CASES_CAPABILITY] as const, + delete: [DELETE_CASES_CAPABILITY] as const, +}); diff --git a/x-pack/plugins/cases/common/utils/index.ts b/x-pack/plugins/cases/common/utils/index.ts index 072c2b10dc225..b8be12831200e 100644 --- a/x-pack/plugins/cases/common/utils/index.ts +++ b/x-pack/plugins/cases/common/utils/index.ts @@ -6,3 +6,4 @@ */ export * from './connectors_api'; +export * from './capabilities'; diff --git a/x-pack/plugins/cases/public/client/helpers/can_use_cases.test.ts b/x-pack/plugins/cases/public/client/helpers/can_use_cases.test.ts index ea3b508e3113c..9898f9c374c78 100644 --- a/x-pack/plugins/cases/public/client/helpers/can_use_cases.test.ts +++ b/x-pack/plugins/cases/public/client/helpers/can_use_cases.test.ts @@ -6,124 +6,91 @@ */ import type { ApplicationStart } from '@kbn/core/public'; +import { + allCasesCapabilities, + allCasesPermissions, + noCasesCapabilities, + noCasesPermissions, + readCasesCapabilities, + readCasesPermissions, + writeCasesCapabilities, + writeCasesPermissions, +} from '../../common/mock'; import { canUseCases } from './can_use_cases'; type CasesCapabilities = Pick< ApplicationStart['capabilities'], - 'securitySolutionCases' | 'observabilityCases' + 'securitySolutionCases' | 'observabilityCases' | 'generalCases' >; const hasAll: CasesCapabilities = { - securitySolutionCases: { - crud_cases: true, - read_cases: true, - }, - observabilityCases: { - crud_cases: true, - read_cases: true, - }, + securitySolutionCases: allCasesCapabilities(), + observabilityCases: allCasesCapabilities(), + generalCases: allCasesCapabilities(), }; const hasNone: CasesCapabilities = { - securitySolutionCases: { - crud_cases: false, - read_cases: false, - }, - observabilityCases: { - crud_cases: false, - read_cases: false, - }, + securitySolutionCases: noCasesCapabilities(), + observabilityCases: noCasesCapabilities(), + generalCases: noCasesCapabilities(), }; -const hasSecurity = { - securitySolutionCases: { - crud_cases: true, - read_cases: true, - }, - observabilityCases: { - crud_cases: false, - read_cases: false, - }, +const hasSecurity: CasesCapabilities = { + securitySolutionCases: allCasesCapabilities(), + observabilityCases: noCasesCapabilities(), + generalCases: noCasesCapabilities(), }; -const hasObservability = { - securitySolutionCases: { - crud_cases: false, - read_cases: false, - }, - observabilityCases: { - crud_cases: true, - read_cases: true, - }, +const hasObservability: CasesCapabilities = { + securitySolutionCases: noCasesCapabilities(), + observabilityCases: allCasesCapabilities(), + generalCases: noCasesCapabilities(), }; -const hasObservabilityCrudTrue = { - securitySolutionCases: { - crud_cases: false, - read_cases: false, - }, - observabilityCases: { - crud_cases: true, - read_cases: false, - }, +const hasObservabilityWriteTrue: CasesCapabilities = { + securitySolutionCases: noCasesCapabilities(), + observabilityCases: writeCasesCapabilities(), + generalCases: noCasesCapabilities(), }; -const hasSecurityCrudTrue = { - securitySolutionCases: { - crud_cases: false, - read_cases: false, - }, - observabilityCases: { - crud_cases: true, - read_cases: false, - }, +const hasSecurityWriteTrue: CasesCapabilities = { + securitySolutionCases: writeCasesCapabilities(), + observabilityCases: noCasesCapabilities(), + generalCases: noCasesCapabilities(), }; -const hasObservabilityReadTrue = { - securitySolutionCases: { - crud_cases: false, - read_cases: false, - }, - observabilityCases: { - crud_cases: false, - read_cases: true, - }, +const hasObservabilityReadTrue: CasesCapabilities = { + securitySolutionCases: noCasesCapabilities(), + observabilityCases: readCasesCapabilities(), + generalCases: noCasesCapabilities(), }; -const hasSecurityReadTrue = { - securitySolutionCases: { - crud_cases: false, - read_cases: true, - }, - observabilityCases: { - crud_cases: false, - read_cases: false, - }, +const hasSecurityReadTrue: CasesCapabilities = { + securitySolutionCases: readCasesCapabilities(), + observabilityCases: noCasesCapabilities(), + generalCases: noCasesCapabilities(), }; -const hasSecurityAsCrudAndObservabilityAsRead = { - securitySolutionCases: { - crud_cases: true, - }, - observabilityCases: { - read_cases: true, - }, +const hasSecurityWriteAndObservabilityRead: CasesCapabilities = { + securitySolutionCases: writeCasesCapabilities(), + observabilityCases: readCasesCapabilities(), + generalCases: noCasesCapabilities(), }; describe('canUseCases', () => { - it.each([hasAll, hasSecurity, hasObservability, hasSecurityAsCrudAndObservabilityAsRead])( - 'returns true for both crud and read, if a user has access to both on any solution', + it.each([hasAll, hasSecurity, hasObservability, hasSecurityWriteAndObservabilityRead])( + 'returns true for all permissions, if a user has access to both on any solution', (capability) => { const permissions = canUseCases(capability)(); - expect(permissions).toStrictEqual({ crud: true, read: true }); + expect(permissions).toStrictEqual(allCasesPermissions()); } ); - it.each([hasObservabilityCrudTrue, hasSecurityCrudTrue])( - 'returns true for only crud, if a user has access to only crud on any solution', + it.each([hasObservabilityWriteTrue, hasSecurityWriteTrue])( + 'returns true for only write, if a user has access to only write on any solution', (capability) => { const permissions = canUseCases(capability)(); - expect(permissions).toStrictEqual({ crud: true, read: false }); + expect(permissions).toStrictEqual(writeCasesPermissions()); } ); @@ -131,15 +98,15 @@ describe('canUseCases', () => { 'returns true for only read, if a user has access to only read on any solution', (capability) => { const permissions = canUseCases(capability)(); - expect(permissions).toStrictEqual({ crud: false, read: true }); + expect(permissions).toStrictEqual(readCasesPermissions()); } ); it.each([hasNone, {}])( - 'returns false for both, if a user has access to no solution', + 'returns false for all permissions, if a user has access to no solution', (capability) => { const permissions = canUseCases(capability)(); - expect(permissions).toStrictEqual({ crud: false, read: false }); + expect(permissions).toStrictEqual(noCasesPermissions()); } ); }); diff --git a/x-pack/plugins/cases/public/client/helpers/can_use_cases.ts b/x-pack/plugins/cases/public/client/helpers/can_use_cases.ts index d34e2c9bf5912..13504cb2605cf 100644 --- a/x-pack/plugins/cases/public/client/helpers/can_use_cases.ts +++ b/x-pack/plugins/cases/public/client/helpers/can_use_cases.ts @@ -6,9 +6,19 @@ */ import type { ApplicationStart } from '@kbn/core/public'; -import { OBSERVABILITY_OWNER, SECURITY_SOLUTION_OWNER } from '../../../common/constants'; +import { + FEATURE_ID, + GENERAL_CASES_OWNER, + OBSERVABILITY_OWNER, + SECURITY_SOLUTION_OWNER, +} from '../../../common/constants'; +import { getUICapabilities } from './capabilities'; +import { CasesPermissions } from '../../../common'; -export type CasesOwners = typeof SECURITY_SOLUTION_OWNER | typeof OBSERVABILITY_OWNER; +export type CasesOwners = + | typeof SECURITY_SOLUTION_OWNER + | typeof OBSERVABILITY_OWNER + | typeof GENERAL_CASES_OWNER; /* * Returns an object denoting the current user's ability to read and crud cases. @@ -16,14 +26,44 @@ export type CasesOwners = typeof SECURITY_SOLUTION_OWNER | typeof OBSERVABILITY_ * then crud or read is set to true. * Permissions for a specific owners can be found by passing an owner array */ - export const canUseCases = (capabilities: Partial) => ( - owners: CasesOwners[] = [OBSERVABILITY_OWNER, SECURITY_SOLUTION_OWNER] - ): { crud: boolean; read: boolean } => ({ - crud: - (capabilities && owners.some((owner) => capabilities[`${owner}Cases`]?.crud_cases)) ?? false, - read: - (capabilities && owners.some((owner) => capabilities[`${owner}Cases`]?.read_cases)) ?? false, - }); + owners: CasesOwners[] = [OBSERVABILITY_OWNER, SECURITY_SOLUTION_OWNER, GENERAL_CASES_OWNER] + ): CasesPermissions => { + const aggregatedPermissions = owners.reduce( + (acc, owner) => { + const userCapabilitiesForOwner = getUICapabilities(capabilities[getFeatureID(owner)]); + + acc.create = acc.create || userCapabilitiesForOwner.create; + acc.read = acc.read || userCapabilitiesForOwner.read; + acc.update = acc.update || userCapabilitiesForOwner.update; + acc.delete = acc.delete || userCapabilitiesForOwner.delete; + acc.push = acc.push || userCapabilitiesForOwner.push; + const allFromAcc = acc.create && acc.read && acc.update && acc.delete && acc.push; + acc.all = acc.all || userCapabilitiesForOwner.all || allFromAcc; + + return acc; + }, + { + all: false, + create: false, + read: false, + update: false, + delete: false, + push: false, + } + ); + + return { + ...aggregatedPermissions, + }; + }; + +const getFeatureID = (owner: CasesOwners) => { + if (owner === GENERAL_CASES_OWNER) { + return FEATURE_ID; + } + + return `${owner}Cases`; +}; diff --git a/x-pack/plugins/cases/public/client/helpers/capabilities.test.ts b/x-pack/plugins/cases/public/client/helpers/capabilities.test.ts new file mode 100644 index 0000000000000..58d6d61e80324 --- /dev/null +++ b/x-pack/plugins/cases/public/client/helpers/capabilities.test.ts @@ -0,0 +1,104 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { getUICapabilities } from './capabilities'; + +describe('getUICapabilities', () => { + it('returns false for all fields when the feature cannot be found', () => { + expect(getUICapabilities(undefined)).toMatchInlineSnapshot(` + Object { + "all": false, + "create": false, + "delete": false, + "push": false, + "read": false, + "update": false, + } + `); + }); + + it('returns false for all fields when the capabilities are not passed in', () => { + expect(getUICapabilities()).toMatchInlineSnapshot(` + Object { + "all": false, + "create": false, + "delete": false, + "push": false, + "read": false, + "update": false, + } + `); + }); + + it('returns true for create when it is set to true in the ui capabilities', () => { + expect(getUICapabilities({ create_cases: true })).toMatchInlineSnapshot(` + Object { + "all": false, + "create": true, + "delete": false, + "push": false, + "read": false, + "update": false, + } + `); + }); + + it('returns false for all fields when the ui capabilities are false', () => { + expect( + getUICapabilities({ + create_cases: false, + read_cases: false, + update_cases: false, + delete_cases: false, + push_cases: false, + }) + ).toMatchInlineSnapshot(` + Object { + "all": false, + "create": false, + "delete": false, + "push": false, + "read": false, + "update": false, + } + `); + }); + + it('returns false for all fields when the ui capabilities is an empty object', () => { + expect(getUICapabilities({})).toMatchInlineSnapshot(` + Object { + "all": false, + "create": false, + "delete": false, + "push": false, + "read": false, + "update": false, + } + `); + }); + + it('returns false for the all field when a single field is false', () => { + expect( + getUICapabilities({ + create_cases: false, + read_cases: true, + update_cases: true, + delete_cases: true, + push_cases: true, + }) + ).toMatchInlineSnapshot(` + Object { + "all": false, + "create": false, + "delete": true, + "push": true, + "read": true, + "update": true, + } + `); + }); +}); diff --git a/x-pack/plugins/cases/public/client/helpers/capabilities.ts b/x-pack/plugins/cases/public/client/helpers/capabilities.ts index 652678d0add28..918f0c73c8ebd 100644 --- a/x-pack/plugins/cases/public/client/helpers/capabilities.ts +++ b/x-pack/plugins/cases/public/client/helpers/capabilities.ts @@ -5,19 +5,31 @@ * 2.0. */ -export interface CasesPermissions { - all: boolean; - read: boolean; -} +import { CasesPermissions } from '../../../common'; +import { + CREATE_CASES_CAPABILITY, + DELETE_CASES_CAPABILITY, + PUSH_CASES_CAPABILITY, + READ_CASES_CAPABILITY, + UPDATE_CASES_CAPABILITY, +} from '../../../common/constants'; export const getUICapabilities = ( - featureCapabilities: Partial>> + featureCapabilities?: Partial>> ): CasesPermissions => { - const read = !!featureCapabilities?.read_cases; - const all = !!featureCapabilities?.crud_cases; + const create = !!featureCapabilities?.[CREATE_CASES_CAPABILITY]; + const read = !!featureCapabilities?.[READ_CASES_CAPABILITY]; + const update = !!featureCapabilities?.[UPDATE_CASES_CAPABILITY]; + const deletePriv = !!featureCapabilities?.[DELETE_CASES_CAPABILITY]; + const push = !!featureCapabilities?.[PUSH_CASES_CAPABILITY]; + const all = create && read && update && deletePriv && push; return { all, + create, read, + update, + delete: deletePriv, + push, }; }; diff --git a/x-pack/plugins/cases/public/common/lib/kibana/hooks.test.tsx b/x-pack/plugins/cases/public/common/lib/kibana/hooks.test.tsx index 3fb2ccf2ddc6b..1ec28de4c3d3c 100644 --- a/x-pack/plugins/cases/public/common/lib/kibana/hooks.test.tsx +++ b/x-pack/plugins/cases/public/common/lib/kibana/hooks.test.tsx @@ -9,7 +9,7 @@ import React from 'react'; import { renderHook } from '@testing-library/react-hooks'; import { useApplicationCapabilities } from './hooks'; -import { TestProviders } from '../../mock'; +import { allCasesPermissions, TestProviders } from '../../mock'; describe('hooks', () => { describe('useApplicationCapabilities', () => { @@ -23,7 +23,7 @@ describe('hooks', () => { expect(result.current).toEqual({ actions: { crud: true, read: true }, - generalCases: { all: true, read: true }, + generalCases: allCasesPermissions(), visualize: { crud: true, read: true }, dashboard: { crud: true, read: true }, }); diff --git a/x-pack/plugins/cases/public/common/lib/kibana/hooks.ts b/x-pack/plugins/cases/public/common/lib/kibana/hooks.ts index b144fcf9e24d2..86d137f55dc93 100644 --- a/x-pack/plugins/cases/public/common/lib/kibana/hooks.ts +++ b/x-pack/plugins/cases/public/common/lib/kibana/hooks.ts @@ -12,13 +12,14 @@ import { i18n } from '@kbn/i18n'; import { AuthenticatedUser } from '@kbn/security-plugin/common/model'; import { NavigateToAppOptions } from '@kbn/core/public'; -import { CasesPermissions, getUICapabilities } from '../../../client/helpers/capabilities'; +import { getUICapabilities } from '../../../client/helpers/capabilities'; import { convertToCamelCase } from '../../../api/utils'; import { FEATURE_ID, DEFAULT_DATE_FORMAT, DEFAULT_DATE_FORMAT_TZ, } from '../../../../common/constants'; +import { CasesPermissions } from '../../../../common'; import { StartServices } from '../../../types'; import { useUiSetting, useKibana } from './kibana_react'; @@ -187,7 +188,11 @@ export const useApplicationCapabilities = (): UseApplicationCapabilities => { actions: { crud: !!capabilities.actions?.save, read: !!capabilities.actions?.show }, generalCases: { all: permissions.all, + create: permissions.create, read: permissions.read, + update: permissions.update, + delete: permissions.delete, + push: permissions.push, }, visualize: { crud: !!capabilities.visualize?.save, read: !!capabilities.visualize?.show }, dashboard: { @@ -203,7 +208,11 @@ export const useApplicationCapabilities = (): UseApplicationCapabilities => { capabilities.visualize?.save, capabilities.visualize?.show, permissions.all, + permissions.create, permissions.read, + permissions.update, + permissions.delete, + permissions.push, ] ); }; diff --git a/x-pack/plugins/cases/public/common/lib/kibana/kibana_react.mock.ts b/x-pack/plugins/cases/public/common/lib/kibana/kibana_react.mock.ts index 49b7028a8f883..6e279a7798cf1 100644 --- a/x-pack/plugins/cases/public/common/lib/kibana/kibana_react.mock.ts +++ b/x-pack/plugins/cases/public/common/lib/kibana/kibana_react.mock.ts @@ -53,7 +53,13 @@ export const createStartServicesMock = (): StartServices => { services.application.capabilities = { ...services.application.capabilities, actions: { save: true, show: true }, - generalCases: { crud_cases: true, read_cases: true }, + generalCases: { + create_cases: true, + read_cases: true, + update_cases: true, + delete_cases: true, + push_cases: true, + }, visualize: { save: true, show: true }, dashboard: { show: true, createNew: true }, }; diff --git a/x-pack/plugins/cases/public/common/mock/test_providers.tsx b/x-pack/plugins/cases/public/common/mock/test_providers.tsx index 84bf68f7fa814..46dda67c23f7f 100644 --- a/x-pack/plugins/cases/public/common/mock/test_providers.tsx +++ b/x-pack/plugins/cases/public/common/mock/test_providers.tsx @@ -14,7 +14,7 @@ import { render as reactRender, RenderOptions, RenderResult } from '@testing-lib import { KibanaContextProvider } from '@kbn/kibana-react-plugin/public'; import { QueryClient, QueryClientProvider } from 'react-query'; import { SECURITY_SOLUTION_OWNER } from '../../../common/constants'; -import { CasesFeatures } from '../../../common/ui/types'; +import { CasesCapabilities, CasesFeatures, CasesPermissions } from '../../../common/ui/types'; import { CasesProvider } from '../../components/cases_context'; import { createKibanaContextProviderMock, @@ -23,7 +23,6 @@ import { import { FieldHook } from '../shared_imports'; import { StartServices } from '../../types'; import { ReleasePhase } from '../../components/types'; -import { CasesPermissions } from '../../client/helpers/capabilities'; import { ExternalReferenceAttachmentTypeRegistry } from '../../client/attachment_framework/external_reference_registry'; import { PersistableStateAttachmentTypeRegistry } from '../../client/attachment_framework/persistable_state_registry'; @@ -101,19 +100,66 @@ export const testQueryClient = new QueryClient({ }, }); -export const buildCasesPermissions = (overrides: Partial = {}) => { +export const allCasesPermissions = () => buildCasesPermissions(); +export const noCasesPermissions = () => + buildCasesPermissions({ read: false, create: false, update: false, delete: false, push: false }); +export const readCasesPermissions = () => + buildCasesPermissions({ read: true, create: false, update: false, delete: false, push: false }); +export const noCreateCasesPermissions = () => buildCasesPermissions({ create: false }); +export const noUpdateCasesPermissions = () => buildCasesPermissions({ update: false }); +export const noPushCasesPermissions = () => buildCasesPermissions({ push: false }); +export const noDeleteCasesPermissions = () => buildCasesPermissions({ delete: false }); +export const writeCasesPermissions = () => buildCasesPermissions({ read: false }); + +export const buildCasesPermissions = (overrides: Partial> = {}) => { + const create = overrides.create ?? true; const read = overrides.read ?? true; - const all = overrides.all ?? true; + const update = overrides.update ?? true; + const deletePermissions = overrides.delete ?? true; + const push = overrides.push ?? true; + const all = create && read && update && deletePermissions && push; return { all, + create, read, + update, + delete: deletePermissions, + push, }; }; -export const allCasesPermissions = () => buildCasesPermissions(); -export const noCasesPermissions = () => buildCasesPermissions({ read: false, all: false }); -export const readCasesPermissions = () => buildCasesPermissions({ all: false }); +export const allCasesCapabilities = () => buildCasesCapabilities(); +export const noCasesCapabilities = () => + buildCasesCapabilities({ + create_cases: false, + read_cases: false, + update_cases: false, + delete_cases: false, + push_cases: false, + }); +export const readCasesCapabilities = () => + buildCasesCapabilities({ + create_cases: false, + update_cases: false, + delete_cases: false, + push_cases: false, + }); +export const writeCasesCapabilities = () => { + return buildCasesCapabilities({ + read_cases: false, + }); +}; + +export const buildCasesCapabilities = (overrides?: Partial) => { + return { + create_cases: overrides?.create_cases ?? true, + read_cases: overrides?.read_cases ?? true, + update_cases: overrides?.update_cases ?? true, + delete_cases: overrides?.delete_cases ?? true, + push_cases: overrides?.push_cases ?? true, + }; +}; export const createAppMockRenderer = ({ features, diff --git a/x-pack/plugins/cases/public/components/add_comment/index.test.tsx b/x-pack/plugins/cases/public/components/add_comment/index.test.tsx index 18e02ff098314..8def93fef325d 100644 --- a/x-pack/plugins/cases/public/components/add_comment/index.test.tsx +++ b/x-pack/plugins/cases/public/components/add_comment/index.test.tsx @@ -10,7 +10,7 @@ import { mount } from 'enzyme'; import { waitFor, act } from '@testing-library/react'; import { noop } from 'lodash/fp'; -import { TestProviders } from '../../common/mock'; +import { noCreateCasesPermissions, TestProviders } from '../../common/mock'; import { CommentRequest, CommentType } from '../../../common/api'; import { SECURITY_SOLUTION_OWNER } from '../../../common/constants'; @@ -113,13 +113,13 @@ describe('AddComment ', () => { ).toBeTruthy(); }); - it('should hide the component when the user does not have crud permissions', () => { + it('should hide the component when the user does not have create permissions', () => { useCreateAttachmentsMock.mockImplementation(() => ({ ...defaultResponse, isLoading: true, })); const wrapper = mount( - + ); diff --git a/x-pack/plugins/cases/public/components/add_comment/index.tsx b/x-pack/plugins/cases/public/components/add_comment/index.tsx index 235917a504e2e..98e505b113ecd 100644 --- a/x-pack/plugins/cases/public/components/add_comment/index.tsx +++ b/x-pack/plugins/cases/public/components/add_comment/index.tsx @@ -147,7 +147,7 @@ export const AddComment = React.memo( return ( {isLoading && showLoading && } - {permissions.all && ( + {permissions.create && (
    { }); }); + it('should not render table utility bar when the user does not have permissions to delete', async () => { + const wrapper = mount( + + + + ); + await waitFor(() => { + expect(wrapper.find('[data-test-subj="case-table-selected-case-count"]').exists()).toBe( + false + ); + expect(wrapper.find('[data-test-subj="case-table-bulk-actions"]').exists()).toBe(false); + }); + }); + it('should render metrics when isSelectorView=false', async () => { const wrapper = mount( diff --git a/x-pack/plugins/cases/public/components/all_cases/all_cases_list.tsx b/x-pack/plugins/cases/public/components/all_cases/all_cases_list.tsx index 887a30212833e..7d63813440159 100644 --- a/x-pack/plugins/cases/public/components/all_cases/all_cases_list.tsx +++ b/x-pack/plugins/cases/public/components/all_cases/all_cases_list.tsx @@ -185,7 +185,11 @@ export const AllCasesList = React.memo( [deselectCases, setFilterOptions, refreshCases, setQueryParams] ); - const showActions = permissions.all && !isSelectorView; + /** + * At the time of changing this from all to delete the only bulk action we have is to delete. When we add more + * actions we'll need to revisit this to allow more granular checks around the bulk actions. + */ + const showActions = permissions.delete && !isSelectorView; const columns = useCasesColumns({ filterStatus: filterOptions.status ?? StatusAll, diff --git a/x-pack/plugins/cases/public/components/all_cases/columns.tsx b/x-pack/plugins/cases/public/components/all_cases/columns.tsx index 3476be64c09ff..e4a6927c2e840 100644 --- a/x-pack/plugins/cases/public/components/all_cases/columns.tsx +++ b/x-pack/plugins/cases/public/components/all_cases/columns.tsx @@ -319,7 +319,7 @@ export const useCasesColumns = ({ return ( handleDispatchUpdate({ updateKey: 'status', @@ -372,7 +372,7 @@ export const useCasesColumns = ({ }, ] : []), - ...(permissions.all && !isSelectorView + ...(permissions.delete && !isSelectorView ? [ { name: ( diff --git a/x-pack/plugins/cases/public/components/all_cases/header.test.tsx b/x-pack/plugins/cases/public/components/all_cases/header.test.tsx new file mode 100644 index 0000000000000..64e84affe14d5 --- /dev/null +++ b/x-pack/plugins/cases/public/components/all_cases/header.test.tsx @@ -0,0 +1,56 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; + +import { AppMockRenderer, buildCasesPermissions, createAppMockRenderer } from '../../common/mock'; +import { CasesTableHeader } from './header'; + +describe('CasesTableHeader', () => { + let appMockRender: AppMockRenderer; + + beforeEach(() => { + jest.clearAllMocks(); + appMockRender = createAppMockRenderer(); + }); + + it('displays the create new case button when the user has create privileges', () => { + appMockRender = createAppMockRenderer({ + permissions: buildCasesPermissions({ update: false, create: true }), + }); + const result = appMockRender.render(); + + expect(result.getByTestId('createNewCaseBtn')).toBeInTheDocument(); + }); + + it('does not display the create new case button when the user does not have create privileges', () => { + appMockRender = createAppMockRenderer({ + permissions: buildCasesPermissions({ create: false }), + }); + const result = appMockRender.render(); + + expect(result.queryByTestId('createNewCaseBtn')).not.toBeInTheDocument(); + }); + + it('displays the configure button when the user has update privileges', () => { + appMockRender = createAppMockRenderer({ + permissions: buildCasesPermissions({ create: false, update: true }), + }); + const result = appMockRender.render(); + + expect(result.getByTestId('configure-case-button')).toBeInTheDocument(); + }); + + it('does not display the configure button when the user does not have update privileges', () => { + appMockRender = createAppMockRenderer({ + permissions: buildCasesPermissions({ update: false }), + }); + const result = appMockRender.render(); + + expect(result.queryByTestId('configure-case-button')).not.toBeInTheDocument(); + }); +}); diff --git a/x-pack/plugins/cases/public/components/all_cases/header.tsx b/x-pack/plugins/cases/public/components/all_cases/header.tsx index aeb8a25340811..a40a38a3be581 100644 --- a/x-pack/plugins/cases/public/components/all_cases/header.tsx +++ b/x-pack/plugins/cases/public/components/all_cases/header.tsx @@ -6,12 +6,11 @@ */ import React, { FunctionComponent } from 'react'; -import { EuiFlexGroup, EuiFlexItem } from '@elastic/eui'; +import { EuiFlexGroup } from '@elastic/eui'; import { HeaderPage } from '../header_page'; import * as i18n from './translations'; import { ErrorMessage } from '../use_push_to_service/callout/types'; import { NavButtons } from './nav_buttons'; -import { useCasesContext } from '../cases_context/use_cases_context'; interface OwnProps { actionsErrors: ErrorMessage[]; @@ -20,8 +19,6 @@ interface OwnProps { type Props = OwnProps; export const CasesTableHeader: FunctionComponent = ({ actionsErrors }) => { - const { permissions } = useCasesContext(); - return ( = ({ actionsErrors }) => wrap={true} data-test-subj="all-cases-header" > - {permissions.all ? ( - - - - ) : null} + ); diff --git a/x-pack/plugins/cases/public/components/all_cases/index.test.tsx b/x-pack/plugins/cases/public/components/all_cases/index.test.tsx index fb9d4a62d82da..8e5263a31ff3d 100644 --- a/x-pack/plugins/cases/public/components/all_cases/index.test.tsx +++ b/x-pack/plugins/cases/public/components/all_cases/index.test.tsx @@ -10,7 +10,12 @@ import { mount } from 'enzyme'; import { waitFor } from '@testing-library/react'; import { AllCases } from '.'; -import { TestProviders } from '../../common/mock'; +import { + AppMockRenderer, + createAppMockRenderer, + noCreateCasesPermissions, + TestProviders, +} from '../../common/mock'; import { useGetReporters } from '../../containers/use_get_reporters'; import { useGetActionLicense } from '../../containers/use_get_action_license'; import { casesStatus, connectorsMock, useGetCasesMockState } from '../../containers/mock'; @@ -79,8 +84,39 @@ describe('AllCases', () => { useGetCasesMock.mockReturnValue(defaultGetCases); }); + let appMockRender: AppMockRenderer; + beforeEach(() => { jest.clearAllMocks(); + appMockRender = createAppMockRenderer(); + }); + + describe('empty table', () => { + beforeEach(() => { + useGetCasesMock.mockReturnValue({ + ...defaultGetCases, + data: { + ...defaultGetCases.data, + cases: [], + total: 0, + }, + }); + }); + + it('should render the create new case link when the user has create privileges', async () => { + const result = appMockRender.render(); + await waitFor(() => { + expect(result.getByTestId('cases-table-add-case')).toBeInTheDocument(); + }); + }); + + it('should not render the create new case link when the user does not have create privileges', async () => { + appMockRender = createAppMockRenderer({ permissions: noCreateCasesPermissions() }); + const result = appMockRender.render(); + await waitFor(() => { + expect(result.queryByTestId('cases-table-add-case')).not.toBeInTheDocument(); + }); + }); }); it('should render the stats', async () => { diff --git a/x-pack/plugins/cases/public/components/all_cases/nav_buttons.tsx b/x-pack/plugins/cases/public/components/all_cases/nav_buttons.tsx index 5409cf092d8c9..5217c7022d907 100644 --- a/x-pack/plugins/cases/public/components/all_cases/nav_buttons.tsx +++ b/x-pack/plugins/cases/public/components/all_cases/nav_buttons.tsx @@ -13,6 +13,7 @@ import * as i18n from './translations'; import { ConfigureCaseButton, LinkButton } from '../links'; import { ErrorMessage } from '../use_push_to_service/callout/types'; import { useCreateCaseNavigation } from '../../common/navigation'; +import { useCasesContext } from '../cases_context/use_cases_context'; const ButtonFlexGroup = styled(EuiFlexGroup)` ${({ theme }) => css` @@ -31,6 +32,7 @@ interface OwnProps { type Props = OwnProps; export const NavButtons: FunctionComponent = ({ actionsErrors }) => { + const { permissions } = useCasesContext(); const { getCreateCaseUrl, navigateToCreateCase } = useCreateCaseNavigation(); const navigateToCreateCaseClick = useCallback( (e) => { @@ -39,29 +41,40 @@ export const NavButtons: FunctionComponent = ({ actionsErrors }) => { }, [navigateToCreateCase] ); + + if (!permissions.create && !permissions.update) { + return null; + } + return ( - - - {actionsErrors[0].description} : <>} - titleTooltip={!isEmpty(actionsErrors) ? actionsErrors[0].title : ''} - /> - - - - {i18n.CREATE_CASE_TITLE} - - - + + + {permissions.update && ( + + {actionsErrors[0].description} : <>} + titleTooltip={!isEmpty(actionsErrors) ? actionsErrors[0].title : ''} + /> + + )} + {permissions.create && ( + + + {i18n.CREATE_CASE_TITLE} + + + )} + + ); }; NavButtons.displayName = 'NavButtons'; diff --git a/x-pack/plugins/cases/public/components/all_cases/selector_modal/use_cases_add_to_existing_case_modal.test.tsx b/x-pack/plugins/cases/public/components/all_cases/selector_modal/use_cases_add_to_existing_case_modal.test.tsx index 312235b724b5a..b95b2fba0f14f 100644 --- a/x-pack/plugins/cases/public/components/all_cases/selector_modal/use_cases_add_to_existing_case_modal.test.tsx +++ b/x-pack/plugins/cases/public/components/all_cases/selector_modal/use_cases_add_to_existing_case_modal.test.tsx @@ -11,7 +11,7 @@ import userEvent from '@testing-library/user-event'; import React from 'react'; import AllCasesSelectorModal from '.'; import { Case, CaseStatuses, StatusAll } from '../../../../common'; -import { AppMockRenderer, createAppMockRenderer } from '../../../common/mock'; +import { allCasesPermissions, AppMockRenderer, createAppMockRenderer } from '../../../common/mock'; import { useCasesToast } from '../../../common/use_cases_toast'; import { alertComment } from '../../../containers/mock'; import { useCreateAttachments } from '../../../containers/use_create_attachments'; @@ -64,10 +64,7 @@ describe('use cases add to existing case modal hook', () => { externalReferenceAttachmentTypeRegistry, persistableStateAttachmentTypeRegistry, owner: ['test'], - permissions: { - all: true, - read: true, - }, + permissions: allCasesPermissions(), appId: 'test', appTitle: 'jest', basePath: '/jest', diff --git a/x-pack/plugins/cases/public/components/all_cases/table.tsx b/x-pack/plugins/cases/public/components/all_cases/table.tsx index 86f5ea1ad195c..afe653a50e4db 100644 --- a/x-pack/plugins/cases/public/components/all_cases/table.tsx +++ b/x-pack/plugins/cases/public/components/all_cases/table.tsx @@ -109,11 +109,11 @@ export const CasesTable: FunctionComponent = ({ {i18n.NO_CASES}} titleSize="xs" - body={permissions.all ? i18n.NO_CASES_BODY : i18n.NO_CASES_BODY_READ_ONLY} + body={permissions.create ? i18n.NO_CASES_BODY : i18n.NO_CASES_BODY_READ_ONLY} actions={ - permissions.all && ( + permissions.create && ( ({ AllCases: () =>
    {'All cases'}
    , @@ -85,8 +90,8 @@ describe('Cases routes', () => { expect(screen.getByText('Create case')).toBeInTheDocument(); }); - it('shows the no privileges page if user is read only', () => { - renderWithRouter(['/cases/create'], readCasesPermissions()); + it('shows the no privileges page if the user does not have create privileges', () => { + renderWithRouter(['/cases/create'], noCreateCasesPermissions()); expect(screen.getByText('Privileges required')).toBeInTheDocument(); }); }); @@ -97,8 +102,8 @@ describe('Cases routes', () => { expect(screen.getByText('Configure cases')).toBeInTheDocument(); }); - it('shows the no privileges page if user is read only', () => { - renderWithRouter(['/cases/configure'], readCasesPermissions()); + it('shows the no privileges page if the user does not have update privileges', () => { + renderWithRouter(['/cases/configure'], noUpdateCasesPermissions()); expect(screen.getByText('Privileges required')).toBeInTheDocument(); }); }); diff --git a/x-pack/plugins/cases/public/components/app/routes.tsx b/x-pack/plugins/cases/public/components/app/routes.tsx index fae77ef94fb0e..6e952ce84ba1e 100644 --- a/x-pack/plugins/cases/public/components/app/routes.tsx +++ b/x-pack/plugins/cases/public/components/app/routes.tsx @@ -58,7 +58,7 @@ const CasesRoutesComponent: React.FC = ({ - {permissions.all ? ( + {permissions.create ? ( = ({ - {permissions.all ? ( + {permissions.update ? ( ) : ( diff --git a/x-pack/plugins/cases/public/components/app/use_available_owners.test.ts b/x-pack/plugins/cases/public/components/app/use_available_owners.test.ts index 3475cae722e43..a26647704785f 100644 --- a/x-pack/plugins/cases/public/components/app/use_available_owners.test.ts +++ b/x-pack/plugins/cases/public/components/app/use_available_owners.test.ts @@ -7,8 +7,13 @@ import { renderHook } from '@testing-library/react-hooks'; -import { OBSERVABILITY_OWNER, SECURITY_SOLUTION_OWNER } from '../../../common/constants'; +import { APP_ID, OBSERVABILITY_OWNER, SECURITY_SOLUTION_OWNER } from '../../../common/constants'; import { useKibana } from '../../common/lib/kibana'; +import { + allCasesCapabilities, + noCasesCapabilities, + readCasesCapabilities, +} from '../../common/mock'; import { useAvailableCasesOwners } from './use_available_owners'; jest.mock('../../common/lib/kibana'); @@ -16,30 +21,19 @@ jest.mock('../../common/lib/kibana'); const useKibanaMock = useKibana as jest.MockedFunction; const hasAll = { - securitySolutionCases: { - crud_cases: true, - read_cases: true, - }, - observabilityCases: { - crud_cases: true, - read_cases: true, - }, + securitySolutionCases: allCasesCapabilities(), + observabilityCases: allCasesCapabilities(), + generalCases: allCasesCapabilities(), }; -const hasSecurityAsCrudAndObservabilityAsRead = { - securitySolutionCases: { - crud_cases: true, - }, - observabilityCases: { - read_cases: true, - }, +const secAllObsReadGenNone = { + securitySolutionCases: allCasesCapabilities(), + observabilityCases: readCasesCapabilities(), + generalCases: noCasesCapabilities(), }; const unrelatedFeatures = { - bogusCapability: { - crud_cases: true, - read_cases: true, - }, + bogusCapability: allCasesCapabilities(), }; const mockKibana = (permissionType: unknown = hasAll) => { @@ -57,7 +51,7 @@ describe('useAvailableCasesOwners correctly grabs user case permissions', () => mockKibana(); const { result } = renderHook(useAvailableCasesOwners); - expect(result.current).toEqual([SECURITY_SOLUTION_OWNER, OBSERVABILITY_OWNER]); + expect(result.current).toEqual([SECURITY_SOLUTION_OWNER, OBSERVABILITY_OWNER, APP_ID]); }); it('returns no owner types if user has access to none', () => { @@ -68,17 +62,17 @@ describe('useAvailableCasesOwners correctly grabs user case permissions', () => }); it('returns only the permission it should have with CRUD as default', () => { - mockKibana(hasSecurityAsCrudAndObservabilityAsRead); + mockKibana(secAllObsReadGenNone); const { result } = renderHook(useAvailableCasesOwners); expect(result.current).toEqual([SECURITY_SOLUTION_OWNER]); }); it('returns only the permission it should have with READ as default', () => { - mockKibana(hasSecurityAsCrudAndObservabilityAsRead); - const { result } = renderHook(() => useAvailableCasesOwners('read')); + mockKibana(secAllObsReadGenNone); + const { result } = renderHook(() => useAvailableCasesOwners(['read'])); - expect(result.current).toEqual([OBSERVABILITY_OWNER]); + expect(result.current).toEqual([SECURITY_SOLUTION_OWNER, OBSERVABILITY_OWNER]); }); it('returns no owners when the capabilities does not contain valid entries', () => { diff --git a/x-pack/plugins/cases/public/components/app/use_available_owners.ts b/x-pack/plugins/cases/public/components/app/use_available_owners.ts index 783e856bd36e9..8715af5d6fa68 100644 --- a/x-pack/plugins/cases/public/components/app/use_available_owners.ts +++ b/x-pack/plugins/cases/public/components/app/use_available_owners.ts @@ -5,27 +5,45 @@ * 2.0. */ +import { APP_ID, FEATURE_ID } from '../../../common/constants'; import { useKibana } from '../../common/lib/kibana'; +import { CasesPermissions } from '../../containers/types'; + +type Capability = Omit; /** * - * @param level : 'crud' | 'read' (default: 'crud') - * - * `securitySolution` owner uses cases capability feature id: 'securitySolutionCases'; //owner - * `observability` owner uses cases capability feature id: 'observabilityCases'; - * both solutions use `crud_cases` and `read_cases` capability names + * @param capabilities : specifies the requirements for a valid owner, an owner will be included if it has the specified + * capabilities **/ -export const useAvailableCasesOwners = (level: 'crud' | 'read' = 'crud'): string[] => { - const { capabilities } = useKibana().services.application; - const capabilityName = `${level}_cases`; - return Object.entries(capabilities).reduce( - (availableOwners: string[], [featureId, capability]) => { - if (featureId.endsWith('Cases') && !!capability[capabilityName]) { - availableOwners.push(featureId.replace('Cases', '')); +export const useAvailableCasesOwners = ( + capabilities: Capability[] = ['create', 'read', 'update', 'delete', 'push'] +): string[] => { + const { capabilities: kibanaCapabilities } = useKibana().services.application; + + return Object.entries(kibanaCapabilities).reduce( + (availableOwners: string[], [featureId, kibananCapability]) => { + if (!featureId.endsWith('Cases')) { + return availableOwners; + } + for (const cap of capabilities) { + const hasCapability = !!kibananCapability[`${cap}_cases`]; + if (!hasCapability) { + return availableOwners; + } } + availableOwners.push(getOwnerFromFeatureID(featureId)); return availableOwners; }, [] ); }; + +const getOwnerFromFeatureID = (featureID: string) => { + if (featureID === FEATURE_ID) { + return APP_ID; + } + + return featureID.replace('Cases', ''); +}; diff --git a/x-pack/plugins/cases/public/components/app/use_readonly_header.ts b/x-pack/plugins/cases/public/components/app/use_readonly_header.ts index 08aa05ab98ffe..40c4d25468d15 100644 --- a/x-pack/plugins/cases/public/components/app/use_readonly_header.ts +++ b/x-pack/plugins/cases/public/components/app/use_readonly_header.ts @@ -10,6 +10,7 @@ import { useCallback, useEffect } from 'react'; import * as i18n from './translations'; import { useKibana } from '../../common/lib/kibana'; import { useCasesContext } from '../cases_context/use_cases_context'; +import { isReadOnlyPermissions } from '../../utils/permissions'; /** * This component places a read-only icon badge in the header if user only has read permissions @@ -20,7 +21,7 @@ export function useReadonlyHeader() { // if the user is read only then display the glasses badge in the global navigation header const setBadge = useCallback(() => { - if (!permissions.all && permissions.read) { + if (isReadOnlyPermissions(permissions)) { chrome.setBadge({ text: i18n.READ_ONLY_BADGE_TEXT, tooltip: i18n.READ_ONLY_BADGE_TOOLTIP, diff --git a/x-pack/plugins/cases/public/components/case_action_bar/actions.test.tsx b/x-pack/plugins/cases/public/components/case_action_bar/actions.test.tsx index 308f6bc86f41a..8735b94d71b2c 100644 --- a/x-pack/plugins/cases/public/components/case_action_bar/actions.test.tsx +++ b/x-pack/plugins/cases/public/components/case_action_bar/actions.test.tsx @@ -9,7 +9,7 @@ import React from 'react'; import { mount } from 'enzyme'; import { useDeleteCases } from '../../containers/use_delete_cases'; -import { TestProviders } from '../../common/mock'; +import { noDeleteCasesPermissions, TestProviders } from '../../common/mock'; import { basicCase, basicPush } from '../../containers/mock'; import { Actions } from './actions'; import * as i18n from '../case_view/translations'; @@ -67,6 +67,17 @@ describe('CaseView actions', () => { expect(handleToggleModal).toHaveBeenCalled(); }); + it('does not show trash icon when user does not have deletion privileges', () => { + const wrapper = mount( + + + + ); + + expect(wrapper.find('[data-test-subj="confirm-delete-case-modal"]').exists()).toBeFalsy(); + expect(wrapper.find('button[data-test-subj="property-actions-ellipses"]').exists()).toBeFalsy(); + }); + it('toggle delete modal and confirm', () => { useDeleteCasesMock.mockImplementation(() => ({ ...defaultDeleteState, diff --git a/x-pack/plugins/cases/public/components/case_action_bar/actions.tsx b/x-pack/plugins/cases/public/components/case_action_bar/actions.tsx index 3c78fa6f5fa4b..975cf89fc1031 100644 --- a/x-pack/plugins/cases/public/components/case_action_bar/actions.tsx +++ b/x-pack/plugins/cases/public/components/case_action_bar/actions.tsx @@ -7,6 +7,7 @@ import { isEmpty } from 'lodash/fp'; import React, { useMemo } from 'react'; +import { EuiFlexItem } from '@elastic/eui'; import * as i18n from '../case_view/translations'; import { useDeleteCases } from '../../containers/use_delete_cases'; import { ConfirmDeleteCaseModal } from '../confirm_delete_case'; @@ -14,6 +15,7 @@ import { PropertyActions } from '../property_actions'; import { Case } from '../../../common/ui/types'; import { CaseService } from '../../containers/use_get_case_user_actions'; import { useAllCasesNavigation } from '../../common/navigation'; +import { useCasesContext } from '../cases_context/use_cases_context'; interface CaseViewActions { caseData: Case; @@ -25,14 +27,19 @@ const ActionsComponent: React.FC = ({ caseData, currentExternal const { handleToggleModal, handleOnDeleteConfirm, isDeleted, isDisplayConfirmDeleteModal } = useDeleteCases(); const { navigateToAllCases } = useAllCasesNavigation(); + const { permissions } = useCasesContext(); const propertyActions = useMemo( () => [ - { - iconType: 'trash', - label: i18n.DELETE_CASE(), - onClick: handleToggleModal, - }, + ...(permissions.delete + ? [ + { + iconType: 'trash', + label: i18n.DELETE_CASE(), + onClick: handleToggleModal, + }, + ] + : []), ...(currentExternalIncident != null && !isEmpty(currentExternalIncident?.externalUrl) ? [ { @@ -43,15 +50,20 @@ const ActionsComponent: React.FC = ({ caseData, currentExternal ] : []), ], - [handleToggleModal, currentExternalIncident] + [handleToggleModal, currentExternalIncident, permissions.delete] ); if (isDeleted) { navigateToAllCases(); return null; } + + if (propertyActions.length === 0) { + return null; + } + return ( - <> + = ({ caseData, currentExternal onCancel={handleToggleModal} onConfirm={handleOnDeleteConfirm.bind(null, [{ id: caseData.id, title: caseData.title }])} /> - + ); }; ActionsComponent.displayName = 'Actions'; diff --git a/x-pack/plugins/cases/public/components/case_action_bar/index.test.tsx b/x-pack/plugins/cases/public/components/case_action_bar/index.test.tsx index f9c92c8222ccf..1802a063ca932 100644 --- a/x-pack/plugins/cases/public/components/case_action_bar/index.test.tsx +++ b/x-pack/plugins/cases/public/components/case_action_bar/index.test.tsx @@ -7,11 +7,17 @@ import React from 'react'; import { mount } from 'enzyme'; -import { render } from '@testing-library/react'; +import { render, screen } from '@testing-library/react'; +import userEvent from '@testing-library/user-event'; import { basicCase, caseUserActions, getAlertUserAction } from '../../containers/mock'; import { CaseActionBar, CaseActionBarProps } from '.'; -import { TestProviders } from '../../common/mock'; +import { + allCasesPermissions, + noDeleteCasesPermissions, + noUpdateCasesPermissions, + TestProviders, +} from '../../common/mock'; import { useGetCaseUserActions } from '../../containers/use_get_case_user_actions'; import { useRefreshCaseViewPage } from '../case_view/use_on_refresh_case_view_page'; @@ -188,4 +194,56 @@ describe('CaseActionBar', () => { expect(getByText('Case opened')).toBeInTheDocument(); }); + + it('should show the change status text when the user has update privileges', () => { + render( + + + + ); + + expect(screen.getByTitle('Change status')).toBeInTheDocument(); + }); + + it('should not show the change status text when the user does not have update privileges', () => { + render( + + + + ); + + expect(screen.queryByTitle('Change status')).not.toBeInTheDocument(); + }); + + it('should not show the sync alerts toggle when the user does not have update privileges', () => { + const { queryByText } = render( + + + + ); + + expect(queryByText('Sync alerts')).not.toBeInTheDocument(); + }); + + it('should not show the delete item in the menu when the user does not have delete privileges', () => { + const { queryByText, queryByTestId } = render( + + + + ); + + expect(queryByTestId('property-actions-ellipses')).not.toBeInTheDocument(); + expect(queryByText('Delete case')).not.toBeInTheDocument(); + }); + + it('should show the the delete item in the menu when the user does have delete privileges', () => { + const { queryByText } = render( + + + + ); + + userEvent.click(screen.getByTestId('property-actions-ellipses')); + expect(queryByText('Delete case')).toBeInTheDocument(); + }); }); diff --git a/x-pack/plugins/cases/public/components/case_action_bar/index.tsx b/x-pack/plugins/cases/public/components/case_action_bar/index.tsx index dbffb0c338248..36d0a0152171f 100644 --- a/x-pack/plugins/cases/public/components/case_action_bar/index.tsx +++ b/x-pack/plugins/cases/public/components/case_action_bar/index.tsx @@ -107,7 +107,7 @@ const CaseActionBarComponent: React.FC = ({ @@ -134,7 +134,7 @@ const CaseActionBarComponent: React.FC = ({ responsive={false} justifyContent="spaceBetween" > - {permissions.all && isSyncAlertsEnabled && ( + {permissions.update && isSyncAlertsEnabled && ( = ({ - {permissions.all && ( - - - - )} + diff --git a/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.test.tsx b/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.test.tsx index f934cc88dc404..8a3a457bcfd00 100644 --- a/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.test.tsx +++ b/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.test.tsx @@ -13,7 +13,11 @@ import { getAlertUserAction, } from '../../../containers/mock'; import React from 'react'; -import { AppMockRenderer, createAppMockRenderer } from '../../../common/mock'; +import { + AppMockRenderer, + createAppMockRenderer, + noUpdateCasesPermissions, +} from '../../../common/mock'; import { CaseViewActivity } from './case_view_activity'; import { ConnectorTypes } from '../../../../common/api/connectors'; import { Case } from '../../../../common'; @@ -110,6 +114,30 @@ describe('Case View Page activity tab', () => { expect(useGetCaseUserActionsMock).toHaveBeenCalledWith(caseData.id, caseData.connector.id); }); + it('should not render the case view status button when the user does not have update permissions', () => { + appMockRender = createAppMockRenderer({ permissions: noUpdateCasesPermissions() }); + + const result = appMockRender.render(); + expect(result.getByTestId('case-view-activity')).toBeTruthy(); + expect(result.getByTestId('user-actions')).toBeTruthy(); + expect(result.getByTestId('case-tags')).toBeTruthy(); + expect(result.getByTestId('connector-edit-header')).toBeTruthy(); + expect(result.queryByTestId('case-view-status-action-button')).not.toBeInTheDocument(); + expect(useGetCaseUserActionsMock).toHaveBeenCalledWith(caseData.id, caseData.connector.id); + }); + + it('should disable the severity selector when the user does not have update permissions', () => { + appMockRender = createAppMockRenderer({ permissions: noUpdateCasesPermissions() }); + + const result = appMockRender.render(); + expect(result.getByTestId('case-view-activity')).toBeTruthy(); + expect(result.getByTestId('user-actions')).toBeTruthy(); + expect(result.getByTestId('case-tags')).toBeTruthy(); + expect(result.getByTestId('connector-edit-header')).toBeTruthy(); + expect(result.getByTestId('case-severity-selection')).toBeDisabled(); + expect(useGetCaseUserActionsMock).toHaveBeenCalledWith(caseData.id, caseData.connector.id); + }); + it('should show a loading when is fetching data is true and hide the user actions activity', () => { useGetCaseUserActionsMock.mockReturnValue({ ...defaultUseGetCaseUserActions, diff --git a/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.tsx b/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.tsx index ccf0bd9b475b3..82ce1be7dc84b 100644 --- a/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.tsx +++ b/x-pack/plugins/cases/public/components/case_view/components/case_view_activity.tsx @@ -133,7 +133,7 @@ export const CaseViewActivity = ({ onShowAlertDetails={onShowAlertDetails} onUpdateField={onUpdateField} statusActionButton={ - permissions.all ? ( + permissions.update ? ( { expect(wrapper.find('[data-test-subj="edit-connector-flyout"]').exists()).toBe(false); }); - test('it disables correctly when the user cannot crud', () => { + test('it disables correctly when the user cannot update', () => { const newWrapper = mount(, { wrappingComponent: TestProviders, - wrappingComponentProps: { permissions: noCasesPermissions() }, + wrappingComponentProps: { permissions: noUpdateCasesPermissions() }, }); expect(newWrapper.find('button[data-test-subj="dropdown-connectors"]').prop('disabled')).toBe( diff --git a/x-pack/plugins/cases/public/components/configure_cases/index.tsx b/x-pack/plugins/cases/public/components/configure_cases/index.tsx index bf75dd5a828cd..fbfadb6b1a7cd 100644 --- a/x-pack/plugins/cases/public/components/configure_cases/index.tsx +++ b/x-pack/plugins/cases/public/components/configure_cases/index.tsx @@ -225,7 +225,7 @@ export const ConfigureCases: React.FC = React.memo(() => { @@ -233,13 +233,13 @@ export const ConfigureCases: React.FC = React.memo(() => { {ConnectorAddFlyout} diff --git a/x-pack/plugins/cases/public/components/edit_connector/index.test.tsx b/x-pack/plugins/cases/public/components/edit_connector/index.test.tsx index ee8c34faff078..9205dd357c762 100644 --- a/x-pack/plugins/cases/public/components/edit_connector/index.test.tsx +++ b/x-pack/plugins/cases/public/components/edit_connector/index.test.tsx @@ -15,6 +15,7 @@ import { AppMockRenderer, createAppMockRenderer, readCasesPermissions, + noPushCasesPermissions, TestProviders, } from '../../common/mock'; import { basicCase, basicPush, caseUserActions, connectorsMock } from '../../containers/mock'; @@ -362,6 +363,16 @@ describe('EditConnector ', () => { }); }); + it('does not show the push button if the user does not have push permissions', async () => { + const defaultProps = getDefaultProps(); + + appMockRender = createAppMockRenderer({ permissions: noPushCasesPermissions() }); + const result = appMockRender.render(); + await waitFor(() => { + expect(result.queryByTestId('has-data-to-push-button')).toBe(null); + }); + }); + it('does not show the edit connectors pencil if the user does not have read access to actions', async () => { const defaultProps = getDefaultProps(); const props = { ...defaultProps, connectors: [] }; @@ -376,4 +387,16 @@ describe('EditConnector ', () => { expect(result.queryByTestId('connector-edit')).toBe(null); }); }); + + it('does not show the edit connectors pencil if the user does not have push permissions', async () => { + const defaultProps = getDefaultProps(); + const props = { ...defaultProps, connectors: [] }; + appMockRender = createAppMockRenderer({ permissions: noPushCasesPermissions() }); + + const result = appMockRender.render(); + await waitFor(() => { + expect(result.getByTestId('connector-edit-header')).toBeInTheDocument(); + expect(result.queryByTestId('connector-edit')).toBe(null); + }); + }); }); diff --git a/x-pack/plugins/cases/public/components/edit_connector/index.tsx b/x-pack/plugins/cases/public/components/edit_connector/index.tsx index 0c691460ba007..cbfea7913dec7 100644 --- a/x-pack/plugins/cases/public/components/edit_connector/index.tsx +++ b/x-pack/plugins/cases/public/components/edit_connector/index.tsx @@ -288,7 +288,7 @@ export const EditConnector = React.memo(

    {i18n.CONNECTORS}

    {isLoading && } - {!isLoading && !editConnector && permissions.all && actionsReadCapabilities && ( + {!isLoading && !editConnector && permissions.push && actionsReadCapabilities && ( {pushButton} diff --git a/x-pack/plugins/cases/public/components/header_page/__snapshots__/editable_title.test.tsx.snap b/x-pack/plugins/cases/public/components/header_page/__snapshots__/editable_title.test.tsx.snap index 832b5477d17f7..bc4dba5843e62 100644 --- a/x-pack/plugins/cases/public/components/header_page/__snapshots__/editable_title.test.tsx.snap +++ b/x-pack/plugins/cases/public/components/header_page/__snapshots__/editable_title.test.tsx.snap @@ -44,7 +44,11 @@ exports[`EditableTitle renders 1`] = ` ], "permissions": Object { "all": true, + "create": true, + "delete": true, + "push": true, "read": true, + "update": true, }, "persistableStateAttachmentTypeRegistry": PersistableStateAttachmentTypeRegistry { "collection": Map {}, diff --git a/x-pack/plugins/cases/public/components/header_page/__snapshots__/index.test.tsx.snap b/x-pack/plugins/cases/public/components/header_page/__snapshots__/index.test.tsx.snap index cfb75e0c286f2..083975a40330e 100644 --- a/x-pack/plugins/cases/public/components/header_page/__snapshots__/index.test.tsx.snap +++ b/x-pack/plugins/cases/public/components/header_page/__snapshots__/index.test.tsx.snap @@ -44,7 +44,11 @@ exports[`HeaderPage it renders 1`] = ` ], "permissions": Object { "all": true, + "create": true, + "delete": true, + "push": true, "read": true, + "update": true, }, "persistableStateAttachmentTypeRegistry": PersistableStateAttachmentTypeRegistry { "collection": Map {}, diff --git a/x-pack/plugins/cases/public/components/header_page/editable_title.tsx b/x-pack/plugins/cases/public/components/header_page/editable_title.tsx index c92e1122c53e8..7e0dd2f5fd1fc 100644 --- a/x-pack/plugins/cases/public/components/header_page/editable_title.tsx +++ b/x-pack/plugins/cases/public/components/header_page/editable_title.tsx @@ -118,7 +118,7 @@ const EditableTitleComponent: React.FC = ({ onSubmit, isLoad ) : ( {isLoading && <MySpinner data-test-subj="editable-title-loading" />} - {!isLoading && permissions.all && ( + {!isLoading && permissions.update && ( <MyEuiButtonIcon aria-label={i18n.EDIT_TITLE_ARIA(title as string)} iconType="pencil" diff --git a/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.test.tsx b/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.test.tsx index eb968834d765e..c53c096aaa821 100644 --- a/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.test.tsx +++ b/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.test.tsx @@ -25,7 +25,7 @@ describe('NoCases', () => { ); }); - it('displays a message without a link to create a case when the user does not have write permissions', () => { + it('displays a message without a link to create a case when the user does not have create permissions', () => { const wrapper = mount( <TestProviders permissions={readCasesPermissions()}> <NoCases /> diff --git a/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.tsx b/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.tsx index d39dfdbb2c50b..b9c842dba279f 100644 --- a/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.tsx +++ b/x-pack/plugins/cases/public/components/recent_cases/no_cases/index.tsx @@ -24,7 +24,7 @@ const NoCasesComponent = () => { [navigateToCreateCase] ); - return permissions.all ? ( + return permissions.create ? ( <> <span>{i18n.NO_CASES}</span> <LinkAnchor diff --git a/x-pack/plugins/cases/public/components/tag_list/index.test.tsx b/x-pack/plugins/cases/public/components/tag_list/index.test.tsx index 46633503dd734..cbe17b0d8b8e3 100644 --- a/x-pack/plugins/cases/public/components/tag_list/index.test.tsx +++ b/x-pack/plugins/cases/public/components/tag_list/index.test.tsx @@ -107,7 +107,7 @@ describe('TagList ', () => { expect(wrapper.find(`[data-test-subj="tag-pepsi"]`).last().exists()).toBeTruthy(); }); - it('does not render when the user does not have write permissions', () => { + it('does not render when the user does not have update permissions', () => { const wrapper = mount( <TestProviders permissions={readCasesPermissions()}> <TagList {...defaultProps} /> diff --git a/x-pack/plugins/cases/public/components/tag_list/index.tsx b/x-pack/plugins/cases/public/components/tag_list/index.tsx index 74fb2efcb4fad..c85f989f88281 100644 --- a/x-pack/plugins/cases/public/components/tag_list/index.tsx +++ b/x-pack/plugins/cases/public/components/tag_list/index.tsx @@ -104,7 +104,7 @@ export const TagList = React.memo(({ isLoading, onSubmit, tags }: TagListProps) <h4>{i18n.TAGS}</h4> </EuiFlexItem> {isLoading && <EuiLoadingSpinner data-test-subj="tag-list-loading" />} - {!isLoading && permissions.all && ( + {!isLoading && permissions.update && ( <EuiFlexItem data-test-subj="tag-list-edit" grow={false}> <EuiButtonIcon data-test-subj="tag-list-edit-button" diff --git a/x-pack/plugins/cases/public/components/use_push_to_service/index.test.tsx b/x-pack/plugins/cases/public/components/use_push_to_service/index.test.tsx index c00ebc7b48045..f56a55fdeb7b1 100644 --- a/x-pack/plugins/cases/public/components/use_push_to_service/index.test.tsx +++ b/x-pack/plugins/cases/public/components/use_push_to_service/index.test.tsx @@ -11,7 +11,7 @@ import { render, screen } from '@testing-library/react'; import '../../common/mock/match_media'; import { usePushToService, ReturnUsePushToService, UsePushToService } from '.'; -import { readCasesPermissions, TestProviders } from '../../common/mock'; +import { noPushCasesPermissions, readCasesPermissions, TestProviders } from '../../common/mock'; import { CaseStatuses, ConnectorTypes } from '../../../common/api'; import { usePostPushToService } from '../../containers/use_post_push_to_service'; import { basicPush, actionLicenses, connectorsMock } from '../../containers/mock'; @@ -280,6 +280,24 @@ describe('usePushToService', () => { }); describe('user does not have write permissions', () => { + it('disables the push button when the user does not have push permissions', async () => { + await act(async () => { + const { result, waitForNextUpdate } = renderHook<UsePushToService, ReturnUsePushToService>( + () => usePushToService(defaultArgs), + { + wrapper: ({ children }) => ( + <TestProviders permissions={noPushCasesPermissions()}> {children}</TestProviders> + ), + } + ); + await waitForNextUpdate(); + + const { getByTestId } = render(result.current.pushButton); + + expect(getByTestId('push-to-external-service')).toBeDisabled(); + }); + }); + it('does not display a message when user does not have a premium license', async () => { useFetchActionLicenseMock.mockImplementation(() => ({ isLoading: false, diff --git a/x-pack/plugins/cases/public/components/use_push_to_service/index.tsx b/x-pack/plugins/cases/public/components/use_push_to_service/index.tsx index 253170fdd955c..a9e8f7c176b74 100644 --- a/x-pack/plugins/cases/public/components/use_push_to_service/index.tsx +++ b/x-pack/plugins/cases/public/components/use_push_to_service/index.tsx @@ -76,7 +76,7 @@ export const usePushToService = ({ // these message require that the user do some sort of write action as a result of the message, readonly users won't // be able to perform such an action so let's not display the error to the user in that situation - if (!permissions.all) { + if (!permissions.update) { return errors; } @@ -114,7 +114,7 @@ export const usePushToService = ({ return errors; // eslint-disable-next-line react-hooks/exhaustive-deps - }, [actionLicense, caseStatus, connectors.length, connector, loadingLicense, permissions.all]); + }, [actionLicense, caseStatus, connectors.length, connector, loadingLicense, permissions.update]); const pushToServiceButton = useMemo( () => ( @@ -126,7 +126,7 @@ export const usePushToService = ({ isLoading || loadingLicense || errorsMsg.length > 0 || - !permissions.all || + !permissions.push || !isValidConnector || !hasDataToPush } @@ -146,13 +146,13 @@ export const usePushToService = ({ hasDataToPush, isLoading, loadingLicense, - permissions.all, + permissions.push, isValidConnector, ] ); const objToReturn = useMemo(() => { - const hidePushButton = errorsMsg.length > 0 || !hasDataToPush || !permissions.all; + const hidePushButton = errorsMsg.length > 0 || !hasDataToPush || !permissions.push; return { pushButton: hidePushButton ? ( @@ -184,7 +184,7 @@ export const usePushToService = ({ hasLicenseError, onEditClick, pushToServiceButton, - permissions.all, + permissions.push, ]); return objToReturn; diff --git a/x-pack/plugins/cases/public/components/user_actions/index.tsx b/x-pack/plugins/cases/public/components/user_actions/index.tsx index 7224eee213719..4b53499c9e5ec 100644 --- a/x-pack/plugins/cases/public/components/user_actions/index.tsx +++ b/x-pack/plugins/cases/public/components/user_actions/index.tsx @@ -233,7 +233,7 @@ export const UserActions = React.memo( const { permissions } = useCasesContext(); - const bottomActions = permissions.all + const bottomActions = permissions.create ? [ { username: ( diff --git a/x-pack/plugins/cases/public/components/user_actions/property_actions.test.tsx b/x-pack/plugins/cases/public/components/user_actions/property_actions.test.tsx index e9319169b953c..88df48c1fac78 100644 --- a/x-pack/plugins/cases/public/components/user_actions/property_actions.test.tsx +++ b/x-pack/plugins/cases/public/components/user_actions/property_actions.test.tsx @@ -6,11 +6,15 @@ */ import React from 'react'; -import { mount, ReactWrapper } from 'enzyme'; -import { UserActionPropertyActions } from './property_actions'; -import { render } from '@testing-library/react'; +import { UserActionPropertyActions, UserActionPropertyActionsProps } from './property_actions'; +import { render, screen } from '@testing-library/react'; import userEvent from '@testing-library/user-event'; -import { TestProviders } from '../../common/mock'; +import { + noCreateCasesPermissions, + noDeleteCasesPermissions, + noUpdateCasesPermissions, + TestProviders, +} from '../../common/mock'; jest.mock('../../common/lib/kibana'); @@ -28,67 +32,123 @@ const props = { }; describe('UserActionPropertyActions ', () => { - let wrapper: ReactWrapper; - - beforeAll(() => { - wrapper = mount( - <TestProviders> - <UserActionPropertyActions {...props} /> - </TestProviders> - ); - }); - beforeEach(() => { jest.clearAllMocks(); }); it('renders', async () => { - expect( - wrapper.find('[data-test-subj="user-action-title-loading"]').first().exists() - ).toBeFalsy(); + render( + <TestProviders> + <UserActionPropertyActions {...props} /> + </TestProviders> + ); - expect(wrapper.find('[data-test-subj="property-actions"]').first().exists()).toBeTruthy(); + expect(screen.queryByTestId('user-action-title-loading')).not.toBeInTheDocument(); + expect(screen.getByTestId('property-actions')).toBeInTheDocument(); }); it('shows the edit and quote buttons', async () => { - wrapper.find('[data-test-subj="property-actions-ellipses"]').first().simulate('click'); - wrapper.find('[data-test-subj="property-actions-pencil"]').exists(); - wrapper.find('[data-test-subj="property-actions-quote"]').exists(); + const renderResult = render( + <TestProviders> + <UserActionPropertyActions {...props} /> + </TestProviders> + ); + + userEvent.click(renderResult.getByTestId('property-actions-ellipses')); + expect(screen.getByTestId('property-actions-pencil')).toBeInTheDocument(); + expect(screen.getByTestId('property-actions-quote')).toBeInTheDocument(); }); it('quote click calls onQuote', async () => { - wrapper.find('[data-test-subj="property-actions-ellipses"]').first().simulate('click'); - wrapper.find('[data-test-subj="property-actions-quote"]').first().simulate('click'); + const renderResult = render( + <TestProviders> + <UserActionPropertyActions {...props} /> + </TestProviders> + ); + + userEvent.click(renderResult.getByTestId('property-actions-ellipses')); + userEvent.click(renderResult.getByTestId('property-actions-quote')); + expect(onQuote).toHaveBeenCalledWith(props.id); }); it('pencil click calls onEdit', async () => { - wrapper.find('[data-test-subj="property-actions-ellipses"]').first().simulate('click'); - wrapper.find('[data-test-subj="property-actions-pencil"]').first().simulate('click'); + const renderResult = render( + <TestProviders> + <UserActionPropertyActions {...props} /> + </TestProviders> + ); + + userEvent.click(renderResult.getByTestId('property-actions-ellipses')); + userEvent.click(renderResult.getByTestId('property-actions-pencil')); expect(onEdit).toHaveBeenCalledWith(props.id); }); it('shows the spinner when loading', async () => { - wrapper = mount( + render( <TestProviders> <UserActionPropertyActions {...props} isLoading={true} /> </TestProviders> ); - expect( - wrapper.find('[data-test-subj="user-action-title-loading"]').first().exists() - ).toBeTruthy(); - - expect(wrapper.find('[data-test-subj="property-actions"]').first().exists()).toBeFalsy(); + expect(screen.getByTestId('user-action-title-loading')).toBeInTheDocument(); + expect(screen.queryByTestId('property-actions')).not.toBeInTheDocument(); }); - describe('Delete button', () => { - const onDelete = jest.fn(); - const deleteProps = { - ...props, - onDelete, - deleteLabel: 'delete me', - deleteConfirmlabel: 'confirm delete me', - }; + describe('deletion props', () => { + let onDelete: jest.Mock; + let deleteProps: UserActionPropertyActionsProps; + + beforeEach(() => { + jest.clearAllMocks(); + + onDelete = jest.fn(); + deleteProps = { + ...props, + onDelete, + deleteLabel: 'delete me', + deleteConfirmTitle: 'confirm delete me', + }; + }); + + it('does not show the delete icon when the user does not have delete permissions', () => { + const renderResult = render( + <TestProviders permissions={noDeleteCasesPermissions()}> + <UserActionPropertyActions {...deleteProps} /> + </TestProviders> + ); + + userEvent.click(renderResult.getByTestId('property-actions-ellipses')); + expect(renderResult.queryByTestId('property-actions-trash')).not.toBeInTheDocument(); + expect(renderResult.queryByTestId('property-actions-pencil')).toBeInTheDocument(); + expect(renderResult.queryByTestId('property-actions-quote')).toBeInTheDocument(); + }); + + it('does not show the pencil icon when the user does not have update permissions', () => { + const renderResult = render( + <TestProviders permissions={noUpdateCasesPermissions()}> + <UserActionPropertyActions {...deleteProps} /> + </TestProviders> + ); + + userEvent.click(renderResult.getByTestId('property-actions-ellipses')); + expect(renderResult.queryByTestId('property-actions-trash')).toBeInTheDocument(); + expect(renderResult.queryByTestId('property-actions-pencil')).not.toBeInTheDocument(); + expect(renderResult.queryByTestId('property-actions-quote')).toBeInTheDocument(); + }); + + it('does not show the quote icon when the user does not have create permissions', () => { + const renderResult = render( + <TestProviders permissions={noCreateCasesPermissions()}> + <UserActionPropertyActions {...deleteProps} /> + </TestProviders> + ); + + userEvent.click(renderResult.getByTestId('property-actions-ellipses')); + expect(renderResult.queryByTestId('property-actions-trash')).toBeInTheDocument(); + expect(renderResult.queryByTestId('property-actions-pencil')).toBeInTheDocument(); + expect(renderResult.queryByTestId('property-actions-quote')).not.toBeInTheDocument(); + }); + it('shows the delete button', () => { const renderResult = render( <TestProviders> diff --git a/x-pack/plugins/cases/public/components/user_actions/property_actions.tsx b/x-pack/plugins/cases/public/components/user_actions/property_actions.tsx index 502e69a9d1903..13273346241e5 100644 --- a/x-pack/plugins/cases/public/components/user_actions/property_actions.tsx +++ b/x-pack/plugins/cases/public/components/user_actions/property_actions.tsx @@ -13,7 +13,7 @@ import { useLensOpenVisualization } from '../markdown_editor/plugins/lens/use_le import { CANCEL_BUTTON, CONFIRM_BUTTON } from './translations'; import { useCasesContext } from '../cases_context/use_cases_context'; -interface UserActionPropertyActionsProps { +export interface UserActionPropertyActionsProps { id: string; editLabel: string; deleteLabel?: string; @@ -59,47 +59,56 @@ const UserActionPropertyActionsComponent = ({ setShowDeleteConfirm(false); }, []); - const propertyActions = useMemo( - () => - [ - permissions.all - ? [ - { - iconType: 'pencil', - label: editLabel, - onClick: onEditClick, - }, - ...(deleteLabel && onDelete - ? [ - { - iconType: 'trash', - label: deleteLabel, - onClick: onDeleteClick, - }, - ] - : []), - { - iconType: 'quote', - label: quoteLabel, - onClick: onQuoteClick, - }, - ] - : [], - canUseEditor && actionConfig ? [actionConfig] : [], - ].flat(), - [ - permissions.all, - editLabel, - onEditClick, - deleteLabel, - onDelete, - onDeleteClick, - quoteLabel, - onQuoteClick, - canUseEditor, - actionConfig, - ] - ); + const propertyActions = useMemo(() => { + const showEditPencilIcon = permissions.update; + const showTrashIcon = permissions.delete && deleteLabel && onDelete; + const showQuoteIcon = permissions.create; + const showLensEditor = permissions.update && canUseEditor && actionConfig; + + return [ + ...(showEditPencilIcon + ? [ + { + iconType: 'pencil', + label: editLabel, + onClick: onEditClick, + }, + ] + : []), + ...(showTrashIcon + ? [ + { + iconType: 'trash', + label: deleteLabel, + onClick: onDeleteClick, + }, + ] + : []), + ...(showQuoteIcon + ? [ + { + iconType: 'quote', + label: quoteLabel, + onClick: onQuoteClick, + }, + ] + : []), + ...(showLensEditor ? [actionConfig] : []), + ]; + }, [ + permissions.update, + permissions.delete, + permissions.create, + deleteLabel, + onDelete, + canUseEditor, + actionConfig, + editLabel, + onEditClick, + onDeleteClick, + quoteLabel, + onQuoteClick, + ]); if (!propertyActions.length) { return null; diff --git a/x-pack/plugins/cases/public/mocks.ts b/x-pack/plugins/cases/public/mocks.ts index 5d86b31d1e0cd..57eead3b80b10 100644 --- a/x-pack/plugins/cases/public/mocks.ts +++ b/x-pack/plugins/cases/public/mocks.ts @@ -28,6 +28,14 @@ const hooksMock: jest.Mocked<CasesUiStart['hooks']> = { const helpersMock: jest.Mocked<CasesUiStart['helpers']> = { canUseCases: jest.fn(), + getUICapabilities: jest.fn().mockReturnValue({ + all: false, + create: false, + read: false, + update: false, + delete: false, + push: false, + }), getRuleIdFromEvent: jest.fn(), groupAlertsByRule: jest.fn(), }; diff --git a/x-pack/plugins/cases/public/plugin.ts b/x-pack/plugins/cases/public/plugin.ts index 410ce5b31b07f..53b3b57d4e2ef 100644 --- a/x-pack/plugins/cases/public/plugin.ts +++ b/x-pack/plugins/cases/public/plugin.ts @@ -24,6 +24,7 @@ import { getCasesContextLazy } from './client/ui/get_cases_context'; import { getCreateCaseFlyoutLazy } from './client/ui/get_create_case_flyout'; import { getRecentCasesLazy } from './client/ui/get_recent_cases'; import { groupAlertsByRule } from './client/helpers/group_alerts_by_rule'; +import { getUICapabilities } from './client/helpers/capabilities'; import { ExternalReferenceAttachmentTypeRegistry } from './client/attachment_framework/external_reference_registry'; import { PersistableStateAttachmentTypeRegistry } from './client/attachment_framework/persistable_state_registry'; @@ -150,6 +151,7 @@ export class CasesUiPlugin }, helpers: { canUseCases: canUseCases(core.application.capabilities), + getUICapabilities, getRuleIdFromEvent, groupAlertsByRule, }, diff --git a/x-pack/plugins/cases/public/types.ts b/x-pack/plugins/cases/public/types.ts index b417fd0202516..f07dd8cd9fb04 100644 --- a/x-pack/plugins/cases/public/types.ts +++ b/x-pack/plugins/cases/public/types.ts @@ -29,7 +29,7 @@ import type { } from '../common/api'; import type { UseCasesAddToExistingCaseModal } from './components/all_cases/selector_modal/use_cases_add_to_existing_case_modal'; import type { UseCasesAddToNewCaseFlyout } from './components/create/flyout/use_cases_add_to_new_case_flyout'; -import type { CasesOwners } from './client/helpers/can_use_cases'; +import { canUseCases } from './client/helpers/can_use_cases'; import { getRuleIdFromEvent } from './client/helpers/get_rule_id_from_event'; import type { GetCasesContextProps } from './client/ui/get_cases_context'; import type { GetCasesProps } from './client/ui/get_cases'; @@ -38,6 +38,7 @@ import type { GetCreateCaseFlyoutProps } from './client/ui/get_create_case_flyou import type { GetRecentCasesProps } from './client/ui/get_recent_cases'; import type { Cases, CasesStatus, CasesMetrics } from '../common/ui'; import { groupAlertsByRule } from './client/helpers/group_alerts_by_rule'; +import { getUICapabilities } from './client/helpers/capabilities'; import type { AttachmentFramework } from './client/attachment_framework/types'; import { ExternalReferenceAttachmentTypeRegistry } from './client/attachment_framework/external_reference_registry'; import { PersistableStateAttachmentTypeRegistry } from './client/attachment_framework/persistable_state_registry'; @@ -137,7 +138,8 @@ export interface CasesUiStart { * @param owners an array of CaseOwners that should be queried for permission * @returns An object denoting the case permissions of the current user */ - canUseCases: (owners?: CasesOwners[]) => { crud: boolean; read: boolean }; + canUseCases: ReturnType<typeof canUseCases>; + getUICapabilities: typeof getUICapabilities; getRuleIdFromEvent: typeof getRuleIdFromEvent; groupAlertsByRule: typeof groupAlertsByRule; }; diff --git a/x-pack/plugins/cases/public/utils/permissions.ts b/x-pack/plugins/cases/public/utils/permissions.ts new file mode 100644 index 0000000000000..827535d484588 --- /dev/null +++ b/x-pack/plugins/cases/public/utils/permissions.ts @@ -0,0 +1,19 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { CasesPermissions } from '../../common'; + +export const isReadOnlyPermissions = (permissions: CasesPermissions) => { + return ( + !permissions.all && + !permissions.create && + !permissions.update && + !permissions.delete && + !permissions.push && + permissions.read + ); +}; diff --git a/x-pack/plugins/cases/server/features.ts b/x-pack/plugins/cases/server/features.ts index dabd3b37e5bb0..f2e7ad3bb74c6 100644 --- a/x-pack/plugins/cases/server/features.ts +++ b/x-pack/plugins/cases/server/features.ts @@ -11,6 +11,7 @@ import { KibanaFeatureConfig } from '@kbn/features-plugin/common'; import { DEFAULT_APP_CATEGORIES } from '@kbn/core/server'; import { APP_ID, FEATURE_ID } from '../common/constants'; +import { createUICapabilities } from '../common'; /** * The order of appearance in the feature privilege page @@ -20,44 +21,81 @@ import { APP_ID, FEATURE_ID } from '../common/constants'; const FEATURE_ORDER = 3100; -export const getCasesKibanaFeature = (): KibanaFeatureConfig => ({ - id: FEATURE_ID, - name: i18n.translate('xpack.cases.features.casesFeatureName', { - defaultMessage: 'Cases', - }), - category: DEFAULT_APP_CATEGORIES.management, - app: [], - order: FEATURE_ORDER, - management: { - insightsAndAlerting: [APP_ID], - }, - cases: [APP_ID], - privileges: { - all: { - cases: { - all: [APP_ID], - }, - management: { - insightsAndAlerting: [APP_ID], - }, - savedObject: { - all: [], - read: [], - }, - ui: ['crud_cases', 'read_cases'], +export const getCasesKibanaFeature = (): KibanaFeatureConfig => { + const capabilities = createUICapabilities(); + + return { + id: FEATURE_ID, + name: i18n.translate('xpack.cases.features.casesFeatureName', { + defaultMessage: 'Cases', + }), + category: DEFAULT_APP_CATEGORIES.management, + app: [], + order: FEATURE_ORDER, + management: { + insightsAndAlerting: [APP_ID], }, - read: { - cases: { - read: [APP_ID], - }, - management: { - insightsAndAlerting: [APP_ID], + cases: [APP_ID], + privileges: { + all: { + cases: { + create: [APP_ID], + read: [APP_ID], + update: [APP_ID], + push: [APP_ID], + }, + management: { + insightsAndAlerting: [APP_ID], + }, + savedObject: { + all: [], + read: [], + }, + ui: capabilities.all, }, - savedObject: { - all: [], - read: [], + read: { + cases: { + read: [APP_ID], + }, + management: { + insightsAndAlerting: [APP_ID], + }, + savedObject: { + all: [], + read: [], + }, + ui: capabilities.read, }, - ui: ['read_cases'], }, - }, -}); + subFeatures: [ + { + name: i18n.translate('xpack.cases.features.deleteSubFeatureName', { + defaultMessage: 'Delete', + }), + privilegeGroups: [ + { + groupType: 'independent', + privileges: [ + { + api: [], + id: 'cases_delete', + name: i18n.translate('xpack.cases.features.deleteSubFeatureDetails', { + defaultMessage: 'Delete cases and comments', + }), + includeIn: 'all', + savedObject: { + all: [], + read: [], + }, + cases: { + delete: [APP_ID], + }, + ui: capabilities.delete, + }, + ], + }, + ], + }, + ], + }; +}; diff --git a/x-pack/plugins/observability/public/components/shared/exploratory_view/components/action_menu/action_menu.test.tsx b/x-pack/plugins/observability/public/components/shared/exploratory_view/components/action_menu/action_menu.test.tsx index 0c2063ba8b1b0..566c271381125 100644 --- a/x-pack/plugins/observability/public/components/shared/exploratory_view/components/action_menu/action_menu.test.tsx +++ b/x-pack/plugins/observability/public/components/shared/exploratory_view/components/action_menu/action_menu.test.tsx @@ -12,6 +12,7 @@ import { sampleAttribute } from '../../configurations/test_data/sample_attribute import * as pluginHook from '../../../../../hooks/use_plugin_context'; import { TypedLensByValueInput } from '@kbn/lens-plugin/public'; import { ExpViewActionMenuContent } from './action_menu'; +import { noCasesPermissions as mockUseGetCasesPermissions } from '../../../../../utils/cases_permissions'; jest.spyOn(pluginHook, 'usePluginContext').mockReturnValue({ appMountParameters: { @@ -19,7 +20,15 @@ jest.spyOn(pluginHook, 'usePluginContext').mockReturnValue({ }, } as any); +jest.mock('../../../../../hooks/use_get_user_cases_permissions', () => ({ + useGetUserCasesPermissions: jest.fn(() => mockUseGetCasesPermissions()), +})); + describe('Action Menu', function () { + afterAll(() => { + jest.clearAllMocks(); + }); + it('should be able to click open in lens', async function () { const { findByText, core } = render( <ExpViewActionMenuContent diff --git a/x-pack/plugins/observability/public/components/shared/exploratory_view/exploratory_view.test.tsx b/x-pack/plugins/observability/public/components/shared/exploratory_view/exploratory_view.test.tsx index 2bd79116dc45b..9f50b22dc9f76 100644 --- a/x-pack/plugins/observability/public/components/shared/exploratory_view/exploratory_view.test.tsx +++ b/x-pack/plugins/observability/public/components/shared/exploratory_view/exploratory_view.test.tsx @@ -12,12 +12,18 @@ import { ExploratoryView } from './exploratory_view'; import * as obsvDataViews from '../../../utils/observability_data_views/observability_data_views'; import * as pluginHook from '../../../hooks/use_plugin_context'; import { createStubIndexPattern } from '@kbn/data-plugin/common/stubs'; +import { noCasesPermissions as mockUseGetCasesPermissions } from '../../../utils/cases_permissions'; jest.spyOn(pluginHook, 'usePluginContext').mockReturnValue({ appMountParameters: { setHeaderActionMenu: jest.fn(), }, } as any); + +jest.mock('../../../hooks/use_get_user_cases_permissions', () => ({ + useGetUserCasesPermissions: jest.fn(() => mockUseGetCasesPermissions()), +})); + describe('ExploratoryView', () => { mockAppDataView(); diff --git a/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.test.tsx b/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.test.tsx index b394b085a7c75..e6f432f4f30cb 100644 --- a/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.test.tsx +++ b/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.test.tsx @@ -11,8 +11,12 @@ import { fireEvent } from '@testing-library/dom'; import { AddToCaseAction } from './add_to_case_action'; import * as useCaseHook from '../hooks/use_add_to_case'; import * as datePicker from '../components/date_range_picker'; -import * as useGetUserCasesPermissionsModule from '../../../../hooks/use_get_user_cases_permissions'; import moment from 'moment'; +import { noCasesPermissions as mockUseGetCasesPermissions } from '../../../../utils/cases_permissions'; + +jest.mock('../../../../hooks/use_get_user_cases_permissions', () => ({ + useGetUserCasesPermissions: jest.fn(() => mockUseGetCasesPermissions()), +})); describe('AddToCaseAction', function () { beforeEach(() => { @@ -82,10 +86,6 @@ describe('AddToCaseAction', function () { }); it('should be able to click add to case button', async function () { - const mockUseGetUserCasesPermissions = jest - .spyOn(useGetUserCasesPermissionsModule, 'useGetUserCasesPermissions') - .mockImplementation(() => ({ crud: false, read: false })); - const initSeries = { data: [ { @@ -113,11 +113,13 @@ describe('AddToCaseAction', function () { owner: ['observability'], permissions: { all: false, + create: false, read: false, + update: false, + delete: false, + push: false, }, }) ); - - mockUseGetUserCasesPermissions.mockRestore(); }); }); diff --git a/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.tsx b/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.tsx index 118451b302948..dd2124e6b1982 100644 --- a/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.tsx +++ b/x-pack/plugins/observability/public/components/shared/exploratory_view/header/add_to_case_action.tsx @@ -39,8 +39,7 @@ export function AddToCaseAction({ timeRange, }: AddToCaseProps) { const kServices = useKibana<ObservabilityAppServices>().services; - const userPermissions = useGetUserCasesPermissions(); - const casesPermissions = { all: userPermissions.crud, read: userPermissions.read }; + const userCasesPermissions = useGetUserCasesPermissions(); const { cases, @@ -77,7 +76,7 @@ export function AddToCaseAction({ }); const getAllCasesSelectorModalProps: GetAllCasesSelectorModalProps = { - permissions: casesPermissions, + permissions: userCasesPermissions, onRowClick: onCaseClicked, owner: [owner], onClose: () => { diff --git a/x-pack/plugins/observability/public/hooks/use_alert_bulk_case_actions.ts b/x-pack/plugins/observability/public/hooks/use_alert_bulk_case_actions.ts index 2aa4c40575143..0ca4f5a7187ba 100644 --- a/x-pack/plugins/observability/public/hooks/use_alert_bulk_case_actions.ts +++ b/x-pack/plugins/observability/public/hooks/use_alert_bulk_case_actions.ts @@ -25,8 +25,7 @@ export interface UseAddToCaseActions { export const useBulkAddToCaseActions = ({ onClose, onSuccess }: UseAddToCaseActions = {}) => { const { cases: casesUi } = useKibana<ObservabilityAppServices>().services; - const casePermissions = useGetUserCasesPermissions(); - const hasWritePermissions = casePermissions?.crud ?? false; + const userCasesPermissions = useGetUserCasesPermissions(); const createCaseFlyout = casesUi.hooks.getUseCasesAddToNewCaseFlyout({ onClose, @@ -38,7 +37,7 @@ export const useBulkAddToCaseActions = ({ onClose, onSuccess }: UseAddToCaseActi }); return useMemo(() => { - return hasWritePermissions + return userCasesPermissions.create && userCasesPermissions.read ? [ { label: ADD_TO_NEW_CASE, @@ -68,5 +67,11 @@ export const useBulkAddToCaseActions = ({ onClose, onSuccess }: UseAddToCaseActi }, ] : []; - }, [casesUi.helpers, createCaseFlyout, hasWritePermissions, selectCaseModal]); + }, [ + casesUi.helpers, + createCaseFlyout, + userCasesPermissions.create, + userCasesPermissions.read, + selectCaseModal, + ]); }; diff --git a/x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.test.ts b/x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.test.ts deleted file mode 100644 index 3f23aec4a6058..0000000000000 --- a/x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.test.ts +++ /dev/null @@ -1,79 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { renderHook } from '@testing-library/react-hooks'; -import { applicationServiceMock } from '@kbn/core/public/mocks'; -import { casesFeatureId } from '../../common'; -import { useGetUserCasesPermissions } from './use_get_user_cases_permissions'; -import { kibanaStartMock } from '../utils/kibana_react.mock'; - -let mockUseKibanaReturnValue = kibanaStartMock.startContract(); - -jest.mock('../utils/kibana_react', () => ({ - __esModule: true, - useKibana: jest.fn(() => mockUseKibanaReturnValue), -})); - -describe('useGetUserCasesPermissions', function () { - it('returns expected permissions when capabilities entry exists', () => { - mockUseKibanaReturnValue = { - ...mockUseKibanaReturnValue, - services: { - ...mockUseKibanaReturnValue.services, - application: { - ...mockUseKibanaReturnValue.services.application, - capabilities: { - ...applicationServiceMock.createStartContract().capabilities, - [casesFeatureId]: { crud_cases: false, read_cases: true }, - }, - }, - }, - }; - const { result } = renderHook(() => useGetUserCasesPermissions(), {}); - expect(result.current?.read).toBe(true); - expect(result.current?.crud).toBe(false); - }); - - it('returns false when capabilities entry permissions are missing', () => { - mockUseKibanaReturnValue = { - ...mockUseKibanaReturnValue, - services: { - ...mockUseKibanaReturnValue.services, - application: { - ...mockUseKibanaReturnValue.services.application, - capabilities: { - ...applicationServiceMock.createStartContract().capabilities, - [casesFeatureId]: { - /* intentionally empty */ - }, - }, - }, - }, - }; - const { result } = renderHook(() => useGetUserCasesPermissions(), {}); - expect(result.current?.read).toBe(false); - expect(result.current?.crud).toBe(false); - }); - - it('returns false when capabilities entry is missing entirely', () => { - mockUseKibanaReturnValue = { - ...mockUseKibanaReturnValue, - services: { - ...mockUseKibanaReturnValue.services, - application: { - ...mockUseKibanaReturnValue.services.application, - capabilities: { - ...applicationServiceMock.createStartContract().capabilities, - }, - }, - }, - }; - const { result } = renderHook(() => useGetUserCasesPermissions(), {}); - expect(result.current?.read).toBe(false); - expect(result.current?.crud).toBe(false); - }); -}); diff --git a/x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.tsx b/x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.tsx index 83481c6d1f2f4..d2c47da425a01 100644 --- a/x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.tsx +++ b/x-pack/plugins/observability/public/hooks/use_get_user_cases_permissions.tsx @@ -6,35 +6,42 @@ */ import { useEffect, useState } from 'react'; +import { CasesPermissions } from '@kbn/cases-plugin/common'; import { useKibana } from '../utils/kibana_react'; import { casesFeatureId } from '../../common'; -export interface UseGetUserCasesPermissions { - crud: boolean; - read: boolean; -} - export function useGetUserCasesPermissions() { - const [casesPermissions, setCasesPermissions] = useState<UseGetUserCasesPermissions>({ - crud: false, + const [casesPermissions, setCasesPermissions] = useState<CasesPermissions>({ + all: false, read: false, + create: false, + update: false, + delete: false, + push: false, }); const uiCapabilities = useKibana().services.application.capabilities; + const casesCapabilities = useKibana().services.cases.helpers.getUICapabilities( + uiCapabilities[casesFeatureId] + ); + useEffect(() => { - const capabilitiesCanUserCRUD: boolean = - typeof uiCapabilities[casesFeatureId]?.crud_cases === 'boolean' - ? (uiCapabilities[casesFeatureId].crud_cases as boolean) - : false; - const capabilitiesCanUserRead: boolean = - typeof uiCapabilities[casesFeatureId]?.read_cases === 'boolean' - ? (uiCapabilities[casesFeatureId].read_cases as boolean) - : false; setCasesPermissions({ - crud: capabilitiesCanUserCRUD, - read: capabilitiesCanUserRead, + all: casesCapabilities.all, + create: casesCapabilities.create, + read: casesCapabilities.read, + update: casesCapabilities.update, + delete: casesCapabilities.delete, + push: casesCapabilities.push, }); - }, [uiCapabilities]); + }, [ + casesCapabilities.all, + casesCapabilities.create, + casesCapabilities.read, + casesCapabilities.update, + casesCapabilities.delete, + casesCapabilities.push, + ]); return casesPermissions; } diff --git a/x-pack/plugins/observability/public/observability_public_plugins_start.mock.ts b/x-pack/plugins/observability/public/observability_public_plugins_start.mock.ts index 80a207a846d33..5d87ff009040c 100644 --- a/x-pack/plugins/observability/public/observability_public_plugins_start.mock.ts +++ b/x-pack/plugins/observability/public/observability_public_plugins_start.mock.ts @@ -5,16 +5,7 @@ * 2.0. */ -const casesUiStartMock = { - createStart() { - return { - getCases: jest.fn(), - getAllCasesSelectorModal: jest.fn(), - getCreateCaseFlyout: jest.fn(), - getRecentCases: jest.fn(), - }; - }, -}; +import { mockCasesContract } from '@kbn/cases-plugin/public/mocks'; const embeddableStartMock = { createStart() { @@ -60,7 +51,7 @@ const triggersActionsUiStartMock = { export const observabilityPublicPluginsStartMock = { createStart() { return { - cases: casesUiStartMock.createStart(), + cases: mockCasesContract(), embeddable: embeddableStartMock.createStart(), triggersActionsUi: triggersActionsUiStartMock.createStart(), data: null, diff --git a/x-pack/plugins/observability/public/pages/alerts/containers/alerts_page/alerts_page.tsx b/x-pack/plugins/observability/public/pages/alerts/containers/alerts_page/alerts_page.tsx index d903876c79f86..b33a7ecd03c10 100644 --- a/x-pack/plugins/observability/public/pages/alerts/containers/alerts_page/alerts_page.tsx +++ b/x-pack/plugins/observability/public/pages/alerts/containers/alerts_page/alerts_page.tsx @@ -219,8 +219,7 @@ function AlertsPage() { const hasData = hasAnyData === true || (isAllRequestsComplete === false ? undefined : false); const CasesContext = cases.ui.getCasesContext(); - const userPermissions = useGetUserCasesPermissions(); - const casesPermissions = { all: userPermissions.crud, read: userPermissions.read }; + const userCasesPermissions = useGetUserCasesPermissions(); if (!hasAnyData && !isAllRequestsComplete) { return <LoadingObservability />; @@ -266,7 +265,7 @@ function AlertsPage() { <EuiFlexItem> <CasesContext owner={[observabilityFeatureId]} - permissions={casesPermissions} + permissions={userCasesPermissions} features={{ alerts: { sync: false } }} > <AlertsTableTGrid diff --git a/x-pack/plugins/observability/public/pages/alerts/containers/alerts_table_t_grid/alerts_table_t_grid.tsx b/x-pack/plugins/observability/public/pages/alerts/containers/alerts_table_t_grid/alerts_table_t_grid.tsx index 1b6f0b1860045..9afe75f2ae310 100644 --- a/x-pack/plugins/observability/public/pages/alerts/containers/alerts_table_t_grid/alerts_table_t_grid.tsx +++ b/x-pack/plugins/observability/public/pages/alerts/containers/alerts_table_t_grid/alerts_table_t_grid.tsx @@ -168,7 +168,7 @@ function ObservabilityActions({ setActionsPopover((current) => (current ? null : id)); }, []); - const casePermissions = useGetUserCasesPermissions(); + const userCasesPermissions = useGetUserCasesPermissions(); const ruleId = alert.fields['kibana.alert.rule.uuid'] ?? null; const linkToRule = ruleId ? http.basePath.prepend(paths.observability.ruleDetails(ruleId)) : null; const caseAttachments: CaseAttachments = useMemo(() => { @@ -201,7 +201,7 @@ function ObservabilityActions({ const actionsMenuItems = useMemo(() => { return [ - ...(casePermissions.crud + ...(userCasesPermissions.create && userCasesPermissions.read ? [ <EuiContextMenuItem data-test-subj="add-to-existing-case-action" @@ -246,7 +246,8 @@ function ObservabilityActions({ ], ]; }, [ - casePermissions.crud, + userCasesPermissions.create, + userCasesPermissions.read, handleAddToExistingCaseClick, handleAddToNewCaseClick, linkToRule, @@ -332,7 +333,7 @@ export function AlertsTableTGrid(props: AlertsTableTGridProps) { storage.get(stateStorageKey) ); - const casePermissions = useGetUserCasesPermissions(); + const userCasesPermissions = useGetUserCasesPermissions(); const hasAlertsCrudPermissions = useCallback( ({ ruleConsumer, ruleProducer }: { ruleConsumer: string; ruleProducer?: string }) => { @@ -415,7 +416,7 @@ export function AlertsTableTGrid(props: AlertsTableTGridProps) { return { appId: observabilityAppId, casesOwner: observabilityFeatureId, - casePermissions, + casePermissions: userCasesPermissions, type, columns: (tGridState?.columns ?? columns).map(addDisplayNames), deletedEventIds, @@ -464,7 +465,7 @@ export function AlertsTableTGrid(props: AlertsTableTGridProps) { unit: (totalAlerts: number) => translations.alertsTable.showingAlertsTitle(totalAlerts), }; }, [ - casePermissions, + userCasesPermissions, tGridState?.columns, tGridState?.sort, deletedEventIds, diff --git a/x-pack/plugins/observability/public/pages/cases/cases.tsx b/x-pack/plugins/observability/public/pages/cases/cases.tsx index ee7af69937881..28a9f90251f64 100644 --- a/x-pack/plugins/observability/public/pages/cases/cases.tsx +++ b/x-pack/plugins/observability/public/pages/cases/cases.tsx @@ -7,18 +7,18 @@ import React, { Suspense, useCallback, useState } from 'react'; +import { CasesPermissions } from '@kbn/cases-plugin/common'; import { useKibana } from '@kbn/kibana-react-plugin/public'; import { CASES_OWNER, CASES_PATH } from './constants'; import { usePluginContext } from '../../hooks/use_plugin_context'; import { LazyAlertsFlyout } from '../..'; import { useFetchAlertDetail } from './use_fetch_alert_detail'; import { useFetchAlertData } from './use_fetch_alert_data'; -import { UseGetUserCasesPermissions } from '../../hooks/use_get_user_cases_permissions'; import { paths } from '../../config'; import { ObservabilityAppServices } from '../../application/types'; interface CasesProps { - permissions: UseGetUserCasesPermissions; + permissions: CasesPermissions; } export const Cases = React.memo<CasesProps>(({ permissions }) => { const { @@ -30,7 +30,6 @@ export const Cases = React.memo<CasesProps>(({ permissions }) => { } = useKibana<ObservabilityAppServices>().services; const { observabilityRuleTypeRegistry } = usePluginContext(); const [selectedAlertId, setSelectedAlertId] = useState<string>(''); - const casesPermissions = { all: permissions.crud, read: permissions.read }; const handleFlyoutClose = useCallback(() => { setSelectedAlertId(''); @@ -51,7 +50,7 @@ export const Cases = React.memo<CasesProps>(({ permissions }) => { )} {cases.ui.getCases({ basePath: CASES_PATH, - permissions: casesPermissions, + permissions, owner: [CASES_OWNER], features: { alerts: { sync: false } }, useFetchAlertData, diff --git a/x-pack/plugins/observability/public/pages/cases/index.tsx b/x-pack/plugins/observability/public/pages/cases/index.tsx index a3d1505d8f488..08a5b7c7cf6bc 100644 --- a/x-pack/plugins/observability/public/pages/cases/index.tsx +++ b/x-pack/plugins/observability/public/pages/cases/index.tsx @@ -19,7 +19,7 @@ import { getNoDataConfig } from '../../utils/no_data_config'; import { ObservabilityAppServices } from '../../application/types'; export const CasesPage = React.memo(() => { - const userPermissions = useGetUserCasesPermissions(); + const userCasesPermissions = useGetUserCasesPermissions(); const { docLinks, http } = useKibana<ObservabilityAppServices>().services; const { ObservabilityPageTemplate } = usePluginContext(); @@ -38,13 +38,13 @@ export const CasesPage = React.memo(() => { docsLink: docLinks.links.observability.guide, }); - return userPermissions.read ? ( + return userCasesPermissions.read ? ( <ObservabilityPageTemplate isPageDataLoaded={Boolean(hasAnyData || isAllRequestsComplete)} data-test-subj={noDataConfig ? 'noDataPage' : undefined} noDataConfig={noDataConfig} > - <Cases permissions={userPermissions} /> + <Cases permissions={userCasesPermissions} /> </ObservabilityPageTemplate> ) : ( <CaseFeatureNoPermissions /> diff --git a/x-pack/plugins/observability/public/pages/overview/index.tsx b/x-pack/plugins/observability/public/pages/overview/index.tsx index dc0a6c9667400..fdf56e88a156e 100644 --- a/x-pack/plugins/observability/public/pages/overview/index.tsx +++ b/x-pack/plugins/observability/public/pages/overview/index.tsx @@ -127,8 +127,7 @@ export function OverviewPage({ routeParams }: Props) { }, []); const CasesContext = cases.ui.getCasesContext(); - const userPermissions = useGetUserCasesPermissions(); - const casesPermissions = { all: userPermissions.crud, read: userPermissions.read }; + const userCasesPermissions = useGetUserCasesPermissions(); useEffect(() => { if (hasAnyData !== true) { @@ -200,7 +199,7 @@ export function OverviewPage({ routeParams }: Props) { > <CasesContext owner={[observabilityFeatureId]} - permissions={casesPermissions} + permissions={userCasesPermissions} features={{ alerts: { sync: false } }} > <AlertsTableTGrid diff --git a/x-pack/plugins/observability/public/utils/cases_permissions.ts b/x-pack/plugins/observability/public/utils/cases_permissions.ts new file mode 100644 index 0000000000000..2b3ff9cfbaf54 --- /dev/null +++ b/x-pack/plugins/observability/public/utils/cases_permissions.ts @@ -0,0 +1,15 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +export const noCasesPermissions = () => ({ + all: false, + create: false, + read: false, + update: false, + delete: false, + push: false, +}); diff --git a/x-pack/plugins/observability/server/plugin.ts b/x-pack/plugins/observability/server/plugin.ts index f1f58bd55b8f4..a5e530f6d6fbe 100644 --- a/x-pack/plugins/observability/server/plugin.ts +++ b/x-pack/plugins/observability/server/plugin.ts @@ -14,6 +14,7 @@ import { } from '@kbn/core/server'; import { RuleRegistryPluginSetupContract } from '@kbn/rule-registry-plugin/server'; import { PluginSetupContract as FeaturesSetup } from '@kbn/features-plugin/server'; +import { createUICapabilities } from '@kbn/cases-plugin/common'; import { ObservabilityConfig } from '.'; import { bootstrapAnnotations, @@ -40,6 +41,8 @@ export class ObservabilityPlugin implements Plugin<ObservabilityPluginSetup> { public setup(core: CoreSetup, plugins: PluginSetup) { const config = this.initContext.config.get<ObservabilityConfig>(); + const casesCapabilities = createUICapabilities(); + plugins.features.registerKibanaFeature({ id: casesFeatureId, name: i18n.translate('xpack.observability.featureRegistry.linkObservabilityTitle', { @@ -55,14 +58,17 @@ export class ObservabilityPlugin implements Plugin<ObservabilityPluginSetup> { app: [casesFeatureId, 'kibana'], catalogue: [observabilityFeatureId], cases: { - all: [observabilityFeatureId], + create: [observabilityFeatureId], + read: [observabilityFeatureId], + update: [observabilityFeatureId], + push: [observabilityFeatureId], }, api: [], savedObject: { all: [], read: [], }, - ui: ['crud_cases', 'read_cases'], // uiCapabilities[casesFeatureId].crud_cases or read_cases + ui: casesCapabilities.all, }, read: { app: [casesFeatureId, 'kibana'], @@ -75,9 +81,42 @@ export class ObservabilityPlugin implements Plugin<ObservabilityPluginSetup> { all: [], read: [], }, - ui: ['read_cases'], // uiCapabilities[uiCapabilities[casesFeatureId]].read_cases + ui: casesCapabilities.read, }, }, + subFeatures: [ + { + name: i18n.translate('xpack.observability.featureRegistry.deleteSubFeatureName', { + defaultMessage: 'Delete', + }), + privilegeGroups: [ + { + groupType: 'independent', + privileges: [ + { + api: [], + id: 'cases_delete', + name: i18n.translate( + 'xpack.observability.featureRegistry.deleteSubFeatureDetails', + { + defaultMessage: 'Delete cases and comments', + } + ), + includeIn: 'all', + savedObject: { + all: [], + read: [], + }, + cases: { + delete: [observabilityFeatureId], + }, + ui: casesCapabilities.delete, + }, + ], + }, + ], + }, + ], }); let annotationsApiPromise: Promise<AnnotationsAPI> | undefined; diff --git a/x-pack/plugins/security_solution/cypress/integration/cases/privileges.spec.ts b/x-pack/plugins/security_solution/cypress/integration/cases/privileges.spec.ts index a33e7f9bd295c..b19a4eb6b4501 100644 --- a/x-pack/plugins/security_solution/cypress/integration/cases/privileges.spec.ts +++ b/x-pack/plugins/security_solution/cypress/integration/cases/privileges.spec.ts @@ -6,7 +6,7 @@ */ import type { TestCaseWithoutTimeline } from '../../objects/case'; -import { ALL_CASES_NAME } from '../../screens/all_cases'; +import { ALL_CASES_CREATE_NEW_CASE_BTN, ALL_CASES_NAME } from '../../screens/all_cases'; import { goToCreateNewCase } from '../../tasks/all_cases'; import { cleanKibana, deleteCases } from '../../tasks/common'; @@ -31,12 +31,21 @@ import { secAllUser, secReadCasesAllUser, secReadCasesAll, + secAllCasesNoDelete, + secAllCasesNoDeleteUser, + secAllCasesOnlyReadDeleteUser, + secAllCasesOnlyReadDelete, } from '../../tasks/privileges'; import { CASES_URL } from '../../urls/navigation'; import { openSourcerer } from '../../tasks/sourcerer'; -const usersToCreate = [secAllUser, secReadCasesAllUser]; -const rolesToCreate = [secAll, secReadCasesAll]; +const usersToCreate = [ + secAllUser, + secReadCasesAllUser, + secAllCasesNoDeleteUser, + secAllCasesOnlyReadDeleteUser, +]; +const rolesToCreate = [secAll, secReadCasesAll, secAllCasesNoDelete, secAllCasesOnlyReadDelete]; // needed to generate index pattern const visitSecuritySolution = () => { visitHostDetailsPage(); @@ -51,6 +60,7 @@ const testCase: TestCaseWithoutTimeline = { reporter: 'elastic', owner: 'securitySolution', }; + describe('Cases privileges', () => { before(() => { cleanKibana(); @@ -67,7 +77,7 @@ describe('Cases privileges', () => { deleteCases(); }); - for (const user of [secAllUser, secReadCasesAllUser]) { + for (const user of [secAllUser, secReadCasesAllUser, secAllCasesNoDeleteUser]) { it(`User ${user.username} with role(s) ${user.roles.join()} can create a case`, () => { loginWithUser(user); visitWithUser(CASES_URL, user); @@ -80,4 +90,12 @@ describe('Cases privileges', () => { cy.get(ALL_CASES_NAME).should('have.text', testCase.name); }); } + + for (const user of [secAllCasesOnlyReadDeleteUser]) { + it(`User ${user.username} with role(s) ${user.roles.join()} cannot create a case`, () => { + loginWithUser(user); + visitWithUser(CASES_URL, user); + cy.get(ALL_CASES_CREATE_NEW_CASE_BTN).should('not.exist'); + }); + } }); diff --git a/x-pack/plugins/security_solution/cypress/tasks/privileges.ts b/x-pack/plugins/security_solution/cypress/tasks/privileges.ts index bd6bb80d2edb6..bd55745200b4f 100644 --- a/x-pack/plugins/security_solution/cypress/tasks/privileges.ts +++ b/x-pack/plugins/security_solution/cypress/tasks/privileges.ts @@ -110,6 +110,68 @@ export const secReadCasesAllUser: User = { roles: [secReadCasesAll.name], }; +export const secAllCasesOnlyReadDelete: Role = { + name: 'sec_all_cases_only_read_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['all'], + securitySolutionCases: ['cases_read', 'cases_delete'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secAllCasesOnlyReadDeleteUser: User = { + username: 'sec_all_cases_only_read_delete_user', + password: 'password', + roles: [secAllCasesOnlyReadDelete.name], +}; + +export const secAllCasesNoDelete: Role = { + name: 'sec_all_cases_no_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['all'], + securitySolutionCases: ['minimal_all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secAllCasesNoDeleteUser: User = { + username: 'sec_all_cases_no_delete_user', + password: 'password', + roles: [secAllCasesNoDelete.name], +}; + const getUserInfo = (user: User): UserInfo => ({ username: user.username, full_name: user.username.replace('_', ' '), diff --git a/x-pack/plugins/security_solution/public/app/app.tsx b/x-pack/plugins/security_solution/public/app/app.tsx index 74aaa25f615fa..990c089a35fc1 100644 --- a/x-pack/plugins/security_solution/public/app/app.tsx +++ b/x-pack/plugins/security_solution/public/app/app.tsx @@ -57,8 +57,7 @@ const StartAppComponent: FC<StartAppComponent> = ({ cases, } = useKibana().services; const [darkMode] = useUiSetting$<boolean>(DEFAULT_DARK_MODE); - const userPermissions = useGetUserCasesPermissions(); - const casesPermissions = { all: userPermissions.crud, read: userPermissions.read }; + const userCasesPermissions = useGetUserCasesPermissions(); const CasesContext = cases.ui.getCasesContext(); return ( <EuiErrorBoundary> @@ -71,7 +70,7 @@ const StartAppComponent: FC<StartAppComponent> = ({ <UserPrivilegesProvider kibanaCapabilities={capabilities}> <ManageUserInfo> <ReactQueryClientProvider> - <CasesContext owner={[APP_ID]} permissions={casesPermissions}> + <CasesContext owner={[APP_ID]} permissions={userCasesPermissions}> <PageRouter history={history} onAppLeave={onAppLeave} diff --git a/x-pack/plugins/security_solution/public/app/deep_links/index.test.ts b/x-pack/plugins/security_solution/public/app/deep_links/index.test.ts index 2e829e87c1490..8b6db14e78986 100644 --- a/x-pack/plugins/security_solution/public/app/deep_links/index.test.ts +++ b/x-pack/plugins/security_solution/public/app/deep_links/index.test.ts @@ -4,11 +4,12 @@ * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ -import { getDeepLinks } from '.'; +import { getDeepLinks, hasFeaturesCapability } from '.'; import type { AppDeepLink, Capabilities } from '@kbn/core/public'; import { SecurityPageName } from '../types'; import { mockGlobalState } from '../../common/mock'; import { CASES_FEATURE_ID, SERVER_APP_ID } from '../../../common/constants'; +import { createCapabilities } from '../../common/links/test_utils'; const findDeepLink = (id: string, deepLinks: AppDeepLink[]): AppDeepLink | null => deepLinks.reduce((deepLinkFound: AppDeepLink | null, deepLink) => { @@ -28,6 +29,14 @@ const basicLicense = 'basic'; const platinumLicense = 'platinum'; describe('deepLinks', () => { + describe('hasFeaturesCapability', () => { + it('returns true when features is undefined', () => { + expect( + hasFeaturesCapability(undefined, createCapabilities({ siem: { show: true } })) + ).toBeTruthy(); + }); + }); + it('should return a all basic license deep links in the premium deep links', () => { const basicLinks = getDeepLinks(mockGlobalState.app.enableExperimental, basicLicense); const platinumLinks = getDeepLinks(mockGlobalState.app.enableExperimental, platinumLicense); @@ -68,7 +77,7 @@ describe('deepLinks', () => { it('should return case links for basic license with only read_cases capabilities', () => { const basicLinks = getDeepLinks(mockGlobalState.app.enableExperimental, basicLicense, { - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: false }, + [CASES_FEATURE_ID]: { read_cases: true }, [SERVER_APP_ID]: { show: true }, } as unknown as Capabilities); expect(findDeepLink(SecurityPageName.case, basicLinks)).toBeTruthy(); @@ -76,15 +85,21 @@ describe('deepLinks', () => { it('should return case links with NO deepLinks for basic license with only read_cases capabilities', () => { const basicLinks = getDeepLinks(mockGlobalState.app.enableExperimental, basicLicense, { - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: false }, + [CASES_FEATURE_ID]: { read_cases: true }, [SERVER_APP_ID]: { show: true }, } as unknown as Capabilities); expect(findDeepLink(SecurityPageName.case, basicLinks)?.deepLinks?.length === 0).toBeTruthy(); }); - it('should return case links with deepLinks for basic license with crud_cases capabilities', () => { + it('should return case links with deepLinks for basic license with permissive capabilities', () => { const basicLinks = getDeepLinks(mockGlobalState.app.enableExperimental, basicLicense, { - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: true }, + [CASES_FEATURE_ID]: { + create_cases: true, + read_cases: true, + update_cases: true, + delete_cases: true, + push_cases: true, + }, [SERVER_APP_ID]: { show: true }, } as unknown as Capabilities); @@ -93,17 +108,29 @@ describe('deepLinks', () => { ).toBeTruthy(); }); - it('should return case links with deepLinks for basic license with crud_cases capabilities and security disabled', () => { + it('should return case links with deepLinks for basic license with permissive capabilities and security disabled', () => { const basicLinks = getDeepLinks(mockGlobalState.app.enableExperimental, platinumLicense, { - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: true }, + [CASES_FEATURE_ID]: { + create_cases: true, + read_cases: true, + update_cases: true, + delete_cases: true, + push_cases: true, + }, [SERVER_APP_ID]: { show: false }, } as unknown as Capabilities); expect(findDeepLink(SecurityPageName.case, basicLinks)).toBeTruthy(); }); - it('should return NO case links for basic license with NO read_cases capabilities', () => { + it('should return NO case links for basic license with NO cases capabilities', () => { const basicLinks = getDeepLinks(mockGlobalState.app.enableExperimental, basicLicense, { - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: { + create_cases: false, + read_cases: false, + update_cases: false, + delete_cases: false, + push_cases: false, + }, [SERVER_APP_ID]: { show: true }, } as unknown as Capabilities); expect(findDeepLink(SecurityPageName.case, basicLinks)).toBeFalsy(); diff --git a/x-pack/plugins/security_solution/public/app/deep_links/index.ts b/x-pack/plugins/security_solution/public/app/deep_links/index.ts index c6745b4f9b614..2060d21baaf9c 100644 --- a/x-pack/plugins/security_solution/public/app/deep_links/index.ts +++ b/x-pack/plugins/security_solution/public/app/deep_links/index.ts @@ -7,9 +7,15 @@ import { i18n } from '@kbn/i18n'; -import { get } from 'lodash'; import type { LicenseType } from '@kbn/licensing-plugin/common/types'; import { getCasesDeepLinks } from '@kbn/cases-plugin/public'; +import { + CREATE_CASES_CAPABILITY, + DELETE_CASES_CAPABILITY, + PUSH_CASES_CAPABILITY, + READ_CASES_CAPABILITY, + UPDATE_CASES_CAPABILITY, +} from '@kbn/cases-plugin/common'; import type { AppDeepLink, AppUpdater, Capabilities } from '@kbn/core/public'; import { AppNavLinkStatus } from '@kbn/core/public'; import type { Subject, Subscription } from 'rxjs'; @@ -65,20 +71,36 @@ import { RESPONSE_ACTIONS_PATH, } from '../../../common/constants'; import type { ExperimentalFeatures } from '../../../common/experimental_features'; -import { subscribeAppLinks } from '../../common/links'; +import { hasCapabilities, subscribeAppLinks } from '../../common/links'; import type { AppLinkItems } from '../../common/links/types'; -const FEATURE = { +export const FEATURE = { general: `${SERVER_APP_ID}.show`, - casesRead: `${CASES_FEATURE_ID}.read_cases`, - casesCrud: `${CASES_FEATURE_ID}.crud_cases`, + casesCreate: `${CASES_FEATURE_ID}.${CREATE_CASES_CAPABILITY}`, + casesRead: `${CASES_FEATURE_ID}.${READ_CASES_CAPABILITY}`, + casesUpdate: `${CASES_FEATURE_ID}.${UPDATE_CASES_CAPABILITY}`, + casesDelete: `${CASES_FEATURE_ID}.${DELETE_CASES_CAPABILITY}`, + casesPush: `${CASES_FEATURE_ID}.${PUSH_CASES_CAPABILITY}`, } as const; -type Feature = typeof FEATURE[keyof typeof FEATURE]; +type FeatureKey = typeof FEATURE[keyof typeof FEATURE]; + +/** + * The format of defining features supports OR and AND mechanism. To specify features in an OR fashion + * they can be defined in a single level array like: [requiredFeature1, requiredFeature2]. If either of these features + * is satisfied the deeplinks would be included. To require that the features be AND'd together a second level array + * can be specified: [feature1, [feature2, feature3]] this would result in feature1 || (feature2 && feature3). To specify + * features that all must be and'd together an example would be: [[feature1, feature2]], this would result in the boolean + * operation feature1 && feature2. + * + * The final format is to specify a single feature, this would be like: features: feature1, which is the same as + * features: [feature1] + */ +type Features = FeatureKey | Array<FeatureKey | FeatureKey[]>; type SecuritySolutionDeepLink = AppDeepLink & { isPremium?: boolean; - features?: Feature[]; + features?: Features; /** * Displays deep link when feature flag is enabled. */ @@ -417,11 +439,11 @@ export const securitySolutionsDeepLinks: SecuritySolutionDeepLink[] = [ features: [FEATURE.casesRead], }, [SecurityPageName.caseConfigure]: { - features: [FEATURE.casesCrud], + features: [FEATURE.casesUpdate], isPremium: true, }, [SecurityPageName.caseCreate]: { - features: [FEATURE.casesCrud], + features: [FEATURE.casesCreate], }, }, }), @@ -525,14 +547,15 @@ export function getDeepLinks( return filterDeepLinks(securitySolutionsDeepLinks); } -function hasFeaturesCapability( - features: Feature[] | undefined, +export function hasFeaturesCapability( + features: Features | undefined, capabilities: Capabilities ): boolean { if (!features) { return true; } - return features.some((featureKey) => get(capabilities, featureKey, false)); + + return hasCapabilities(features, capabilities); } export function isPremiumLicense(licenseType?: LicenseType): boolean { diff --git a/x-pack/plugins/security_solution/public/cases/links.ts b/x-pack/plugins/security_solution/public/cases/links.ts index 4beb1c625cda1..e74ed3ca103f3 100644 --- a/x-pack/plugins/security_solution/public/cases/links.ts +++ b/x-pack/plugins/security_solution/public/cases/links.ts @@ -5,6 +5,11 @@ * 2.0. */ +import { + CREATE_CASES_CAPABILITY, + READ_CASES_CAPABILITY, + UPDATE_CASES_CAPABILITY, +} from '@kbn/cases-plugin/common'; import { getCasesDeepLinks } from '@kbn/cases-plugin/public'; import { CASES_FEATURE_ID, CASES_PATH, SecurityPageName } from '../../common/constants'; import type { LinkItem } from '../common/links/types'; @@ -16,16 +21,16 @@ export const getCasesLinkItems = (): LinkItem => { [SecurityPageName.case]: { globalNavEnabled: true, globalNavOrder: 5, - capabilities: [`${CASES_FEATURE_ID}.read_cases`], + capabilities: [`${CASES_FEATURE_ID}.${READ_CASES_CAPABILITY}`], }, [SecurityPageName.caseConfigure]: { - capabilities: [`${CASES_FEATURE_ID}.crud_cases`], + capabilities: [`${CASES_FEATURE_ID}.${UPDATE_CASES_CAPABILITY}`], licenseType: 'gold', sideNavDisabled: true, hideTimeline: true, }, [SecurityPageName.caseCreate]: { - capabilities: [`${CASES_FEATURE_ID}.crud_cases`], + capabilities: [`${CASES_FEATURE_ID}.${CREATE_CASES_CAPABILITY}`], sideNavDisabled: true, hideTimeline: true, }, diff --git a/x-pack/plugins/security_solution/public/cases/pages/index.tsx b/x-pack/plugins/security_solution/public/cases/pages/index.tsx index fc4a990c45082..155873beeee2d 100644 --- a/x-pack/plugins/security_solution/public/cases/pages/index.tsx +++ b/x-pack/plugins/security_solution/public/cases/pages/index.tsx @@ -42,8 +42,7 @@ const TimelineDetailsPanel = () => { const CaseContainerComponent: React.FC = () => { const { cases } = useKibana().services; const { getAppUrl, navigateTo } = useNavigation(); - const userPermissions = useGetUserCasesPermissions(); - const casesPermissions = { all: userPermissions.crud, read: userPermissions.read }; + const userCasesPermissions = useGetUserCasesPermissions(); const dispatch = useDispatch(); const { formatUrl: detectionsFormatUrl, search: detectionsUrlSearch } = useFormatUrl( SecurityPageName.rules @@ -145,7 +144,7 @@ const CaseContainerComponent: React.FC = () => { }, }, useFetchAlertData, - permissions: casesPermissions, + permissions: userCasesPermissions, })} </CaseDetailsRefreshContext.Provider> <SpyRoute pageName={SecurityPageName.case} /> diff --git a/x-pack/plugins/security_solution/public/cases_test_utils.ts b/x-pack/plugins/security_solution/public/cases_test_utils.ts new file mode 100644 index 0000000000000..8dd64424e41e5 --- /dev/null +++ b/x-pack/plugins/security_solution/public/cases_test_utils.ts @@ -0,0 +1,66 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +export const noCasesCapabilities = () => ({ + create_cases: false, + read_cases: false, + update_cases: false, + delete_cases: false, + push_cases: false, +}); + +export const readCasesCapabilities = () => ({ + create_cases: false, + read_cases: true, + update_cases: false, + delete_cases: false, + push_cases: false, +}); + +export const allCasesCapabilities = () => ({ + create_cases: true, + read_cases: true, + update_cases: true, + delete_cases: true, + push_cases: true, +}); + +export const noCasesPermissions = () => ({ + all: false, + create: false, + read: false, + update: false, + delete: false, + push: false, +}); + +export const readCasesPermissions = () => ({ + all: false, + create: false, + read: true, + update: false, + delete: false, + push: false, +}); + +export const writeCasesPermissions = () => ({ + all: false, + create: true, + read: false, + update: true, + delete: true, + push: true, +}); + +export const allCasesPermissions = () => ({ + all: true, + create: true, + read: true, + update: true, + delete: true, + push: true, +}); diff --git a/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.test.tsx b/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.test.tsx index c76f6f42a9e11..bea14a70a8385 100644 --- a/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.test.tsx @@ -12,6 +12,7 @@ import { TestProviders } from '../../mock'; import { useKibana as mockUseKibana } from '../../lib/kibana/__mocks__'; import { useGetUserCasesPermissions } from '../../lib/kibana'; import { RelatedCases } from './related_cases'; +import { noCasesPermissions, readCasesPermissions } from '../../../cases_test_utils'; const mockedUseKibana = mockUseKibana(); const mockGetRelatedCases = jest.fn(); @@ -42,9 +43,7 @@ const eventId = '1c84d9bff4884dabe6aa1bb15f08433463b848d9269e587078dc56669550d27 describe('Related Cases', () => { describe('When user does not have cases read permissions', () => { test('should not show related cases when user does not have permissions', () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - read: false, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(noCasesPermissions()); render( <TestProviders> <RelatedCases eventId={eventId} /> @@ -56,9 +55,7 @@ describe('Related Cases', () => { }); describe('When user does have case read permissions', () => { beforeEach(() => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - read: true, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(readCasesPermissions()); }); describe('When related cases are unable to be retrieved', () => { diff --git a/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.tsx b/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.tsx index d90688d80a86e..3d8943af1e57c 100644 --- a/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.tsx +++ b/x-pack/plugins/security_solution/public/common/components/event_details/related_cases.tsx @@ -25,11 +25,11 @@ export const RelatedCases: React.FC<Props> = React.memo(({ eventId, isReadOnly } services: { cases }, } = useKibana(); const toasts = useToasts(); - const casePermissions = useGetUserCasesPermissions(); + const userCasesPermissions = useGetUserCasesPermissions(); const [relatedCases, setRelatedCases] = useState<RelatedCaseList>([]); const [areCasesLoading, setAreCasesLoading] = useState(true); const [hasError, setHasError] = useState<boolean>(false); - const hasCasesReadPermissions = casePermissions.read; + const hasCasesReadPermissions = userCasesPermissions.read; const getRelatedCases = useCallback(async () => { let relatedCaseList: RelatedCaseList = []; diff --git a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx index 0c545ec83a6ef..86ada5a89fc20 100644 --- a/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/navigation/use_security_solution_navigation/index.test.tsx @@ -20,6 +20,12 @@ import { useIsExperimentalFeatureEnabled } from '../../../hooks/use_experimental import { TestProviders } from '../../../mock'; import { CASES_FEATURE_ID } from '../../../../../common/constants'; import { useCanSeeHostIsolationExceptionsMenu } from '../../../../management/pages/host_isolation_exceptions/view/hooks'; +import { + noCasesPermissions, + readCasesCapabilities, + readCasesPermissions, +} from '../../../../cases_test_utils'; +import { mockCasesContract } from '@kbn/cases-plugin/public/mocks'; jest.mock('../../../lib/kibana/kibana_react'); jest.mock('../../../lib/kibana'); @@ -85,8 +91,12 @@ describe('useSecuritySolutionNavigation', () => { (useRouteSpy as jest.Mock).mockReturnValue(mockRouteSpy); (useCanSeeHostIsolationExceptionsMenu as jest.Mock).mockReturnValue(true); + const cases = mockCasesContract(); + cases.helpers.getUICapabilities.mockReturnValue(readCasesPermissions()); + (useKibana as jest.Mock).mockReturnValue({ services: { + cases, application: { navigateToApp: jest.fn(), getUrlForApp: (appId: string, options?: { path?: string; deepLinkId?: boolean }) => @@ -96,7 +106,7 @@ describe('useSecuritySolutionNavigation', () => { show: true, crud: true, }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: false }, + [CASES_FEATURE_ID]: readCasesCapabilities(), }, }, chrome: { @@ -154,10 +164,7 @@ describe('useSecuritySolutionNavigation', () => { describe('Permission gated routes', () => { describe('cases', () => { it('should display the cases navigation item when the user has read permissions', () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: true, - read: true, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(readCasesPermissions()); const { result } = renderHook<{}, KibanaPageTemplateProps['solutionNav']>( () => useSecuritySolutionNavigation(), @@ -182,10 +189,7 @@ describe('useSecuritySolutionNavigation', () => { }); it('should not display the cases navigation item when the user does not have read permissions', () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: false, - read: false, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(noCasesPermissions()); const { result } = renderHook<{}, KibanaPageTemplateProps['solutionNav']>( () => useSecuritySolutionNavigation(), diff --git a/x-pack/plugins/security_solution/public/common/components/visualization_actions/index.test.tsx b/x-pack/plugins/security_solution/public/common/components/visualization_actions/index.test.tsx index 7a42615a0d771..5338856a8db42 100644 --- a/x-pack/plugins/security_solution/public/common/components/visualization_actions/index.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/visualization_actions/index.test.tsx @@ -23,6 +23,7 @@ import { cloneDeep } from 'lodash'; import { useKibana } from '../../lib/kibana/kibana_react'; import { CASES_FEATURE_ID } from '../../../../common/constants'; import { mockCasesContract } from '@kbn/cases-plugin/public/mocks'; +import { allCasesCapabilities, allCasesPermissions } from '../../../cases_test_utils'; jest.mock('react-router-dom', () => { const actual = jest.requireActual('react-router-dom'); return { @@ -70,6 +71,9 @@ describe('VisualizationActions', () => { beforeEach(() => { jest.clearAllMocks(); + const cases = mockCasesContract(); + cases.helpers.getUICapabilities.mockReturnValue(allCasesPermissions()); + (useKibana as jest.Mock).mockReturnValue({ services: { lens: { @@ -88,7 +92,7 @@ describe('VisualizationActions', () => { }, }, application: { - capabilities: { [CASES_FEATURE_ID]: { crud_cases: true, read_cases: true } }, + capabilities: { [CASES_FEATURE_ID]: allCasesCapabilities() }, getUrlForApp: jest.fn(), navigateToApp: jest.fn(), }, diff --git a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.test.tsx b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.test.tsx index 83f1290ab54e3..6204f77909f65 100644 --- a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.test.tsx @@ -9,6 +9,11 @@ import { useKibana as mockUseKibana } from '../../lib/kibana/__mocks__'; import { kpiHostMetricLensAttributes } from './lens_attributes/hosts/kpi_host_metric'; import { useAddToExistingCase } from './use_add_to_existing_case'; import { useGetUserCasesPermissions } from '../../lib/kibana'; +import { + allCasesPermissions, + readCasesPermissions, + writeCasesPermissions, +} from '../../../cases_test_utils'; const mockedUseKibana = mockUseKibana(); const mockGetUseCasesAddToExistingCaseModal = jest.fn(); @@ -41,10 +46,7 @@ describe('useAddToExistingCase', () => { }; beforeEach(() => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: true, - read: true, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(allCasesPermissions()); }); it('getUseCasesAddToExistingCaseModal with attachments', () => { @@ -62,11 +64,21 @@ describe('useAddToExistingCase', () => { expect(result.current.disabled).toEqual(false); }); - it("button disabled if user Can't Crud", () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: false, - read: true, - }); + it("disables the button if the user can't create but can read", () => { + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(readCasesPermissions()); + + const { result } = renderHook(() => + useAddToExistingCase({ + lensAttributes: kpiHostMetricLensAttributes, + timeRange, + onAddToCaseClicked: mockOnAddToCaseClicked, + }) + ); + expect(result.current.disabled).toEqual(true); + }); + + it("disables the button if the user can't read but can create", () => { + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(writeCasesPermissions()); const { result } = renderHook(() => useAddToExistingCase({ diff --git a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.tsx b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.tsx index 30626215cfd45..9aa85975a1b46 100644 --- a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.tsx +++ b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_existing_case.tsx @@ -24,7 +24,7 @@ export const useAddToExistingCase = ({ lensAttributes: LensAttributes | null; timeRange: { from: string; to: string } | null; }) => { - const userPermissions = useGetUserCasesPermissions(); + const userCasesPermissions = useGetUserCasesPermissions(); const { cases } = useKibana().services; const attachments = useMemo(() => { return [ @@ -53,6 +53,10 @@ export const useAddToExistingCase = ({ return { onAddToExistingCaseClicked, - disabled: lensAttributes == null || timeRange == null || !userPermissions.crud, + disabled: + lensAttributes == null || + timeRange == null || + !userCasesPermissions.create || + !userCasesPermissions.read, }; }; diff --git a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.test.tsx b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.test.tsx index 49fbde71386a5..6491a8ce911b1 100644 --- a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.test.tsx +++ b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.test.tsx @@ -9,6 +9,11 @@ import { useKibana as mockUseKibana } from '../../lib/kibana/__mocks__'; import { kpiHostMetricLensAttributes } from './lens_attributes/hosts/kpi_host_metric'; import { useAddToNewCase } from './use_add_to_new_case'; import { useGetUserCasesPermissions } from '../../lib/kibana'; +import { + allCasesPermissions, + readCasesPermissions, + writeCasesPermissions, +} from '../../../cases_test_utils'; jest.mock('../../lib/kibana/kibana_react'); @@ -41,10 +46,7 @@ describe('useAddToNewCase', () => { to: '2022-03-07T15:59:59.999Z', }; beforeEach(() => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: true, - read: true, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(allCasesPermissions()); }); it('getUseCasesAddToNewCaseFlyout with attachments', () => { @@ -60,11 +62,20 @@ describe('useAddToNewCase', () => { expect(result.current.disabled).toEqual(false); }); - it("button disabled if user Can't Crud", () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: false, - read: true, - }); + it("disables the button if the user can't create but can read", () => { + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(readCasesPermissions()); + + const { result } = renderHook(() => + useAddToNewCase({ + lensAttributes: kpiHostMetricLensAttributes, + timeRange, + }) + ); + expect(result.current.disabled).toEqual(true); + }); + + it("disables the button if the user can't read but can create", () => { + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(writeCasesPermissions()); const { result } = renderHook(() => useAddToNewCase({ diff --git a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.tsx b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.tsx index ac090bfde168c..a0b367738ad9b 100644 --- a/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.tsx +++ b/x-pack/plugins/security_solution/public/common/components/visualization_actions/use_add_to_new_case.tsx @@ -23,7 +23,7 @@ export interface UseAddToNewCaseProps { const owner = APP_ID; export const useAddToNewCase = ({ onClick, timeRange, lensAttributes }: UseAddToNewCaseProps) => { - const userPermissions = useGetUserCasesPermissions(); + const userCasesPermissions = useGetUserCasesPermissions(); const { cases } = useKibana().services; const attachments = useMemo(() => { return [ @@ -52,6 +52,10 @@ export const useAddToNewCase = ({ onClick, timeRange, lensAttributes }: UseAddTo return { onAddToNewCaseClicked, - disabled: lensAttributes == null || timeRange == null || !userPermissions.crud, + disabled: + lensAttributes == null || + timeRange == null || + !userCasesPermissions.create || + !userCasesPermissions.read, }; }; diff --git a/x-pack/plugins/security_solution/public/common/lib/kibana/hooks.ts b/x-pack/plugins/security_solution/public/common/lib/kibana/hooks.ts index 98f53b004c0f6..ba86bfa940294 100644 --- a/x-pack/plugins/security_solution/public/common/lib/kibana/hooks.ts +++ b/x-pack/plugins/security_solution/public/common/lib/kibana/hooks.ts @@ -14,6 +14,7 @@ import { camelCase, isArray, isObject } from 'lodash'; import { set } from '@elastic/safer-lodash-set'; import type { AuthenticatedUser } from '@kbn/security-plugin/common/model'; import type { NavigateToAppOptions } from '@kbn/core/public'; +import type { CasesPermissions } from '@kbn/cases-plugin/common/ui'; import { APP_UI_ID, CASES_FEATURE_ID, @@ -146,24 +147,37 @@ export const useCurrentUser = (): AuthenticatedElasticUser | null => { return user; }; -export interface UseGetUserCasesPermissions { - crud: boolean; - read: boolean; -} - export const useGetUserCasesPermissions = () => { - const [casesPermissions, setCasesPermissions] = useState<UseGetUserCasesPermissions>({ - crud: false, + const [casesPermissions, setCasesPermissions] = useState<CasesPermissions>({ + all: false, + create: false, read: false, + update: false, + delete: false, + push: false, }); const uiCapabilities = useKibana().services.application.capabilities; + const casesCapabilities = useKibana().services.cases.helpers.getUICapabilities( + uiCapabilities[CASES_FEATURE_ID] + ); useEffect(() => { setCasesPermissions({ - crud: !!uiCapabilities[CASES_FEATURE_ID]?.crud_cases, - read: !!uiCapabilities[CASES_FEATURE_ID]?.read_cases, + all: casesCapabilities.all, + create: casesCapabilities.create, + read: casesCapabilities.read, + update: casesCapabilities.update, + delete: casesCapabilities.delete, + push: casesCapabilities.push, }); - }, [uiCapabilities]); + }, [ + casesCapabilities.all, + casesCapabilities.create, + casesCapabilities.read, + casesCapabilities.update, + casesCapabilities.delete, + casesCapabilities.push, + ]); return casesPermissions; }; diff --git a/x-pack/plugins/security_solution/public/common/lib/kibana/kibana_react.mock.ts b/x-pack/plugins/security_solution/public/common/lib/kibana/kibana_react.mock.ts index 349889899c1a0..5629f65570f06 100644 --- a/x-pack/plugins/security_solution/public/common/lib/kibana/kibana_react.mock.ts +++ b/x-pack/plugins/security_solution/public/common/lib/kibana/kibana_react.mock.ts @@ -40,6 +40,8 @@ import { MlLocatorDefinition } from '@kbn/ml-plugin/public'; import type { EuiTheme } from '@kbn/kibana-react-plugin/common'; import { MockUrlService } from '@kbn/share-plugin/common/mocks'; import { fleetMock } from '@kbn/fleet-plugin/public/mocks'; +import { mockCasesContract } from '@kbn/cases-plugin/public/mocks'; +import { noCasesPermissions } from '../../../cases_test_utils'; import { triggersActionsUiMock } from '@kbn/triggers-actions-ui-plugin/public/mocks'; const mockUiSettings: Record<string, unknown> = { @@ -98,17 +100,13 @@ export const createStartServicesMock = ( const locator = urlService.locators.create(new MlLocatorDefinition()); const fleet = fleetMock.createStartMock(); const unifiedSearch = unifiedSearchPluginMock.createStartContract(); + const cases = mockCasesContract(); + cases.helpers.getUICapabilities.mockReturnValue(noCasesPermissions()); const triggersActionsUi = triggersActionsUiMock.createStart(); return { ...core, - cases: { - getAllCases: jest.fn(), - getCaseView: jest.fn(), - getConfigureCases: jest.fn(), - getCreateCase: jest.fn(), - getRecentCases: jest.fn(), - }, + cases, unifiedSearch, data: { ...data, diff --git a/x-pack/plugins/security_solution/public/common/links/links.test.ts b/x-pack/plugins/security_solution/public/common/links/links.test.ts index 408078dc12d78..1fe3f11b213fd 100644 --- a/x-pack/plugins/security_solution/public/common/links/links.test.ts +++ b/x-pack/plugins/security_solution/public/common/links/links.test.ts @@ -18,7 +18,9 @@ import { needsUrlState, updateAppLinks, useLinkExists, + hasCapabilities, } from './links'; +import { createCapabilities } from './test_utils'; const defaultAppLinks: AppLinkItems = [ { @@ -288,4 +290,118 @@ describe('Security app links', () => { }); }); }); + + describe('hasCapabilities', () => { + const siemShow = 'siem.show'; + const createCases = 'securitySolutionCases.create_cases'; + const readCases = 'securitySolutionCases.read_cases'; + const pushCases = 'securitySolutionCases.push_cases'; + + it('returns false when capabilities is an empty array', () => { + expect(hasCapabilities([], createCapabilities())).toBeFalsy(); + }); + + it('returns true when the capability requested is specified as a single value', () => { + expect(hasCapabilities(siemShow, createCapabilities({ siem: { show: true } }))).toBeTruthy(); + }); + + it('returns true when the capability requested is a single entry in an array', () => { + expect( + hasCapabilities([siemShow], createCapabilities({ siem: { show: true } })) + ).toBeTruthy(); + }); + + it("returns true when the capability requested is a single entry in an AND'd array format", () => { + expect( + hasCapabilities([[siemShow]], createCapabilities({ siem: { show: true } })) + ).toBeTruthy(); + }); + + it('returns true when only one requested capability is found in an OR situation', () => { + expect( + hasCapabilities( + [siemShow, createCases], + createCapabilities({ + siem: { show: true }, + securitySolutionCases: { create_cases: false }, + }) + ) + ).toBeTruthy(); + }); + + it('returns true when only the create_cases requested capability is found in an OR situation', () => { + expect( + hasCapabilities( + [siemShow, createCases], + createCapabilities({ + siem: { show: false }, + securitySolutionCases: { create_cases: true }, + }) + ) + ).toBeTruthy(); + }); + + it('returns false when none of the requested capabilities are found in an OR situation', () => { + expect( + hasCapabilities( + [readCases, createCases], + createCapabilities({ + siem: { show: true }, + securitySolutionCases: { create_cases: false }, + }) + ) + ).toBeFalsy(); + }); + + it('returns true when all of the requested capabilities are found in an AND situation', () => { + expect( + hasCapabilities( + [[readCases, createCases]], + createCapabilities({ + siem: { show: true }, + securitySolutionCases: { read_cases: true, create_cases: true }, + }) + ) + ).toBeTruthy(); + }); + + it('returns false when neither the single OR capability is found nor all of the AND capabilities', () => { + expect( + hasCapabilities( + [siemShow, [readCases, createCases]], + createCapabilities({ + siem: { show: false }, + securitySolutionCases: { read_cases: false, create_cases: true }, + }) + ) + ).toBeFalsy(); + }); + + it('returns true when the single OR capability is found when using an OR with an AND format', () => { + expect( + hasCapabilities( + [siemShow, [readCases, createCases]], + createCapabilities({ + siem: { show: true }, + securitySolutionCases: { read_cases: false, create_cases: true }, + }) + ) + ).toBeTruthy(); + }); + + it("returns false when the AND'd expressions are not satisfied", () => { + expect( + hasCapabilities( + [ + [siemShow, pushCases], + [readCases, createCases], + ], + createCapabilities({ + siem: { show: true }, + securitySolutionCases: { read_cases: false, create_cases: true, push_cases: false }, + }) + ) + ).toBeFalsy(); + }); + }); }); diff --git a/x-pack/plugins/security_solution/public/common/links/links.ts b/x-pack/plugins/security_solution/public/common/links/links.ts index 2aa2a672fc54a..de30840d02d9d 100644 --- a/x-pack/plugins/security_solution/public/common/links/links.ts +++ b/x-pack/plugins/security_solution/public/common/links/links.ts @@ -6,7 +6,7 @@ */ import type { Capabilities } from '@kbn/core/public'; -import { get } from 'lodash'; +import { get, isArray } from 'lodash'; import { useEffect, useState } from 'react'; import { BehaviorSubject } from 'rxjs'; import type { SecurityPageName } from '../../../common/constants'; @@ -173,9 +173,35 @@ const getFilteredAppLinks = ( return acc; }, []); +/** + * The format of defining features supports OR and AND mechanism. To specify features in an OR fashion + * they can be defined in a single level array like: [requiredFeature1, requiredFeature2]. If either of these features + * is satisfied the links would be included. To require that the features be AND'd together a second level array + * can be specified: [feature1, [feature2, feature3]] this would result in feature1 || (feature2 && feature3). + * + * The final format is to specify a single feature, this would be like: features: feature1, which is the same as + * features: [feature1] + */ +type LinkCapabilities = string | Array<string | string[]>; + // It checks if the user has at least one of the link capabilities needed -const hasCapabilities = (linkCapabilities: string[], userCapabilities: Capabilities): boolean => - linkCapabilities.some((linkCapability) => get(userCapabilities, linkCapability, false)); +export const hasCapabilities = <T>( + linkCapabilities: LinkCapabilities, + userCapabilities: Capabilities +): boolean => { + if (!isArray(linkCapabilities)) { + return !!get(userCapabilities, linkCapabilities, false); + } else { + return linkCapabilities.some((linkCapabilityKeyOr) => { + if (isArray(linkCapabilityKeyOr)) { + return linkCapabilityKeyOr.every((linkCapabilityKeyAnd) => + get(userCapabilities, linkCapabilityKeyAnd, false) + ); + } + return get(userCapabilities, linkCapabilityKeyOr, false); + }); + } +}; const isLinkAllowed = ( link: LinkItem, diff --git a/x-pack/plugins/security_solution/public/common/links/test_utils.ts b/x-pack/plugins/security_solution/public/common/links/test_utils.ts new file mode 100644 index 0000000000000..2643ebbb861b9 --- /dev/null +++ b/x-pack/plugins/security_solution/public/common/links/test_utils.ts @@ -0,0 +1,21 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import type { Capabilities } from '@kbn/core/public'; + +interface FeatureCap { + [key: string]: Record<string, boolean | Record<string, boolean>>; +} + +export const createCapabilities = (capabilities?: FeatureCap): Capabilities => { + return { + navLinks: {}, + management: {}, + catalogue: {}, + ...capabilities, + }; +}; diff --git a/x-pack/plugins/security_solution/public/common/links/types.ts b/x-pack/plugins/security_solution/public/common/links/types.ts index eae1c700721bc..f5432b16e9f78 100644 --- a/x-pack/plugins/security_solution/public/common/links/types.ts +++ b/x-pack/plugins/security_solution/public/common/links/types.ts @@ -38,9 +38,18 @@ export interface LinkItem { experimentalKey?: keyof ExperimentalFeatures; /** * Capabilities strings (using object dot notation) to enable the link. - * Uses "or" conditional, only one enabled capability is needed to activate the link - */ - capabilities?: string[]; + * + * The format of defining features supports OR and AND mechanism. To specify features in an OR fashion + * they can be defined in a single level array like: [requiredFeature1, requiredFeature2]. If either of these features + * is satisfied the deeplinks would be included. To require that the features be AND'd together a second level array + * can be specified: [feature1, [feature2, feature3]] this would result in feature1 || (feature2 && feature3). To specify + * features that all must be and'd together an example would be: [[feature1, feature2]], this would result in the boolean + * operation feature1 && feature2. + * + * The final format is to specify a single feature, this would be like: features: feature1, which is the same as + * features: [feature1] + */ + capabilities?: string | Array<string | string[]>; /** * Categories to display in the navigation */ diff --git a/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/alert_context_menu.test.tsx b/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/alert_context_menu.test.tsx index 919c9a3a58892..8d0ace8a3dcf5 100644 --- a/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/alert_context_menu.test.tsx +++ b/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/alert_context_menu.test.tsx @@ -63,8 +63,12 @@ jest.mock('../../../../common/lib/kibana', () => ({ }, }), useGetUserCasesPermissions: jest.fn().mockReturnValue({ - crud: true, + all: true, + create: true, read: true, + update: true, + delete: true, + push: true, }), })); diff --git a/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_add_to_case_actions.tsx b/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_add_to_case_actions.tsx index f1e337ac592c0..c8ac06cee92a0 100644 --- a/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_add_to_case_actions.tsx +++ b/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_add_to_case_actions.tsx @@ -34,8 +34,7 @@ export const useAddToCaseActions = ({ timelineId, }: UseAddToCaseActions) => { const { cases: casesUi } = useKibana().services; - const casePermissions = useGetUserCasesPermissions(); - const hasWritePermissions = casePermissions.crud; + const userCasesPermissions = useGetUserCasesPermissions(); const isAlert = useMemo(() => { return ecsData?.event?.kind?.includes('signal'); @@ -84,7 +83,8 @@ export const useAddToCaseActions = ({ TimelineId.detectionsRulesDetailsPage, TimelineId.active, ].includes(timelineId as TimelineId) && - hasWritePermissions && + userCasesPermissions.create && + userCasesPermissions.read && isAlert ) { return [ @@ -113,7 +113,8 @@ export const useAddToCaseActions = ({ ariaLabel, handleAddToExistingCaseClick, handleAddToNewCaseClick, - hasWritePermissions, + userCasesPermissions.create, + userCasesPermissions.read, timelineId, isAlert, ]); diff --git a/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_bulk_add_to_case_actions.tsx b/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_bulk_add_to_case_actions.tsx index c19f48163123e..0251c130981f6 100644 --- a/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_bulk_add_to_case_actions.tsx +++ b/x-pack/plugins/security_solution/public/detections/components/alerts_table/timeline_actions/use_bulk_add_to_case_actions.tsx @@ -19,8 +19,7 @@ export interface UseAddToCaseActions { export const useBulkAddToCaseActions = ({ onClose, onSuccess }: UseAddToCaseActions = {}) => { const { cases: casesUi } = useKibana().services; - const casePermissions = useGetUserCasesPermissions(); - const hasWritePermissions = casePermissions.crud; + const userCasesPermissions = useGetUserCasesPermissions(); const createCaseFlyout = casesUi.hooks.getUseCasesAddToNewCaseFlyout({ onClose, @@ -32,7 +31,7 @@ export const useBulkAddToCaseActions = ({ onClose, onSuccess }: UseAddToCaseActi }); return useMemo(() => { - return hasWritePermissions + return userCasesPermissions.create && userCasesPermissions.read ? [ { label: ADD_TO_NEW_CASE, @@ -58,5 +57,11 @@ export const useBulkAddToCaseActions = ({ onClose, onSuccess }: UseAddToCaseActi }, ] : []; - }, [casesUi.helpers, createCaseFlyout, hasWritePermissions, selectCaseModal]); + }, [ + casesUi.helpers, + createCaseFlyout, + userCasesPermissions.create, + userCasesPermissions.read, + selectCaseModal, + ]); }; diff --git a/x-pack/plugins/security_solution/public/detections/components/take_action_dropdown/index.test.tsx b/x-pack/plugins/security_solution/public/detections/components/take_action_dropdown/index.test.tsx index 93e268947462e..d47b9f0187e8d 100644 --- a/x-pack/plugins/security_solution/public/detections/components/take_action_dropdown/index.test.tsx +++ b/x-pack/plugins/security_solution/public/detections/components/take_action_dropdown/index.test.tsx @@ -35,6 +35,7 @@ import { } from '../../../common/utils/endpoint_alert_check'; import { HostStatus } from '../../../../common/endpoint/types'; import { getUserPrivilegesMockDefaultValue } from '../../../common/components/user_privileges/__mocks__'; +import { allCasesPermissions } from '../../../cases_test_utils'; jest.mock('../../../common/components/user_privileges'); @@ -43,7 +44,7 @@ jest.mock('../user_info', () => ({ })); jest.mock('../../../common/lib/kibana'); -(useGetUserCasesPermissions as jest.Mock).mockReturnValue({ crud: true }); +(useGetUserCasesPermissions as jest.Mock).mockReturnValue(allCasesPermissions()); jest.mock('../../containers/detection_engine/alerts/use_alerts_privileges', () => ({ useAlertsPrivileges: jest.fn().mockReturnValue({ hasIndexWrite: true, hasKibanaCRUD: true }), diff --git a/x-pack/plugins/security_solution/public/helpers.test.tsx b/x-pack/plugins/security_solution/public/helpers.test.tsx index c9895da6753d9..fa244184b454e 100644 --- a/x-pack/plugins/security_solution/public/helpers.test.tsx +++ b/x-pack/plugins/security_solution/public/helpers.test.tsx @@ -18,6 +18,11 @@ import { getField, } from './helpers'; import type { StartedSubPlugins } from './types'; +import { + allCasesCapabilities, + noCasesCapabilities, + readCasesCapabilities, +} from './cases_test_utils'; describe('public helpers parseRoute', () => { it('should properly parse hash route', () => { @@ -76,7 +81,7 @@ describe('#getSubPluginRoutesByCapabilities', () => { it('cases routes should return NoPrivilegesPage component when cases plugin is NOT available ', () => { const routes = getSubPluginRoutesByCapabilities(mockSubPlugins, { [SERVER_APP_ID]: { show: true, crud: false }, - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: noCasesCapabilities(), } as unknown as Capabilities); const casesRoute = routes.find((r) => r.path === 'cases'); // eslint-disable-next-line @typescript-eslint/no-explicit-any @@ -91,7 +96,7 @@ describe('#getSubPluginRoutesByCapabilities', () => { it('alerts should return NoPrivilegesPage component when siem plugin is NOT available ', () => { const routes = getSubPluginRoutesByCapabilities(mockSubPlugins, { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: false }, + [CASES_FEATURE_ID]: readCasesCapabilities(), } as unknown as Capabilities); const alertsRoute = routes.find((r) => r.path === 'alerts'); // eslint-disable-next-line @typescript-eslint/no-explicit-any @@ -106,7 +111,7 @@ describe('#getSubPluginRoutesByCapabilities', () => { it('should return NoPrivilegesPage for each route when both plugins are NOT available ', () => { const routes = getSubPluginRoutesByCapabilities(mockSubPlugins, { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: noCasesCapabilities(), } as unknown as Capabilities); const casesRoute = routes.find((r) => r.path === 'cases'); // eslint-disable-next-line @typescript-eslint/no-explicit-any @@ -134,7 +139,7 @@ describe('#isSubPluginAvailable', () => { expect( isSubPluginAvailable('pluginKey', { [SERVER_APP_ID]: { show: true, crud: true }, - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: noCasesCapabilities(), } as unknown as Capabilities) ).toBeTruthy(); }); @@ -143,7 +148,7 @@ describe('#isSubPluginAvailable', () => { expect( isSubPluginAvailable('pluginKey', { [SERVER_APP_ID]: { show: true, crud: false }, - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: noCasesCapabilities(), } as unknown as Capabilities) ).toBeTruthy(); }); @@ -152,7 +157,7 @@ describe('#isSubPluginAvailable', () => { expect( isSubPluginAvailable('pluginKey', { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: noCasesCapabilities(), } as unknown as Capabilities) ).toBeFalsy(); }); @@ -161,7 +166,7 @@ describe('#isSubPluginAvailable', () => { expect( isSubPluginAvailable('cases', { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: true }, + [CASES_FEATURE_ID]: allCasesCapabilities(), } as unknown as Capabilities) ).toBeTruthy(); }); @@ -170,7 +175,7 @@ describe('#isSubPluginAvailable', () => { expect( isSubPluginAvailable('cases', { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: false }, + [CASES_FEATURE_ID]: readCasesCapabilities(), } as unknown as Capabilities) ).toBeTruthy(); }); @@ -179,7 +184,7 @@ describe('#isSubPluginAvailable', () => { expect( isSubPluginAvailable('pluginKey', { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: noCasesCapabilities(), } as unknown as Capabilities) ).toBeFalsy(); }); @@ -189,7 +194,7 @@ describe('RedirectRoute', () => { it('RedirectRoute should redirect to overview page when siem and case privileges are all', () => { const mockCapabilitities = { [SERVER_APP_ID]: { show: true, crud: true }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: true }, + [CASES_FEATURE_ID]: allCasesCapabilities(), } as unknown as Capabilities; expect(shallow(<RedirectRoute capabilities={mockCapabilitities} />)).toMatchInlineSnapshot(` <Redirect @@ -201,7 +206,7 @@ describe('RedirectRoute', () => { it('RedirectRoute should redirect to overview page when siem and case privileges are read', () => { const mockCapabilitities = { [SERVER_APP_ID]: { show: true, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: false }, + [CASES_FEATURE_ID]: readCasesCapabilities(), } as unknown as Capabilities; expect(shallow(<RedirectRoute capabilities={mockCapabilitities} />)).toMatchInlineSnapshot(` <Redirect @@ -213,7 +218,7 @@ describe('RedirectRoute', () => { it('RedirectRoute should redirect to overview page when siem and case privileges are off', () => { const mockCapabilitities = { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: false, crud_cases: false }, + [CASES_FEATURE_ID]: noCasesCapabilities(), } as unknown as Capabilities; expect(shallow(<RedirectRoute capabilities={mockCapabilitities} />)).toMatchInlineSnapshot(` <Redirect @@ -225,7 +230,7 @@ describe('RedirectRoute', () => { it('RedirectRoute should redirect to overview page when siem privilege is read and case privilege is all', () => { const mockCapabilitities = { [SERVER_APP_ID]: { show: true, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: true }, + [CASES_FEATURE_ID]: allCasesCapabilities(), } as unknown as Capabilities; expect(shallow(<RedirectRoute capabilities={mockCapabilitities} />)).toMatchInlineSnapshot(` <Redirect @@ -237,7 +242,7 @@ describe('RedirectRoute', () => { it('RedirectRoute should redirect to overview page when siem privilege is read and case privilege is read', () => { const mockCapabilitities = { [SERVER_APP_ID]: { show: true, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: true }, + [CASES_FEATURE_ID]: allCasesCapabilities(), } as unknown as Capabilities; expect(shallow(<RedirectRoute capabilities={mockCapabilitities} />)).toMatchInlineSnapshot(` <Redirect @@ -249,7 +254,7 @@ describe('RedirectRoute', () => { it('RedirectRoute should redirect to cases page when siem privilege is none and case privilege is read', () => { const mockCapabilitities = { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: false }, + [CASES_FEATURE_ID]: readCasesCapabilities(), } as unknown as Capabilities; expect(shallow(<RedirectRoute capabilities={mockCapabilitities} />)).toMatchInlineSnapshot(` <Redirect @@ -261,7 +266,7 @@ describe('RedirectRoute', () => { it('RedirectRoute should redirect to cases page when siem privilege is none and case privilege is all', () => { const mockCapabilitities = { [SERVER_APP_ID]: { show: false, crud: false }, - [CASES_FEATURE_ID]: { read_cases: true, crud_cases: true }, + [CASES_FEATURE_ID]: allCasesCapabilities(), } as unknown as Capabilities; expect(shallow(<RedirectRoute capabilities={mockCapabilitities} />)).toMatchInlineSnapshot(` <Redirect diff --git a/x-pack/plugins/security_solution/public/overview/components/recent_cases/index.tsx b/x-pack/plugins/security_solution/public/overview/components/recent_cases/index.tsx index 4e40832a2d718..5e75ed3643a71 100644 --- a/x-pack/plugins/security_solution/public/overview/components/recent_cases/index.tsx +++ b/x-pack/plugins/security_solution/public/overview/components/recent_cases/index.tsx @@ -14,11 +14,10 @@ const MAX_CASES_TO_SHOW = 3; const RecentCasesComponent = () => { const { cases } = useKibana().services; - const permissions = useGetUserCasesPermissions(); - const casesPermissions = { all: permissions.crud, read: permissions.read }; + const userCasesPermissions = useGetUserCasesPermissions(); return cases.ui.getRecentCases({ - permissions: casesPermissions, + permissions: userCasesPermissions, maxCasesToShow: MAX_CASES_TO_SHOW, owner: [APP_ID], }); diff --git a/x-pack/plugins/security_solution/public/overview/components/sidebar/sidebar.test.tsx b/x-pack/plugins/security_solution/public/overview/components/sidebar/sidebar.test.tsx index 757f9fc5aa5f2..692ffd0b44ec8 100644 --- a/x-pack/plugins/security_solution/public/overview/components/sidebar/sidebar.test.tsx +++ b/x-pack/plugins/security_solution/public/overview/components/sidebar/sidebar.test.tsx @@ -13,6 +13,7 @@ import { Sidebar } from './sidebar'; import { useGetUserCasesPermissions, useKibana } from '../../../common/lib/kibana'; import type { CaseUiClientMock } from '@kbn/cases-plugin/public/mocks'; import { casesPluginMock } from '@kbn/cases-plugin/public/mocks'; +import { noCasesPermissions, readCasesPermissions } from '../../../cases_test_utils'; jest.mock('../../../common/lib/kibana'); @@ -37,10 +38,7 @@ describe('Sidebar', () => { }); it('does not render the recently created cases section when the user does not have read permissions', async () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: false, - read: false, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(noCasesPermissions()); await waitFor(() => mount( @@ -54,10 +52,7 @@ describe('Sidebar', () => { }); it('does render the recently created cases section when the user has read permissions', async () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: false, - read: true, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(readCasesPermissions()); await waitFor(() => mount( diff --git a/x-pack/plugins/security_solution/public/overview/pages/detection_response.test.tsx b/x-pack/plugins/security_solution/public/overview/pages/detection_response.test.tsx index 3b88d22eb4da9..6d6c4965b7ec1 100644 --- a/x-pack/plugins/security_solution/public/overview/pages/detection_response.test.tsx +++ b/x-pack/plugins/security_solution/public/overview/pages/detection_response.test.tsx @@ -10,6 +10,7 @@ import { MemoryRouter } from 'react-router-dom'; import { render } from '@testing-library/react'; import { DetectionResponse } from './detection_response'; import { TestProviders } from '../../common/mock'; +import { noCasesPermissions, readCasesPermissions } from '../../cases_test_utils'; jest.mock('../components/detection_response/alerts_by_status', () => ({ AlertsByStatus: () => <div data-test-subj="mock_AlertsByStatus" />, @@ -67,7 +68,7 @@ jest.mock('../../detections/containers/detection_engine/alerts/use_alerts_privil useAlertsPrivileges: () => mockUseAlertsPrivileges(), })); -const defaultUseCasesPermissionsReturn = { read: true }; +const defaultUseCasesPermissionsReturn = readCasesPermissions(); const mockUseCasesPermissions = jest.fn(() => defaultUseCasesPermissionsReturn); jest.mock('../../common/lib/kibana/hooks', () => { const original = jest.requireActual('../../common/lib/kibana/hooks'); @@ -189,8 +190,8 @@ describe('DetectionResponse', () => { expect(result.queryByTestId('mock_AlertsByStatus')).not.toBeInTheDocument(); }); - it('should not render cases data sections if user has not cases read permission', () => { - mockUseCasesPermissions.mockReturnValue({ read: false }); + it('should not render cases data sections if the user does not have cases read permission', () => { + mockUseCasesPermissions.mockReturnValue(noCasesPermissions()); const result = render( <TestProviders> @@ -210,8 +211,8 @@ describe('DetectionResponse', () => { expect(result.queryByTestId('mock_AlertsByStatus')).toBeInTheDocument(); }); - it('should render page permissions message if user has any read permission', () => { - mockUseCasesPermissions.mockReturnValue({ read: false }); + it('should render page permissions message if the user does not have read permission', () => { + mockUseCasesPermissions.mockReturnValue(noCasesPermissions()); mockUseAlertsPrivileges.mockReturnValue({ hasKibanaREAD: true, hasIndexRead: false, diff --git a/x-pack/plugins/security_solution/public/timelines/components/flyout/add_to_case_button/index.tsx b/x-pack/plugins/security_solution/public/timelines/components/flyout/add_to_case_button/index.tsx index 41f7d298eaa61..bc104ad70f1f1 100644 --- a/x-pack/plugins/security_solution/public/timelines/components/flyout/add_to_case_button/index.tsx +++ b/x-pack/plugins/security_solution/public/timelines/components/flyout/add_to_case_button/index.tsx @@ -67,8 +67,7 @@ const AddToCaseButtonComponent: React.FC<Props> = ({ timelineId }) => { [dispatch, graphEventId, navigateToApp, savedObjectId, timelineId, timelineTitle] ); - const userPermissions = useGetUserCasesPermissions(); - const casesPermissions = { all: userPermissions.crud, read: userPermissions.read }; + const userCasesPermissions = useGetUserCasesPermissions(); const handleButtonClick = useCallback(() => { setPopover((currentIsOpen) => !currentIsOpen); @@ -165,7 +164,7 @@ const AddToCaseButtonComponent: React.FC<Props> = ({ timelineId }) => { cases.ui.getAllCasesSelectorModal({ onRowClick, owner: [APP_ID], - permissions: casesPermissions, + permissions: userCasesPermissions, })} </> ); diff --git a/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.test.tsx b/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.test.tsx index 8906bff912d68..42306a7d3d205 100644 --- a/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.test.tsx +++ b/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.test.tsx @@ -16,6 +16,7 @@ import { FlyoutHeader } from '.'; import { useSourcererDataView } from '../../../../common/containers/sourcerer'; import { mockBrowserFields, mockDocValueFields } from '../../../../common/containers/source/mock'; import { getEmptyValue } from '../../../../common/components/empty_value'; +import { allCasesPermissions, readCasesPermissions } from '../../../../cases_test_utils'; const mockUseSourcererDataView: jest.Mock = useSourcererDataView as jest.Mock; jest.mock('../../../../common/containers/sourcerer'); @@ -78,11 +79,8 @@ describe('header', () => { mockUseTimelineKpis.mockReturnValue([false, mockUseTimelineKpiResponse]); }); - it('renders the button when the user has write permissions', () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: true, - read: false, - }); + it('renders the button when the user has create and read permissions', () => { + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(allCasesPermissions()); render( <TestProviders> @@ -93,11 +91,8 @@ describe('header', () => { expect(screen.getByTestId('attach-timeline-case-button')).toBeInTheDocument(); }); - it('does not render the button when the user does not have write permissions', () => { - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: false, - read: false, - }); + it('does not render the button when the user does not have create permissions', () => { + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(readCasesPermissions()); render( <TestProviders> diff --git a/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.tsx b/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.tsx index 3541af9fcb7ca..4dc62c43e7f1e 100644 --- a/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.tsx +++ b/x-pack/plugins/security_solution/public/timelines/components/flyout/header/index.tsx @@ -415,7 +415,7 @@ const FlyoutHeaderComponent: React.FC<FlyoutHeaderProps> = ({ timelineId }) => { filterQuery: combinedQueries?.filterQuery ?? '', }); - const hasWritePermissions = useGetUserCasesPermissions()?.crud ?? false; + const userCasesPermissions = useGetUserCasesPermissions(); return ( <StyledTimelineHeader alignItems="center" gutterSize="s"> @@ -448,7 +448,7 @@ const FlyoutHeaderComponent: React.FC<FlyoutHeaderProps> = ({ timelineId }) => { <EuiFlexItem grow={false}> <AddToFavoritesButton timelineId={timelineId} /> </EuiFlexItem> - {hasWritePermissions && ( + {userCasesPermissions.create && userCasesPermissions.read && ( <EuiFlexItem grow={false}> <AddToCaseButton timelineId={timelineId} /> </EuiFlexItem> diff --git a/x-pack/plugins/security_solution/public/timelines/components/flyout/pane/index.test.tsx b/x-pack/plugins/security_solution/public/timelines/components/flyout/pane/index.test.tsx index ba965cd7ad3d4..1eb8839ee3672 100644 --- a/x-pack/plugins/security_solution/public/timelines/components/flyout/pane/index.test.tsx +++ b/x-pack/plugins/security_solution/public/timelines/components/flyout/pane/index.test.tsx @@ -11,8 +11,16 @@ import React from 'react'; import { TestProviders } from '../../../../common/mock'; import { TimelineId } from '../../../../../common/types/timeline'; import { Pane } from '.'; +import { useGetUserCasesPermissions } from '../../../../common/lib/kibana'; jest.mock('../../../../common/lib/kibana'); +const originalKibanaLib = jest.requireActual('../../../../common/lib/kibana'); + +// Restore the useGetUserCasesPermissions so the calling functions can receive a valid permissions object +// The returned permissions object will indicate that the user does not have permissions by default +const mockUseGetUserCasesPermissions = useGetUserCasesPermissions as jest.Mock; +mockUseGetUserCasesPermissions.mockImplementation(originalKibanaLib.useGetUserCasesPermissions); + jest.mock('../../../../common/components/url_state/normalize_time_range'); jest.mock('../../../../common/hooks/use_resolve_conflict', () => { diff --git a/x-pack/plugins/security_solution/public/timelines/components/side_panel/event_details/index.test.tsx b/x-pack/plugins/security_solution/public/timelines/components/side_panel/event_details/index.test.tsx index e99072a759949..2e69985258247 100644 --- a/x-pack/plugins/security_solution/public/timelines/components/side_panel/event_details/index.test.tsx +++ b/x-pack/plugins/security_solution/public/timelines/components/side_panel/event_details/index.test.tsx @@ -21,6 +21,7 @@ import { import { mockBrowserFields, mockRuntimeMappings } from '../../../../common/containers/source/mock'; import { coreMock } from '@kbn/core/public/mocks'; import { mockCasesContext } from '@kbn/cases-plugin/public/mocks/mock_cases_context'; +import { allCasesPermissions } from '../../../../cases_test_utils'; const ecsData: Ecs = { _id: '1', @@ -138,10 +139,7 @@ describe('event details footer component', () => { }, }, }); - (useGetUserCasesPermissions as jest.Mock).mockReturnValue({ - crud: true, - read: true, - }); + (useGetUserCasesPermissions as jest.Mock).mockReturnValue(allCasesPermissions()); }); afterEach(() => { jest.clearAllMocks(); diff --git a/x-pack/plugins/security_solution/public/timelines/components/timeline/index.test.tsx b/x-pack/plugins/security_solution/public/timelines/components/timeline/index.test.tsx index a9d3f8c31b0a0..c34ace14f91a4 100644 --- a/x-pack/plugins/security_solution/public/timelines/components/timeline/index.test.tsx +++ b/x-pack/plugins/security_solution/public/timelines/components/timeline/index.test.tsx @@ -32,6 +32,7 @@ import { defaultRowRenderers } from './body/renderers'; import { useSourcererDataView } from '../../../common/containers/sourcerer'; import { createStore } from '../../../common/store'; import { SourcererScopeName } from '../../../common/store/sourcerer/model'; +import { useGetUserCasesPermissions } from '../../../common/lib/kibana'; jest.mock('../../containers', () => ({ useTimelineEvents: jest.fn(), @@ -40,6 +41,13 @@ jest.mock('../../containers', () => ({ jest.mock('./tabs_content'); jest.mock('../../../common/lib/kibana'); +const originalKibanaLib = jest.requireActual('../../../common/lib/kibana'); + +// Restore the useGetUserCasesPermissions so the calling functions can receive a valid permissions object +// The returned permissions object will indicate that the user does not have permissions by default +const mockUseGetUserCasesPermissions = useGetUserCasesPermissions as jest.Mock; +mockUseGetUserCasesPermissions.mockImplementation(originalKibanaLib.useGetUserCasesPermissions); + jest.mock('../../../common/components/url_state/normalize_time_range'); jest.mock('@kbn/i18n-react', () => { const originalModule = jest.requireActual('@kbn/i18n-react'); diff --git a/x-pack/plugins/security_solution/server/features.ts b/x-pack/plugins/security_solution/server/features.ts index 96ae8497ad19d..4da85d9fe540a 100644 --- a/x-pack/plugins/security_solution/server/features.ts +++ b/x-pack/plugins/security_solution/server/features.ts @@ -10,48 +10,89 @@ import { i18n } from '@kbn/i18n'; import type { KibanaFeatureConfig, SubFeatureConfig } from '@kbn/features-plugin/common'; import { DEFAULT_APP_CATEGORIES } from '@kbn/core/server'; import { DATA_VIEW_SAVED_OBJECT_TYPE } from '@kbn/data-views-plugin/common'; +import { createUICapabilities } from '@kbn/cases-plugin/common'; import { APP_ID, CASES_FEATURE_ID, SERVER_APP_ID } from '../common/constants'; import { savedObjectTypes } from './saved_objects'; -export const getCasesKibanaFeature = (): KibanaFeatureConfig => ({ - id: CASES_FEATURE_ID, - name: i18n.translate('xpack.securitySolution.featureRegistry.linkSecuritySolutionCaseTitle', { - defaultMessage: 'Cases', - }), - order: 1100, - category: DEFAULT_APP_CATEGORIES.security, - app: [CASES_FEATURE_ID, 'kibana'], - catalogue: [APP_ID], - cases: [APP_ID], - privileges: { - all: { - app: [CASES_FEATURE_ID, 'kibana'], - catalogue: [APP_ID], - cases: { - all: [APP_ID], +export const getCasesKibanaFeature = (): KibanaFeatureConfig => { + const casesCapabilities = createUICapabilities(); + + return { + id: CASES_FEATURE_ID, + name: i18n.translate('xpack.securitySolution.featureRegistry.linkSecuritySolutionCaseTitle', { + defaultMessage: 'Cases', + }), + order: 1100, + category: DEFAULT_APP_CATEGORIES.security, + app: [CASES_FEATURE_ID, 'kibana'], + catalogue: [APP_ID], + cases: [APP_ID], + privileges: { + all: { + app: [CASES_FEATURE_ID, 'kibana'], + catalogue: [APP_ID], + cases: { + create: [APP_ID], + read: [APP_ID], + update: [APP_ID], + push: [APP_ID], + }, + api: [], + savedObject: { + all: [], + read: [], + }, + ui: casesCapabilities.all, }, - api: [], - savedObject: { - all: [], - read: [], + read: { + app: [CASES_FEATURE_ID, 'kibana'], + catalogue: [APP_ID], + cases: { + read: [APP_ID], + }, + api: [], + savedObject: { + all: [], + read: [], + }, + ui: casesCapabilities.read, }, - ui: ['crud_cases', 'read_cases'], // uiCapabilities[CASES_FEATURE_ID].crud_cases or read_cases }, - read: { - app: [CASES_FEATURE_ID, 'kibana'], - catalogue: [APP_ID], - cases: { - read: [APP_ID], - }, - api: [], - savedObject: { - all: [], - read: [], + subFeatures: [ + { + name: i18n.translate('xpack.securitySolution.featureRegistry.deleteSubFeatureName', { + defaultMessage: 'Delete', + }), + privilegeGroups: [ + { + groupType: 'independent', + privileges: [ + { + api: [], + id: 'cases_delete', + name: i18n.translate( + 'xpack.securitySolution.featureRegistry.deleteSubFeatureDetails', + { + defaultMessage: 'Delete cases and comments', + } + ), + includeIn: 'all', + savedObject: { + all: [], + read: [], + }, + cases: { + delete: [APP_ID], + }, + ui: casesCapabilities.delete, + }, + ], + }, + ], }, - ui: ['read_cases'], // uiCapabilities[CASES_FEATURE_ID].read_cases - }, - }, -}); + ], + }; +}; export const getAlertsSubFeature = (ruleTypes: string[]): SubFeatureConfig => ({ name: i18n.translate('xpack.securitySolution.featureRegistry.manageAlertsName', { diff --git a/x-pack/test/api_integration/apis/cases/common/roles.ts b/x-pack/test/api_integration/apis/cases/common/roles.ts new file mode 100644 index 0000000000000..96393dfa6c423 --- /dev/null +++ b/x-pack/test/api_integration/apis/cases/common/roles.ts @@ -0,0 +1,405 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { Role } from '../../../../cases_api_integration/common/lib/authentication/types'; + +/** + * Roles for Cases in Security Solution + */ + +export const secAllCasesOnlyDelete: Role = { + name: 'sec_all_cases_only_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['all'], + securitySolutionCases: ['cases_delete'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secAllCasesNoDelete: Role = { + name: 'sec_all_cases_no_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['all'], + securitySolutionCases: ['minimal_all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secAll: Role = { + name: 'sec_all_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['all'], + securitySolutionCases: ['all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secAllCasesRead: Role = { + name: 'sec_all_cases_read_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['all'], + securitySolutionCases: ['read'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secAllCasesNone: Role = { + name: 'sec_all_cases_none_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secReadCasesAll: Role = { + name: 'sec_read_cases_all_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['read'], + securitySolutionCases: ['all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secReadCasesRead: Role = { + name: 'sec_read_cases_read_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['read'], + securitySolutionCases: ['read'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secRead: Role = { + name: 'sec_read_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['read'], + securitySolutionCases: ['read'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const secReadCasesNone: Role = { + name: 'sec_read_cases_none_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + siem: ['read'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +/** + * Roles for Cases in the stack + */ + +export const casesOnlyDelete: Role = { + name: 'cases_only_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + generalCases: ['cases_delete'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const casesNoDelete: Role = { + name: 'cases_no_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + generalCases: ['minimal_all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const casesAll: Role = { + name: 'cases_all_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + generalCases: ['all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +/** + * Roles for Cases in Observability + */ + +export const obsCasesOnlyDelete: Role = { + name: 'obs_cases_only_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + observabilityCases: ['cases_delete'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const obsCasesNoDelete: Role = { + name: 'obs_cases_no_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + observabilityCases: ['minimal_all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const obsCasesAll: Role = { + name: 'obs_cases_all_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + observabilityCases: ['all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const roles = [ + secAllCasesOnlyDelete, + secAllCasesNoDelete, + secAll, + secAllCasesRead, + secAllCasesNone, + secReadCasesAll, + secReadCasesRead, + secReadCasesNone, + secRead, + casesOnlyDelete, + casesNoDelete, + casesAll, + obsCasesOnlyDelete, + obsCasesNoDelete, + obsCasesAll, +]; diff --git a/x-pack/test/api_integration/apis/cases/common/users.ts b/x-pack/test/api_integration/apis/cases/common/users.ts new file mode 100644 index 0000000000000..13e36f16fde10 --- /dev/null +++ b/x-pack/test/api_integration/apis/cases/common/users.ts @@ -0,0 +1,151 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { User } from '../../../../cases_api_integration/common/lib/authentication/types'; +import { + casesAll, + casesNoDelete, + casesOnlyDelete, + obsCasesAll, + obsCasesNoDelete, + obsCasesOnlyDelete, + secAll, + secAllCasesNoDelete, + secAllCasesNone, + secAllCasesOnlyDelete, + secAllCasesRead, + secRead, + secReadCasesAll, + secReadCasesNone, + secReadCasesRead, +} from './roles'; + +/** + * Users for Cases in Security Solution + */ + +export const secAllCasesOnlyDeleteUser: User = { + username: 'sec_all_cases_only_delete_user', + password: 'password', + roles: [secAllCasesOnlyDelete.name], +}; + +export const secAllCasesNoDeleteUser: User = { + username: 'sec_all_cases_no_delete_user', + password: 'password', + roles: [secAllCasesNoDelete.name], +}; + +export const secAllUser: User = { + username: 'sec_all_user', + password: 'password', + roles: [secAll.name], +}; + +export const secAllCasesReadUser: User = { + username: 'sec_all_cases_read_user', + password: 'password', + roles: [secAllCasesRead.name], +}; + +export const secAllCasesNoneUser: User = { + username: 'sec_all_cases_none_user', + password: 'password', + roles: [secAllCasesNone.name], +}; + +export const secReadCasesAllUser: User = { + username: 'sec_read_cases_all_user', + password: 'password', + roles: [secReadCasesAll.name], +}; + +export const secReadCasesReadUser: User = { + username: 'sec_read_cases_read_user', + password: 'password', + roles: [secReadCasesRead.name], +}; + +export const secReadUser: User = { + username: 'sec_read_user', + password: 'password', + roles: [secRead.name], +}; + +export const secReadCasesNoneUser: User = { + username: 'sec_read_cases_none_user', + password: 'password', + roles: [secReadCasesNone.name], +}; + +/** + * Users for Cases in the Stack + */ + +export const casesOnlyDeleteUser: User = { + username: 'cases_only_delete_user', + password: 'password', + roles: [casesOnlyDelete.name], +}; + +export const casesNoDeleteUser: User = { + username: 'cases_no_delete_user', + password: 'password', + roles: [casesNoDelete.name], +}; + +export const casesAllUser: User = { + username: 'cases_all_user', + password: 'password', + roles: [casesAll.name], +}; + +/** + * Users for Cases in Observability + */ + +export const obsCasesOnlyDeleteUser: User = { + username: 'obs_cases_only_delete_user', + password: 'password', + roles: [obsCasesOnlyDelete.name], +}; + +export const obsCasesNoDeleteUser: User = { + username: 'obs_cases_no_delete_user', + password: 'password', + roles: [obsCasesNoDelete.name], +}; + +export const obsCasesAllUser: User = { + username: 'obs_cases_all_user', + password: 'password', + roles: [obsCasesAll.name], +}; + +export const users = [ + secAllCasesOnlyDeleteUser, + secAllCasesNoDeleteUser, + secAllUser, + secAllCasesReadUser, + secAllCasesNoneUser, + secReadCasesAllUser, + secReadCasesReadUser, + secReadUser, + secReadCasesNoneUser, + casesOnlyDeleteUser, + casesNoDeleteUser, + casesAllUser, + obsCasesOnlyDeleteUser, + obsCasesNoDeleteUser, + obsCasesAllUser, +]; diff --git a/x-pack/test/api_integration/apis/cases/index.ts b/x-pack/test/api_integration/apis/cases/index.ts new file mode 100644 index 0000000000000..3ec21e4d1cce1 --- /dev/null +++ b/x-pack/test/api_integration/apis/cases/index.ts @@ -0,0 +1,14 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { FtrProviderContext } from '../../ftr_provider_context'; + +export default function ({ loadTestFile }: FtrProviderContext) { + describe('cases', function () { + loadTestFile(require.resolve('./privileges')); + }); +} diff --git a/x-pack/test/api_integration/apis/cases/privileges.ts b/x-pack/test/api_integration/apis/cases/privileges.ts new file mode 100644 index 0000000000000..7279e89c9b167 --- /dev/null +++ b/x-pack/test/api_integration/apis/cases/privileges.ts @@ -0,0 +1,178 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import expect from '@kbn/expect'; +import { APP_ID as CASES_APP_ID } from '@kbn/cases-plugin/common/constants'; +import { APP_ID as SECURITY_SOLUTION_APP_ID } from '@kbn/security-solution-plugin/common/constants'; +import { observabilityFeatureId as OBSERVABILITY_APP_ID } from '@kbn/observability-plugin/common'; +import { FtrProviderContext } from '../../ftr_provider_context'; +import { + createUsersAndRoles, + deleteUsersAndRoles, +} from '../../../cases_api_integration/common/lib/authentication'; + +import { + createCase, + deleteAllCaseItems, + deleteCases, + getCase, +} from '../../../cases_api_integration/common/lib/utils'; +import { + casesAllUser, + casesNoDeleteUser, + casesOnlyDeleteUser, + obsCasesAllUser, + obsCasesNoDeleteUser, + obsCasesOnlyDeleteUser, + secAllCasesNoDeleteUser, + secAllCasesNoneUser, + secAllCasesOnlyDeleteUser, + secAllCasesReadUser, + secAllUser, + secReadCasesAllUser, + secReadCasesNoneUser, + secReadCasesReadUser, + secReadUser, + users, +} from './common/users'; +import { roles } from './common/roles'; +import { getPostCaseRequest } from '../../../cases_api_integration/common/lib/mock'; + +export default ({ getService }: FtrProviderContext): void => { + describe('feature privilege', () => { + const es = getService('es'); + const supertestWithoutAuth = getService('supertestWithoutAuth'); + const supertest = getService('supertest'); + + before(async () => { + await createUsersAndRoles(getService, users, roles); + }); + + after(async () => { + await deleteUsersAndRoles(getService, users, roles); + }); + + afterEach(async () => { + await deleteAllCaseItems(es); + }); + + for (const { user, owner } of [ + { user: secAllUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadCasesAllUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: casesAllUser, owner: CASES_APP_ID }, + { user: casesNoDeleteUser, owner: CASES_APP_ID }, + { user: obsCasesAllUser, owner: OBSERVABILITY_APP_ID }, + { user: obsCasesNoDeleteUser, owner: OBSERVABILITY_APP_ID }, + ]) { + it(`User ${user.username} with role(s) ${user.roles.join()} can create a case`, async () => { + await createCase(supertestWithoutAuth, getPostCaseRequest({ owner }), 200, { + user, + space: null, + }); + }); + } + + for (const { user, owner } of [ + { user: secAllCasesReadUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadCasesAllUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadCasesReadUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: casesAllUser, owner: CASES_APP_ID }, + { user: casesNoDeleteUser, owner: CASES_APP_ID }, + { user: obsCasesAllUser, owner: OBSERVABILITY_APP_ID }, + { user: obsCasesNoDeleteUser, owner: OBSERVABILITY_APP_ID }, + ]) { + it(`User ${user.username} with role(s) ${user.roles.join()} can get a case`, async () => { + const caseInfo = await createCase(supertest, getPostCaseRequest({ owner })); + const retrievedCase = await getCase({ + supertest: supertestWithoutAuth, + caseId: caseInfo.id, + expectedHttpCode: 200, + auth: { user, space: null }, + }); + + expect(caseInfo.owner).to.eql(retrievedCase.owner); + }); + } + + for (const { user, owner } of [ + { user: secAllCasesReadUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secAllCasesNoneUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadCasesReadUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadCasesNoneUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: casesOnlyDeleteUser, owner: CASES_APP_ID }, + { user: obsCasesOnlyDeleteUser, owner: OBSERVABILITY_APP_ID }, + ]) { + it(`User ${ + user.username + } with role(s) ${user.roles.join()} cannot create a case`, async () => { + await createCase(supertestWithoutAuth, getPostCaseRequest({ owner }), 403, { + user, + space: null, + }); + }); + } + + for (const { user, owner } of [ + { user: secAllCasesNoneUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secReadCasesNoneUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secAllCasesOnlyDeleteUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: casesOnlyDeleteUser, owner: CASES_APP_ID }, + { user: obsCasesOnlyDeleteUser, owner: OBSERVABILITY_APP_ID }, + ]) { + it(`User ${user.username} with role(s) ${user.roles.join()} cannot get a case`, async () => { + const caseInfo = await createCase(supertest, getPostCaseRequest({ owner })); + + await getCase({ + supertest: supertestWithoutAuth, + caseId: caseInfo.id, + expectedHttpCode: 403, + auth: { user, space: null }, + }); + }); + } + + for (const { user, owner } of [ + { user: secAllUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secAllCasesOnlyDeleteUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: casesAllUser, owner: CASES_APP_ID }, + { user: casesOnlyDeleteUser, owner: CASES_APP_ID }, + { user: obsCasesAllUser, owner: OBSERVABILITY_APP_ID }, + { user: obsCasesOnlyDeleteUser, owner: OBSERVABILITY_APP_ID }, + ]) { + it(`User ${user.username} with role(s) ${user.roles.join()} can delete a case`, async () => { + const caseInfo = await createCase(supertest, getPostCaseRequest({ owner })); + await deleteCases({ + caseIDs: [caseInfo.id], + supertest: supertestWithoutAuth, + expectedHttpCode: 204, + auth: { user, space: null }, + }); + }); + } + + for (const { user, owner } of [ + { user: secAllCasesReadUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: secAllCasesNoDeleteUser, owner: SECURITY_SOLUTION_APP_ID }, + { user: casesNoDeleteUser, owner: CASES_APP_ID }, + { user: obsCasesNoDeleteUser, owner: OBSERVABILITY_APP_ID }, + ]) { + it(`User ${ + user.username + } with role(s) ${user.roles.join()} cannot delete a case`, async () => { + const caseInfo = await createCase(supertest, getPostCaseRequest({ owner })); + await deleteCases({ + caseIDs: [caseInfo.id], + supertest: supertestWithoutAuth, + expectedHttpCode: 403, + auth: { user, space: null }, + }); + }); + } + }); +}; diff --git a/x-pack/test/api_integration/apis/index.ts b/x-pack/test/api_integration/apis/index.ts index 46b10af2a52b3..5f99067833afd 100644 --- a/x-pack/test/api_integration/apis/index.ts +++ b/x-pack/test/api_integration/apis/index.ts @@ -36,6 +36,7 @@ export default function ({ loadTestFile }: FtrProviderContext) { loadTestFile(require.resolve('./watcher')); loadTestFile(require.resolve('./logs_ui')); loadTestFile(require.resolve('./osquery')); + loadTestFile(require.resolve('./cases')); loadTestFile(require.resolve('./monitoring_collection')); }); } diff --git a/x-pack/test/api_integration/apis/security/privileges.ts b/x-pack/test/api_integration/apis/security/privileges.ts index 61ac283dfea34..3e6d18ef40840 100644 --- a/x-pack/test/api_integration/apis/security/privileges.ts +++ b/x-pack/test/api_integration/apis/security/privileges.ts @@ -28,8 +28,8 @@ export default function ({ getService }: FtrProviderContext) { savedObjectsTagging: ['all', 'read', 'minimal_all', 'minimal_read'], canvas: ['all', 'read', 'minimal_all', 'minimal_read'], maps: ['all', 'read', 'minimal_all', 'minimal_read'], - generalCases: ['all', 'read', 'minimal_all', 'minimal_read'], - observabilityCases: ['all', 'read', 'minimal_all', 'minimal_read'], + generalCases: ['all', 'read', 'minimal_all', 'minimal_read', 'cases_delete'], + observabilityCases: ['all', 'read', 'minimal_all', 'minimal_read', 'cases_delete'], fleetv2: ['all', 'read', 'minimal_all', 'minimal_read'], fleet: ['all', 'read', 'minimal_all', 'minimal_read'], actions: ['all', 'read', 'minimal_all', 'minimal_read'], @@ -37,7 +37,7 @@ export default function ({ getService }: FtrProviderContext) { ml: ['all', 'read', 'minimal_all', 'minimal_read'], siem: ['all', 'read', 'minimal_all', 'minimal_read'], uptime: ['all', 'read', 'minimal_all', 'minimal_read'], - securitySolutionCases: ['all', 'read', 'minimal_all', 'minimal_read'], + securitySolutionCases: ['all', 'read', 'minimal_all', 'minimal_read', 'cases_delete'], infrastructure: ['all', 'read', 'minimal_all', 'minimal_read'], logs: ['all', 'read', 'minimal_all', 'minimal_read'], apm: ['all', 'read', 'minimal_all', 'minimal_read'], diff --git a/x-pack/test/api_integration/apis/security_solution/cases_privileges.ts b/x-pack/test/api_integration/apis/security_solution/cases_privileges.ts deleted file mode 100644 index 67341c0dccb99..0000000000000 --- a/x-pack/test/api_integration/apis/security_solution/cases_privileges.ts +++ /dev/null @@ -1,336 +0,0 @@ -/* - * 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; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import expect from '@kbn/expect'; - -import { APP_ID } from '@kbn/security-solution-plugin/common/constants'; -import { FtrProviderContext } from '../../ftr_provider_context'; -import { - createUsersAndRoles, - deleteUsersAndRoles, -} from '../../../cases_api_integration/common/lib/authentication'; - -import { Role, User } from '../../../cases_api_integration/common/lib/authentication/types'; -import { - createCase, - deleteAllCaseItems, - getCase, -} from '../../../cases_api_integration/common/lib/utils'; -import { getPostCaseRequest } from '../../../cases_api_integration/common/lib/mock'; - -const secAll: Role = { - name: 'sec_all_role', - privileges: { - elasticsearch: { - indices: [ - { - names: ['*'], - privileges: ['all'], - }, - ], - }, - kibana: [ - { - feature: { - siem: ['all'], - securitySolutionCases: ['all'], - actions: ['all'], - actionsSimulators: ['all'], - }, - spaces: ['*'], - }, - ], - }, -}; - -const secAllUser: User = { - username: 'sec_all_user', - password: 'password', - roles: [secAll.name], -}; - -const secAllCasesRead: Role = { - name: 'sec_all_cases_read_role', - privileges: { - elasticsearch: { - indices: [ - { - names: ['*'], - privileges: ['all'], - }, - ], - }, - kibana: [ - { - feature: { - siem: ['all'], - securitySolutionCases: ['read'], - actions: ['all'], - actionsSimulators: ['all'], - }, - spaces: ['*'], - }, - ], - }, -}; - -const secAllCasesReadUser: User = { - username: 'sec_all_cases_read_user', - password: 'password', - roles: [secAllCasesRead.name], -}; - -const secAllCasesNone: Role = { - name: 'sec_all_cases_none_role', - privileges: { - elasticsearch: { - indices: [ - { - names: ['*'], - privileges: ['all'], - }, - ], - }, - kibana: [ - { - feature: { - siem: ['all'], - actions: ['all'], - actionsSimulators: ['all'], - }, - spaces: ['*'], - }, - ], - }, -}; - -const secAllCasesNoneUser: User = { - username: 'sec_all_cases_none_user', - password: 'password', - roles: [secAllCasesNone.name], -}; - -const secReadCasesAll: Role = { - name: 'sec_read_cases_all_role', - privileges: { - elasticsearch: { - indices: [ - { - names: ['*'], - privileges: ['all'], - }, - ], - }, - kibana: [ - { - feature: { - siem: ['read'], - securitySolutionCases: ['all'], - actions: ['all'], - actionsSimulators: ['all'], - }, - spaces: ['*'], - }, - ], - }, -}; - -const secReadCasesAllUser: User = { - username: 'sec_read_cases_all_user', - password: 'password', - roles: [secReadCasesAll.name], -}; - -const secReadCasesRead: Role = { - name: 'sec_read_cases_read_role', - privileges: { - elasticsearch: { - indices: [ - { - names: ['*'], - privileges: ['all'], - }, - ], - }, - kibana: [ - { - feature: { - siem: ['read'], - securitySolutionCases: ['read'], - actions: ['all'], - actionsSimulators: ['all'], - }, - spaces: ['*'], - }, - ], - }, -}; - -const secReadCasesReadUser: User = { - username: 'sec_read_cases_read_user', - password: 'password', - roles: [secReadCasesRead.name], -}; - -const secRead: Role = { - name: 'sec_read_role', - privileges: { - elasticsearch: { - indices: [ - { - names: ['*'], - privileges: ['all'], - }, - ], - }, - kibana: [ - { - feature: { - siem: ['read'], - securitySolutionCases: ['read'], - actions: ['all'], - actionsSimulators: ['all'], - }, - spaces: ['*'], - }, - ], - }, -}; - -const secReadUser: User = { - username: 'sec_read_user', - password: 'password', - roles: [secRead.name], -}; - -const secReadCasesNone: Role = { - name: 'sec_read_cases_none_role', - privileges: { - elasticsearch: { - indices: [ - { - names: ['*'], - privileges: ['all'], - }, - ], - }, - kibana: [ - { - feature: { - siem: ['read'], - actions: ['all'], - actionsSimulators: ['all'], - }, - spaces: ['*'], - }, - ], - }, -}; - -const secReadCasesNoneUser: User = { - username: 'sec_read_cases_none_user', - password: 'password', - roles: [secReadCasesNone.name], -}; - -const roles = [ - secAll, - secAllCasesRead, - secAllCasesNone, - secReadCasesAll, - secReadCasesRead, - secRead, - secReadCasesNone, -]; - -const users = [ - secAllUser, - secAllCasesReadUser, - secAllCasesNoneUser, - secReadCasesAllUser, - secReadCasesReadUser, - secReadUser, - secReadCasesNoneUser, -]; - -export default ({ getService }: FtrProviderContext): void => { - describe('security solution cases sub feature privilege', () => { - const es = getService('es'); - const supertestWithoutAuth = getService('supertestWithoutAuth'); - const supertest = getService('supertest'); - - before(async () => { - await createUsersAndRoles(getService, users, roles); - }); - - after(async () => { - await deleteUsersAndRoles(getService, users, roles); - }); - - afterEach(async () => { - await deleteAllCaseItems(es); - }); - - for (const user of [secAllUser, secReadCasesAllUser]) { - it(`User ${user.username} with role(s) ${user.roles.join()} can create a case`, async () => { - await createCase(supertestWithoutAuth, getPostCaseRequest({ owner: APP_ID }), 200, { - user, - space: null, - }); - }); - } - - for (const user of [ - secAllCasesReadUser, - secReadCasesAllUser, - secReadCasesReadUser, - secReadUser, - ]) { - it(`User ${user.username} with role(s) ${user.roles.join()} can get a case`, async () => { - const caseInfo = await createCase(supertest, getPostCaseRequest({ owner: APP_ID })); - const retrievedCase = await getCase({ - supertest: supertestWithoutAuth, - caseId: caseInfo.id, - expectedHttpCode: 200, - auth: { user, space: null }, - }); - - expect(caseInfo.owner).to.eql(retrievedCase.owner); - }); - } - - for (const user of [ - secAllCasesReadUser, - secAllCasesNoneUser, - secReadCasesReadUser, - secReadUser, - secReadCasesNoneUser, - ]) { - it(`User ${ - user.username - } with role(s) ${user.roles.join()} cannot create a case`, async () => { - await createCase(supertestWithoutAuth, getPostCaseRequest({ owner: APP_ID }), 403, { - user, - space: null, - }); - }); - } - - for (const user of [secAllCasesNoneUser, secReadCasesNoneUser]) { - it(`User ${user.username} with role(s) ${user.roles.join()} cannot get a case`, async () => { - const caseInfo = await createCase(supertest, getPostCaseRequest({ owner: APP_ID })); - - await getCase({ - supertest: supertestWithoutAuth, - caseId: caseInfo.id, - expectedHttpCode: 403, - auth: { user, space: null }, - }); - }); - } - }); -}; diff --git a/x-pack/test/api_integration/apis/security_solution/index.js b/x-pack/test/api_integration/apis/security_solution/index.js index 316ffb9601ccd..ba35ac7240852 100644 --- a/x-pack/test/api_integration/apis/security_solution/index.js +++ b/x-pack/test/api_integration/apis/security_solution/index.js @@ -8,7 +8,6 @@ export default function ({ loadTestFile }) { describe('SecuritySolution Endpoints', () => { loadTestFile(require.resolve('./authentications')); - loadTestFile(require.resolve('./cases_privileges')); loadTestFile(require.resolve('./events')); loadTestFile(require.resolve('./hosts')); loadTestFile(require.resolve('./host_details')); diff --git a/x-pack/test/functional/services/cases/index.ts b/x-pack/test/functional/services/cases/index.ts index 886750c4ebfab..28e5fe1a6a326 100644 --- a/x-pack/test/functional/services/cases/index.ts +++ b/x-pack/test/functional/services/cases/index.ts @@ -11,6 +11,7 @@ import { CasesCommonServiceProvider } from './common'; import { CasesCreateViewServiceProvider } from './create'; import { CasesTableServiceProvider } from './list'; import { CasesNavigationProvider } from './navigation'; +import { CasesSingleViewServiceProvider } from './single_case_view'; export function CasesServiceProvider(context: FtrProviderContext) { return { @@ -19,5 +20,6 @@ export function CasesServiceProvider(context: FtrProviderContext) { casesTable: CasesTableServiceProvider(context), create: CasesCreateViewServiceProvider(context), navigation: CasesNavigationProvider(context), + singleCase: CasesSingleViewServiceProvider(context), }; } diff --git a/x-pack/test/functional/services/cases/single_case_view.ts b/x-pack/test/functional/services/cases/single_case_view.ts new file mode 100644 index 0000000000000..83dbb6388fed1 --- /dev/null +++ b/x-pack/test/functional/services/cases/single_case_view.ts @@ -0,0 +1,23 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { FtrProviderContext } from '../../ftr_provider_context'; + +export function CasesSingleViewServiceProvider({ getService, getPageObject }: FtrProviderContext) { + const common = getPageObject('common'); + const testSubjects = getService('testSubjects'); + const header = getPageObject('header'); + + return { + async deleteCase() { + await common.clickAndValidate('property-actions-ellipses', 'property-actions-trash'); + await common.clickAndValidate('property-actions-trash', 'confirmModalConfirmButton'); + await testSubjects.click('confirmModalConfirmButton'); + await header.waitUntilLoadingHasFinished(); + }, + }; +} diff --git a/x-pack/test/functional_with_es_ssl/apps/cases/common/index.ts b/x-pack/test/functional_with_es_ssl/apps/cases/common/index.ts new file mode 100644 index 0000000000000..e24bf42d35e6a --- /dev/null +++ b/x-pack/test/functional_with_es_ssl/apps/cases/common/index.ts @@ -0,0 +1,9 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +export * from './roles'; +export * from './users'; diff --git a/x-pack/test/functional_with_es_ssl/apps/cases/common/roles.ts b/x-pack/test/functional_with_es_ssl/apps/cases/common/roles.ts new file mode 100644 index 0000000000000..f06c8745d6df6 --- /dev/null +++ b/x-pack/test/functional_with_es_ssl/apps/cases/common/roles.ts @@ -0,0 +1,86 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { Role } from '../../../../cases_api_integration/common/lib/authentication/types'; + +/** + * Roles for Cases in the stack + */ + +export const casesReadDelete: Role = { + name: 'cases_read_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + generalCases: ['minimal_read', 'cases_delete'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const casesNoDelete: Role = { + name: 'cases_no_delete', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + generalCases: ['minimal_all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const casesAll: Role = { + name: 'cases_all_role', + privileges: { + elasticsearch: { + indices: [ + { + names: ['*'], + privileges: ['all'], + }, + ], + }, + kibana: [ + { + feature: { + generalCases: ['all'], + actions: ['all'], + actionsSimulators: ['all'], + }, + spaces: ['*'], + }, + ], + }, +}; + +export const roles = [casesReadDelete, casesNoDelete, casesAll]; diff --git a/x-pack/test/functional_with_es_ssl/apps/cases/common/users.ts b/x-pack/test/functional_with_es_ssl/apps/cases/common/users.ts new file mode 100644 index 0000000000000..282072dbb8dce --- /dev/null +++ b/x-pack/test/functional_with_es_ssl/apps/cases/common/users.ts @@ -0,0 +1,33 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { User } from '../../../../cases_api_integration/common/lib/authentication/types'; +import { casesAll, casesNoDelete, casesReadDelete } from './roles'; + +/** + * Users for Cases in the Stack + */ + +export const casesReadDeleteUser: User = { + username: 'cases_read_delete_user', + password: 'password', + roles: [casesReadDelete.name], +}; + +export const casesNoDeleteUser: User = { + username: 'cases_no_delete_user', + password: 'password', + roles: [casesNoDelete.name], +}; + +export const casesAllUser: User = { + username: 'cases_all_user', + password: 'password', + roles: [casesAll.name], +}; + +export const users = [casesReadDeleteUser, casesNoDeleteUser, casesAllUser]; diff --git a/x-pack/test/functional_with_es_ssl/apps/cases/deletion.ts b/x-pack/test/functional_with_es_ssl/apps/cases/deletion.ts new file mode 100644 index 0000000000000..8fd032a8e1b7a --- /dev/null +++ b/x-pack/test/functional_with_es_ssl/apps/cases/deletion.ts @@ -0,0 +1,123 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { FtrProviderContext } from '../../ftr_provider_context'; +import { users, roles, casesReadDeleteUser, casesAllUser, casesNoDeleteUser } from './common'; +import { + createUsersAndRoles, + deleteUsersAndRoles, +} from '../../../cases_api_integration/common/lib/authentication'; + +export default ({ getPageObjects, getService }: FtrProviderContext) => { + const PageObjects = getPageObjects(['security', 'header']); + const testSubjects = getService('testSubjects'); + const cases = getService('cases'); + + describe('cases deletion sub privilege', () => { + before(async () => { + await createUsersAndRoles(getService, users, roles); + await PageObjects.security.forceLogout(); + }); + + after(async () => { + await deleteUsersAndRoles(getService, users, roles); + await cases.api.deleteAllCases(); + await PageObjects.security.forceLogout(); + }); + + describe('create two cases', () => { + beforeEach(async () => { + await cases.api.createNthRandomCases(2); + }); + + afterEach(async () => { + await cases.api.deleteAllCases(); + }); + + for (const user of [casesReadDeleteUser, casesAllUser]) { + describe(`logging in with user ${user.username}`, () => { + before(async () => { + await PageObjects.security.login(user.username, user.password); + }); + + beforeEach(async () => { + await navigateToCasesAndWaitToLoad(getService); + }); + + after(async () => { + await PageObjects.security.forceLogout(); + }); + + describe('single case view', () => { + beforeEach(async () => { + await cases.casesTable.goToFirstListedCase(); + }); + + it(`User ${user.username} can delete a case while on a specific case page`, async () => { + await cases.singleCase.deleteCase(); + await cases.casesTable.validateCasesTableHasNthRows(1); + }); + }); + + describe('all cases list page', () => { + it(`User ${user.username} can bulk delete cases`, async () => { + await cases.casesTable.selectAndDeleteAllCases(); + await cases.casesTable.waitForTableToFinishLoading(); + await cases.casesTable.validateCasesTableHasNthRows(0); + }); + + it(`User ${user.username} can delete a case using the trash icon in the table row`, async () => { + await cases.casesTable.deleteFirstListedCase(); + }); + }); + }); + } + + for (const user of [casesNoDeleteUser]) { + describe(`logging in with user ${user.username}`, () => { + before(async () => { + await PageObjects.security.login(user.username, user.password); + }); + + beforeEach(async () => { + await navigateToCasesAndWaitToLoad(getService); + }); + + after(async () => { + await PageObjects.security.forceLogout(); + }); + + describe('single case view', () => { + beforeEach(async () => { + await cases.casesTable.goToFirstListedCase(); + }); + + it(`User ${user.username} cannot delete a case while on a specific case page`, async () => { + await testSubjects.missingOrFail('case-view-actions'); + }); + }); + + describe('all cases list page', () => { + it(`User ${user.username} cannot delete cases using bulk actions or individual row trash icon`, async () => { + await testSubjects.missingOrFail('case-table-bulk-actions'); + await testSubjects.missingOrFail('checkboxSelectAll'); + await testSubjects.missingOrFail('action-delete'); + }); + }); + }); + } + }); + }); +}; + +const navigateToCasesAndWaitToLoad = async (getService: FtrProviderContext['getService']) => { + const cases = getService('cases'); + + await cases.navigation.navigateToApp(); + await cases.casesTable.waitForCasesToBeListed(); + await cases.casesTable.waitForTableToFinishLoading(); +}; diff --git a/x-pack/test/functional_with_es_ssl/apps/cases/index.ts b/x-pack/test/functional_with_es_ssl/apps/cases/index.ts index 7462b8355b7e3..405361b054d16 100644 --- a/x-pack/test/functional_with_es_ssl/apps/cases/index.ts +++ b/x-pack/test/functional_with_es_ssl/apps/cases/index.ts @@ -14,5 +14,6 @@ export default ({ loadTestFile }: FtrProviderContext) => { loadTestFile(require.resolve('./list_view')); loadTestFile(require.resolve('./configure')); loadTestFile(require.resolve('./attachment_framework')); + loadTestFile(require.resolve('./deletion')); }); }; diff --git a/x-pack/test/functional_with_es_ssl/apps/cases/view_case.ts b/x-pack/test/functional_with_es_ssl/apps/cases/view_case.ts index 42d5d5074e18d..223127125e66d 100644 --- a/x-pack/test/functional_with_es_ssl/apps/cases/view_case.ts +++ b/x-pack/test/functional_with_es_ssl/apps/cases/view_case.ts @@ -12,7 +12,6 @@ import { CaseSeverity } from '@kbn/cases-plugin/common/api'; import { FtrProviderContext } from '../../ftr_provider_context'; export default ({ getPageObject, getService }: FtrProviderContext) => { - const common = getPageObject('common'); const header = getPageObject('header'); const testSubjects = getService('testSubjects'); const find = getService('find'); @@ -182,10 +181,7 @@ export default ({ getPageObject, getService }: FtrProviderContext) => { }); it('deletes the case successfully', async () => { - await common.clickAndValidate('property-actions-ellipses', 'property-actions-trash'); - await common.clickAndValidate('property-actions-trash', 'confirmModalConfirmButton'); - await testSubjects.click('confirmModalConfirmButton'); - await header.waitUntilLoadingHasFinished(); + await cases.singleCase.deleteCase(); await cases.casesTable.validateCasesTableHasNthRows(0); }); }); From cbcfa0bb038da2e8db5dab3cea59583b0610c01d Mon Sep 17 00:00:00 2001 From: Ashokaditya <1849116+ashokaditya@users.noreply.github.com> Date: Mon, 18 Jul 2022 18:23:01 +0200 Subject: [PATCH 109/111] [Security Solution][Endpoint][Response Actions] Show console exit modal if pending actions (#136281) * Show console exit modal if pending actions fixes elastic/security-team/issues/4305 * Update modal content per mocks * fix test mocks * update tests to include exit modal * update modal * pass modal content as a render prop review changes * move the link component to responder review changes --- .../components/console_exit_modal.tsx | 39 +++++++++++++++++ .../components/console_page_overlay.tsx | 39 ++++++++++++++--- .../console_manager/console_manager.tsx | 21 ++++++++- .../components/console_manager/mocks.tsx | 7 ++- .../console_manager/translations.ts | 31 +++++++++++++ .../components/console_manager/types.ts | 3 ++ .../console_exit_modal_info.tsx | 43 +++++++++++++++++++ .../endpoint_exit_modal_message.tsx | 42 ++++++++++++++++++ .../get_processes_action.test.tsx | 11 +++++ .../components/endpoint_responder/index.ts | 1 + .../isolate_action.test.tsx | 11 +++++ .../kill_process_action.test.tsx | 11 +++++ .../release_action.test.tsx | 11 +++++ .../suspend_process_action.test.tsx | 11 +++++ .../use_with_show_endpoint_responder.tsx | 2 + 15 files changed, 275 insertions(+), 8 deletions(-) create mode 100644 x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_exit_modal.tsx create mode 100644 x-pack/plugins/security_solution/public/management/components/console/components/console_manager/translations.ts create mode 100644 x-pack/plugins/security_solution/public/management/components/endpoint_responder/console_exit_modal_info.tsx create mode 100644 x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_exit_modal_message.tsx diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_exit_modal.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_exit_modal.tsx new file mode 100644 index 0000000000000..ba823fc50b922 --- /dev/null +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_exit_modal.tsx @@ -0,0 +1,39 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React, { memo } from 'react'; +import { EuiConfirmModal, EuiText } from '@elastic/eui'; +import { CONSOLE_EXIT_MODAL_INFO } from '../translations'; + +export const ConsoleExitModal = memo( + ({ + 'data-test-subj': dataTestSubj, + message, + onClose, + onCancel, + }: { + 'data-test-subj'?: string; + message?: React.ReactNode; + onClose: () => void; + onCancel: () => void; + }) => { + return ( + <EuiConfirmModal + confirmButtonText={CONSOLE_EXIT_MODAL_INFO.confirmButtonText} + cancelButtonText={CONSOLE_EXIT_MODAL_INFO.cancelButtonText} + data-test-subj={dataTestSubj} + onCancel={onCancel} + onConfirm={onClose} + title={CONSOLE_EXIT_MODAL_INFO.title} + maxWidth={500} + > + {message ? message : <EuiText size="s">{CONSOLE_EXIT_MODAL_INFO.genericMessage}</EuiText>} + </EuiConfirmModal> + ); + } +); +ConsoleExitModal.displayName = 'ConsoleExitModal'; diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_page_overlay.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_page_overlay.tsx index d6140265a9205..38e6a53437fe2 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_page_overlay.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/components/console_page_overlay.tsx @@ -6,7 +6,7 @@ */ import type { ReactNode, MouseEventHandler } from 'react'; -import React, { memo, useCallback, useMemo } from 'react'; +import React, { memo, useCallback, useMemo, useState } from 'react'; import { i18n } from '@kbn/i18n'; import { EuiButton, EuiButtonEmpty } from '@elastic/eui'; import { FormattedMessage } from '@kbn/i18n-react'; @@ -14,6 +14,7 @@ import type { PageLayoutProps } from './page_layout'; import { PageLayout } from './page_layout'; import { useTestIdGenerator } from '../../../../../hooks/use_test_id_generator'; import { PageOverlay } from '../../../../page_overlay/page_overlay'; +import { ConsoleExitModal } from './console_exit_modal'; const BACK_LABEL = i18n.translate('xpack.securitySolution.consolePageOverlay.backButtonLabel', { defaultMessage: 'Return to page content', @@ -21,24 +22,42 @@ const BACK_LABEL = i18n.translate('xpack.securitySolution.consolePageOverlay.bac export interface ConsolePageOverlayProps { console: ReactNode; + hasPendingActions: boolean; isHidden: boolean; onHide: () => void; pageTitle?: ReactNode; + pendingExitMessage?: ReactNode; body?: ReactNode; actions?: ReactNode[]; } export const ConsolePageOverlay = memo<ConsolePageOverlayProps>( - ({ console, onHide, isHidden, body, actions, pageTitle = '' }) => { + ({ + console, + hasPendingActions, + onHide, + pendingExitMessage, + isHidden, + body, + actions, + pageTitle = '', + }) => { const getTestId = useTestIdGenerator('consolePageOverlay'); + const [showExitModal, setShowExitModal] = useState(false); + const handleCloseOverlayOnClick: MouseEventHandler = useCallback( (ev) => { ev.preventDefault(); - onHide(); + setShowExitModal(hasPendingActions); + if (!hasPendingActions) { + onHide(); + } }, - [onHide] + [onHide, hasPendingActions] ); + const onCancelModal = useCallback(() => setShowExitModal(false), [setShowExitModal]); + const layoutProps = useMemo<PageLayoutProps>(() => { // If in `hidden` mode, then we don't render the html for the layout header section // of the layout @@ -85,7 +104,17 @@ export const ConsolePageOverlay = memo<ConsolePageOverlayProps>( paddingSize="l" enableScrolling={false} > - <PageLayout {...layoutProps}>{console}</PageLayout> + <PageLayout {...layoutProps}> + {showExitModal && ( + <ConsoleExitModal + message={pendingExitMessage} + onClose={onHide} + onCancel={onCancelModal} + data-test-subj={getTestId('console-exit-modal')} + /> + )} + {console} + </PageLayout> </PageOverlay> ); } diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/console_manager.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/console_manager.tsx index 932ffb1e4b477..4ee1d1445633c 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/console_manager.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/console_manager.tsx @@ -7,6 +7,7 @@ import type { PropsWithChildren } from 'react'; import React, { memo, useCallback, useContext, useMemo, useRef, useState } from 'react'; + import type { ConsoleDataState } from '../console_state/types'; import { ConsolePageOverlay } from './components/console_page_overlay'; import type { @@ -19,7 +20,11 @@ import { Console } from '../../console'; interface ManagedConsole extends Pick< ConsoleRegistrationInterface, - 'consoleProps' | 'PageTitleComponent' | 'PageBodyComponent' | 'ActionComponents' + | 'consoleProps' + | 'ExitPendingActionComponent' + | 'PageTitleComponent' + | 'PageBodyComponent' + | 'ActionComponents' > { client: RegisteredConsoleClient; console: JSX.Element; // actual console component @@ -64,6 +69,8 @@ export const ConsoleManager = memo<ConsoleManagerProps>(({ storage = {}, childre const [consoleStorage, setConsoleStorage] = useState<RunningConsoleStorage>(storage); const [consoleStateStorage] = useState(new Map<ManagedConsole['key'], ConsoleDataState>()); + const [hasPendingActions, setHasPendingActions] = useState(false); + // `consoleStorageRef` keeps a copy (reference) to the latest copy of the `consoleStorage` so that // some exposed methods (ex. `RegisteredConsoleClient`) are guaranteed to be immutable and function // as expected between state updates without having to re-update every record stored in the `ConsoleStorage` @@ -241,6 +248,11 @@ export const ConsoleManager = memo<ConsoleManagerProps>(({ storage = {}, childre storeManagedConsoleState(key: ManagedConsole['key'], state: ConsoleDataState) { consoleStateStorage.set(key, state); + setHasPendingActions( + !!consoleStateStorage + .get(key) + ?.commandHistory.some((historyItem) => historyItem.state.status === 'pending') + ); }, }, }; @@ -263,9 +275,14 @@ export const ConsoleManager = memo<ConsoleManagerProps>(({ storage = {}, childre return ( <ConsoleManagerContext.Provider value={consoleManageContextClients}> {children} - {visibleConsole && ( <ConsolePageOverlay + hasPendingActions={hasPendingActions} + pendingExitMessage={ + visibleConsole.ExitPendingActionComponent && ( + <visibleConsole.ExitPendingActionComponent meta={visibleConsoleMeta} /> + ) + } onHide={handleOnHide} console={ <Console diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/mocks.tsx b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/mocks.tsx index 1a33514bb47c2..e336ab48dfeea 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/mocks.tsx +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/mocks.tsx @@ -75,7 +75,12 @@ export const getConsoleManagerMockRenderResultQueriesAndActions = ( hideOpenedConsole: async () => { userEvent.click(renderResult.getByTestId('consolePageOverlay-doneButton')); - + const exitModalConfirmButton = renderResult.queryByTestId('confirmModalConfirmButton'); + if (exitModalConfirmButton) { + const exitModal = renderResult.getByTestId('consolePageOverlay-console-exit-modal'); + expect(exitModal).toBeTruthy(); + userEvent.click(exitModalConfirmButton); + } await waitFor(() => { expect(renderResult.queryByTestId('consolePageOverlay')).toBeNull(); }); diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/translations.ts b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/translations.ts new file mode 100644 index 0000000000000..8bdcb9bd957e2 --- /dev/null +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/translations.ts @@ -0,0 +1,31 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import { i18n } from '@kbn/i18n'; + +export const CONSOLE_EXIT_MODAL_INFO = Object.freeze({ + cancelButtonText: i18n.translate( + 'xpack.securitySolution.consolePageOverlay.exitModal.cancelButtonText', + { + defaultMessage: 'Cancel', + } + ), + confirmButtonText: i18n.translate( + 'xpack.securitySolution.consolePageOverlay.exitModal.confirmButtonText', + { + defaultMessage: 'Okay, exit responder', + } + ), + genericMessage: i18n.translate( + 'xpack.securitySolution.consolePageOverlay.exitModal.genericMessage', + { + defaultMessage: 'Pending response actions will resume.', + } + ), + title: i18n.translate('xpack.securitySolution.consolePageOverlay.exitModal.title', { + defaultMessage: 'Action is in progress', + }), +}); diff --git a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/types.ts b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/types.ts index 5fa4fee704036..60c9b98c988fb 100644 --- a/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/types.ts +++ b/x-pack/plugins/security_solution/public/management/components/console/components/console_manager/types.ts @@ -19,6 +19,9 @@ export interface ConsoleRegistrationInterface<TMeta extends object = any> { */ meta?: TMeta; + /** An optional component used to render the modal body on console exit when actions are pending */ + ExitPendingActionComponent?: ComponentType<ManagedConsoleExtensionComponentProps<TMeta>>; + /** An optional component used to render the Overlay page title where the console will be displayed */ PageTitleComponent?: ComponentType<ManagedConsoleExtensionComponentProps<TMeta>>; diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/console_exit_modal_info.tsx b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/console_exit_modal_info.tsx new file mode 100644 index 0000000000000..319241b40fe9a --- /dev/null +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/console_exit_modal_info.tsx @@ -0,0 +1,43 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { i18n } from '@kbn/i18n'; +import React, { memo } from 'react'; +import { FormattedMessage } from '@kbn/i18n-react'; +import { EuiText } from '@elastic/eui'; + +import { CONSOLE_EXIT_MODAL_INFO } from '../console/components/console_manager/translations'; + +const actionLogLink = i18n.translate('xpack.securitySolution.consolePageOverlay.exitModal.link', { + defaultMessage: 'Action log', +}); + +export const HostNameText = ({ hostName }: { hostName: string }) => ( + <EuiText size="s" style={{ maxWidth: 100, display: 'inline-flex' }}> + <span className="eui-textTruncate"> + <strong>{hostName}</strong> + </span> + </EuiText> +); + +export const ConsoleExitModalInfo = memo(({ hostName }: { hostName: string }) => { + return ( + <EuiText size="s"> + <FormattedMessage + id="xpack.securitySolution.consolePageOverlay.exitModal.actionLogLink" + defaultMessage="{genericMessage} You may track progress of the action on {hostName}'s {link}." + values={{ + genericMessage: CONSOLE_EXIT_MODAL_INFO.genericMessage, + hostName: <HostNameText hostName={hostName} />, + link: <strong>{actionLogLink}</strong>, + }} + /> + </EuiText> + ); +}); + +ConsoleExitModalInfo.displayName = 'ConsoleExitModalInfo'; diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_exit_modal_message.tsx b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_exit_modal_message.tsx new file mode 100644 index 0000000000000..963f8d7df6a4b --- /dev/null +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/endpoint_exit_modal_message.tsx @@ -0,0 +1,42 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React, { memo } from 'react'; +import { FormattedMessage } from '@kbn/i18n-react'; +import { EuiSpacer, EuiText } from '@elastic/eui'; +import type { HostMetadata } from '../../../../common/endpoint/types'; +import { ConsoleExitModalInfo, HostNameText } from './console_exit_modal_info'; + +export const EndpointExitModalMessage = memo(({ meta }: { meta: { endpoint: HostMetadata } }) => { + return ( + <> + <ConsoleExitModalInfo hostName={meta.endpoint.host.hostname} /> + <EuiSpacer size="l" /> + <EuiText size="s"> + <FormattedMessage + id="xpack.securitySolution.consolePageOverlay.exitModal.body" + defaultMessage="Access it here : {linkText}" + values={{ + linkText: ( + <strong> + <FormattedMessage + id="xpack.securitySolution.consolePageOverlay.exitModal.linkText" + defaultMessage="Manage> Endpoints> {hostName}> Action log." + values={{ + hostName: <HostNameText hostName={meta.endpoint.host.hostname} />, + }} + /> + </strong> + ), + }} + /> + </EuiText> + </> + ); +}); + +EndpointExitModalMessage.displayName = 'EndpointExitModalMessage'; diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/get_processes_action.test.tsx b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/get_processes_action.test.tsx index 8977b1fb425a4..5e68bb018e6a6 100644 --- a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/get_processes_action.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/get_processes_action.test.tsx @@ -187,5 +187,16 @@ describe('When using processes action from response actions console', () => { expect(apiMocks.responseProvider.actionDetails).toHaveBeenCalledTimes(1); }); + + it('should show exit modal when action still pending', async () => { + const pendingDetailResponse = apiMocks.responseProvider.actionDetails({ + path: '/api/endpoint/action/1.2.3', + }); + pendingDetailResponse.data.isCompleted = false; + apiMocks.responseProvider.actionDetails.mockReturnValue(pendingDetailResponse); + await render(); + await consoleManagerMockAccess.openRunningConsole(); + await consoleManagerMockAccess.hideOpenedConsole(); + }); }); }); diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/index.ts b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/index.ts index 35b632d1ea4ee..842826a1f6017 100644 --- a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/index.ts +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/index.ts @@ -7,3 +7,4 @@ export { getEndpointResponseActionsConsoleCommands } from './endpoint_response_actions_console_commands'; export { ActionLogButton } from './action_log_button'; +export { EndpointExitModalMessage } from './endpoint_exit_modal_message'; diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/isolate_action.test.tsx b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/isolate_action.test.tsx index 7694606490f37..c177f8e6fa113 100644 --- a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/isolate_action.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/isolate_action.test.tsx @@ -171,5 +171,16 @@ describe('When using isolate action from response actions console', () => { expect(apiMocks.responseProvider.actionDetails).toHaveBeenCalledTimes(1); }); + + it('should show exit modal when action still pending', async () => { + const pendingDetailResponse = apiMocks.responseProvider.actionDetails({ + path: '/api/endpoint/action/1.2.3', + }); + pendingDetailResponse.data.isCompleted = false; + apiMocks.responseProvider.actionDetails.mockReturnValue(pendingDetailResponse); + await render(); + await consoleManagerMockAccess.openRunningConsole(); + await consoleManagerMockAccess.hideOpenedConsole(); + }); }); }); diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/kill_process_action.test.tsx b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/kill_process_action.test.tsx index ff027aa7c788e..264cb3779c938 100644 --- a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/kill_process_action.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/kill_process_action.test.tsx @@ -234,5 +234,16 @@ describe('When using the kill-process action from response actions console', () expect(apiMocks.responseProvider.actionDetails).toHaveBeenCalledTimes(1); }); + + it('should show exit modal when action still pending', async () => { + const pendingDetailResponse = apiMocks.responseProvider.actionDetails({ + path: '/api/endpoint/action/1.2.3', + }); + pendingDetailResponse.data.isCompleted = false; + apiMocks.responseProvider.actionDetails.mockReturnValue(pendingDetailResponse); + await render(); + await consoleManagerMockAccess.openRunningConsole(); + await consoleManagerMockAccess.hideOpenedConsole(); + }); }); }); diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/release_action.test.tsx b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/release_action.test.tsx index a132fe11f254b..2314949a4a46b 100644 --- a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/release_action.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/release_action.test.tsx @@ -172,5 +172,16 @@ describe('When using the release action from response actions console', () => { expect(apiMocks.responseProvider.actionDetails).toHaveBeenCalledTimes(1); }); + + it('should show exit modal when action still pending', async () => { + const pendingDetailResponse = apiMocks.responseProvider.actionDetails({ + path: '/api/endpoint/action/1.2.3', + }); + pendingDetailResponse.data.isCompleted = false; + apiMocks.responseProvider.actionDetails.mockReturnValue(pendingDetailResponse); + await render(); + await consoleManagerMockAccess.openRunningConsole(); + await consoleManagerMockAccess.hideOpenedConsole(); + }); }); }); diff --git a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/suspend_process_action.test.tsx b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/suspend_process_action.test.tsx index 1b3cf93bd8e1d..c28515ec11b38 100644 --- a/x-pack/plugins/security_solution/public/management/components/endpoint_responder/suspend_process_action.test.tsx +++ b/x-pack/plugins/security_solution/public/management/components/endpoint_responder/suspend_process_action.test.tsx @@ -234,5 +234,16 @@ describe('When using the suspend-process action from response actions console', expect(apiMocks.responseProvider.actionDetails).toHaveBeenCalledTimes(1); }); + + it('should show exit modal when action still pending', async () => { + const pendingDetailResponse = apiMocks.responseProvider.actionDetails({ + path: '/api/endpoint/action/1.2.3', + }); + pendingDetailResponse.data.isCompleted = false; + apiMocks.responseProvider.actionDetails.mockReturnValue(pendingDetailResponse); + await render(); + await consoleManagerMockAccess.openRunningConsole(); + await consoleManagerMockAccess.hideOpenedConsole(); + }); }); }); diff --git a/x-pack/plugins/security_solution/public/management/hooks/endpoint/use_with_show_endpoint_responder.tsx b/x-pack/plugins/security_solution/public/management/hooks/endpoint/use_with_show_endpoint_responder.tsx index 4c16dcbaed2c9..15541625fbf39 100644 --- a/x-pack/plugins/security_solution/public/management/hooks/endpoint/use_with_show_endpoint_responder.tsx +++ b/x-pack/plugins/security_solution/public/management/hooks/endpoint/use_with_show_endpoint_responder.tsx @@ -10,6 +10,7 @@ import { i18n } from '@kbn/i18n'; import { useUserPrivileges } from '../../../common/components/user_privileges'; import { ActionLogButton, + EndpointExitModalMessage, getEndpointResponseActionsConsoleCommands, } from '../../components/endpoint_responder'; import { useConsoleManager } from '../../components/console'; @@ -55,6 +56,7 @@ export const useWithShowEndpointResponder = (): ShowEndpointResponseActionsConso PageTitleComponent: () => <>{RESPONDER_PAGE_TITLE}</>, PageBodyComponent: () => <OfflineCallout endpointId={endpointAgentId} />, ActionComponents: [ActionLogButton], + ExitPendingActionComponent: EndpointExitModalMessage, }) .show(); } From 0bbc7328bd802e78fcbb03ca5395b52d911b48fc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Efe=20G=C3=BCrkan=20YALAMAN?= <efeguerkan.yalaman@elastic.co> Date: Mon, 18 Jul 2022 18:33:59 +0200 Subject: [PATCH 110/111] [Enterprise Search]Content plugin Index Overview (#136339) *visual updates * modal binding to logic * Add improvised modal. * Update overview with apikey data * i18n changes * Add index created callout * Create popovers * Add links to client libraries * Add header actions * Fix merge conflict issues * Add client libraries popover test * Add generate api key modal logic tests * Some review changes on modal and tests * type and i18n fixes * Fix linting * [CI] Auto-commit changed files from 'node scripts/eslint --no-cache --fix' Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../elasticsearch_cloud_id.tsx | 15 +- .../generate_api_key_logic.ts | 36 ++++ .../api/index/fetch_index_api_logic.ts | 2 + .../components/api_key/api_key.tsx | 35 ++-- .../client_libraries_popover/popover.test.tsx | 97 +++++++++++ .../client_libraries_popover/popover.tsx | 131 +++++++++++++++ .../generate_api_key_modal.logic.test.ts | 153 +++++++++++++++++ .../generate_api_key_modal.logic.ts | 59 +++++++ .../generate_api_key_modal/modal.test.tsx | 91 ++++++++++ .../generate_api_key_modal/modal.tsx | 158 ++++++++++++++++++ .../header_actions/header_actions.logic.ts | 33 ++++ .../header_actions/header_actions.tsx | 85 ++++++++++ .../index_created_callout/callout.tsx | 78 +++++++++ .../index_created_callout/callout_logic.ts | 36 ++++ .../manage_api_keys_popover/popover.tsx | 77 +++++++++ .../search_index/generate_api_key_panel.tsx | 126 +++++++++----- .../components/search_index/overview.logic.ts | 91 ++++++++++ .../components/search_index/overview.tsx | 10 +- .../components/search_index/search_index.tsx | 19 ++- .../components/search_index/total_stats.tsx | 12 +- .../shared/cloud_details/cloud_details.ts | 23 +++ .../doc_links/__mocks__/doc_links.mock.ts | 16 ++ .../shared/doc_links/doc_links.ts | 6 + .../translations/translations/zh-CN.json | 2 +- 24 files changed, 1306 insertions(+), 85 deletions(-) create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/generate_api_key/generate_api_key_logic.ts create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.test.tsx create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.tsx create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.test.ts create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.ts create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.test.tsx create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.tsx create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.logic.ts create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.tsx create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout.tsx create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout_logic.ts create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/manage_api_keys_popover/popover.tsx create mode 100644 x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.logic.ts create mode 100644 x-pack/plugins/enterprise_search/public/applications/shared/cloud_details/cloud_details.ts create mode 100644 x-pack/plugins/enterprise_search/public/applications/shared/doc_links/__mocks__/doc_links.mock.ts diff --git a/x-pack/plugins/enterprise_search/public/applications/elasticsearch/components/elasticsearch_cloud_id/elasticsearch_cloud_id.tsx b/x-pack/plugins/enterprise_search/public/applications/elasticsearch/components/elasticsearch_cloud_id/elasticsearch_cloud_id.tsx index 416c4a428c848..9e3a59aee83df 100644 --- a/x-pack/plugins/enterprise_search/public/applications/elasticsearch/components/elasticsearch_cloud_id/elasticsearch_cloud_id.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/elasticsearch/components/elasticsearch_cloud_id/elasticsearch_cloud_id.tsx @@ -25,8 +25,8 @@ import { import { i18n } from '@kbn/i18n'; +import { useCloudDetails } from '../../../shared/cloud_details/cloud_details'; import { HttpLogic } from '../../../shared/http'; -import { KibanaLogic } from '../../../shared/kibana'; import { TelemetryLogic } from '../../../shared/telemetry'; import { SendTelemetryHelper } from '../../../shared/telemetry/telemetry_logic'; @@ -34,19 +34,6 @@ const onFocusHandler = (e: React.FocusEvent<HTMLInputElement>): void => { e.target.select(); }; -interface CloudDetails { - cloudId: string | undefined; - deploymentUrl: string | undefined; -} - -const useCloudDetails = (): CloudDetails => { - const { cloud } = useValues(KibanaLogic); - return { - cloudId: cloud?.cloudId, - deploymentUrl: cloud?.deploymentUrl, - }; -}; - const copyCloudIdHandler = ( copy: () => void, sendTelemetry: ({ action, metric }: SendTelemetryHelper) => void diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/generate_api_key/generate_api_key_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/generate_api_key/generate_api_key_logic.ts new file mode 100644 index 0000000000000..d5d0f6c691dd2 --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/generate_api_key/generate_api_key_logic.ts @@ -0,0 +1,36 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { createApiLogic } from '../../../shared/api_logic/create_api_logic'; +import { HttpLogic } from '../../../shared/http'; + +interface APIKeyResponse { + apiKey: { + api_key: string; + encoded: string; + id: string; + name: string; + }; +} + +export const generateApiKey = async ({ + indexName, + keyName, +}: { + indexName: string; + keyName: string; +}) => { + const route = `/internal/enterprise_search/${indexName}/api_keys`; + + return await HttpLogic.values.http.post<APIKeyResponse>(route, { + body: JSON.stringify({ + keyName, + }), + }); +}; + +export const GenerateApiKeyLogic = createApiLogic(['generate_api_key_logic'], generateApiKey); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts index 87ab8ecc700ba..96a5061fff039 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/api/index/fetch_index_api_logic.ts @@ -9,6 +9,8 @@ import { createApiLogic } from '../../../shared/api_logic/create_api_logic'; import { HttpLogic } from '../../../shared/http'; import { IndexData } from '../../types'; +export type { IndexData } from '../../types'; + export const fetchIndex = async ({ indexName }: { indexName: string }) => { const route = `/internal/enterprise_search/indices/${indexName}`; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/api_key/api_key.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/api_key/api_key.tsx index f24fc6234d0c8..1fc67699c9a6d 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/api_key/api_key.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/api_key/api_key.tsx @@ -7,23 +7,36 @@ import React from 'react'; -import { EuiCodeBlock, EuiFormLabel, EuiSpacer } from '@elastic/eui'; +import { EuiCodeBlock, EuiFormLabel, EuiSpacer, EuiFlexGroup, EuiFlexItem } from '@elastic/eui'; interface ApiKeyProps { + actions?: React.ReactNode; apiKey: string; label?: string; } -export const ApiKey: React.FC<ApiKeyProps> = ({ apiKey, label }) => ( - <> - {label && ( - <> - <EuiFormLabel>{label}</EuiFormLabel> - <EuiSpacer size="xs" /> - </> - )} +export const ApiKey: React.FC<ApiKeyProps> = ({ apiKey, label, actions }) => { + const codeBlock = ( <EuiCodeBlock fontSize="m" paddingSize="m" color="dark" isCopyable> {apiKey} </EuiCodeBlock> - </> -); + ); + return ( + <> + {label && ( + <> + <EuiFormLabel>{label}</EuiFormLabel> + <EuiSpacer size="xs" /> + </> + )} + {actions ? ( + <EuiFlexGroup alignItems="center"> + <EuiFlexItem>{codeBlock}</EuiFlexItem> + <EuiFlexItem grow={false}>{actions}</EuiFlexItem> + </EuiFlexGroup> + ) : ( + codeBlock + )} + </> + ); +}; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.test.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.test.tsx new file mode 100644 index 0000000000000..50fbf06e65c60 --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.test.tsx @@ -0,0 +1,97 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { setMockValues, setMockActions } from '../../../../../__mocks__/kea_logic'; +import '../../../../../shared/doc_links/__mocks__/doc_links.mock'; + +import React from 'react'; + +import { shallow } from 'enzyme'; + +import { EuiContextMenuItem, EuiContextMenuPanel } from '@elastic/eui'; + +import { docLinks } from '../../../../../shared/doc_links'; + +import { ClientLibrariesPopover } from './popover'; + +const librariesList = [ + { + href: docLinks.clientsJavaIntroduction, + + text: 'Java', + }, + { + href: docLinks.clientsJsIntro, + + text: 'Javascript / Node', + }, + { + href: docLinks.clientsRubyOverview, + + text: 'Ruby', + }, + { + href: docLinks.clientsGoIndex, + + text: 'Go', + }, + { + href: docLinks.clientsNetIntroduction, + + text: '.NET', + }, + { + href: docLinks.clientsPhpGuide, + text: 'PHP', + }, + { + href: docLinks.clientsPerlGuide, + text: 'Perl', + }, + { + href: docLinks.clientsPythonOverview, + text: 'Python', + }, + { + href: docLinks.clientsRustOverview, + text: 'Rust', + }, +]; + +const mockValues = { + isClientsPopoverOpen: false, +}; + +const mockActions = { toggleClientsPopover: jest.fn() }; + +describe('ClientLibrariesPopover', () => { + beforeEach(() => { + jest.clearAllMocks(); + }); + + it('should render all urls correctly', () => { + setMockValues({ + ...mockValues, + indices: [], + }); + setMockActions(mockActions); + + const wrapper = shallow(<ClientLibrariesPopover />); + const contextMenuItems = + wrapper + .find(EuiContextMenuPanel) + .prop('items') + ?.map((item) => shallow(<div>{item}</div>)) || []; + + expect(contextMenuItems.length > 0).toBeTruthy(); + + contextMenuItems.forEach((item, index) => { + const menuItem = item.find(EuiContextMenuItem); + expect(menuItem.prop('href')).toEqual(librariesList[index].href); + }); + }); +}); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.tsx new file mode 100644 index 0000000000000..b89f489952ab8 --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/client_libraries_popover/popover.tsx @@ -0,0 +1,131 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ +import React from 'react'; + +import { useActions, useValues } from 'kea'; + +import { + EuiPopover, + EuiButton, + EuiContextMenuPanel, + EuiContextMenuItem, + EuiText, +} from '@elastic/eui'; + +import { i18n } from '@kbn/i18n'; + +import { docLinks } from '../../../../../shared/doc_links'; + +import { OverviewLogic } from '../../overview.logic'; + +const libraries = [ + { + href: docLinks.clientsJavaIntroduction, + key: 'java', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.java', + { defaultMessage: 'Java' } + ), + }, + { + href: docLinks.clientsJsIntro, + key: 'javascript', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.javascript', + { defaultMessage: 'Javascript / Node' } + ), + }, + { + href: docLinks.clientsRubyOverview, + key: 'ruby', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.ruby', + { defaultMessage: 'Ruby' } + ), + }, + { + href: docLinks.clientsGoIndex, + key: 'go', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.go', + { defaultMessage: 'Go' } + ), + }, + { + href: docLinks.clientsNetIntroduction, + key: 'dotnet', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.dotnet', + { defaultMessage: '.NET' } + ), + }, + { + href: docLinks.clientsPhpGuide, + key: 'php', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.php', + { defaultMessage: 'PHP' } + ), + }, + { + href: docLinks.clientsPerlGuide, + key: 'perl', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.perl', + { defaultMessage: 'Perl' } + ), + }, + { + href: docLinks.clientsPythonOverview, + key: 'python', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.python', + { defaultMessage: 'Python' } + ), + }, + { + href: docLinks.clientsRustOverview, + key: 'rust', + text: i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.clientLibraries.rust', + { defaultMessage: 'Rust' } + ), + }, +]; + +export const ClientLibrariesPopover: React.FC = () => { + const { isClientsPopoverOpen } = useValues(OverviewLogic); + const { toggleClientsPopover } = useActions(OverviewLogic); + + return ( + <EuiPopover + isOpen={isClientsPopoverOpen} + closePopover={toggleClientsPopover} + button={ + <EuiButton iconType="arrowDown" iconSide="right" onClick={toggleClientsPopover}> + {i18n.translate( + 'xpack.enterpriseSearch.content,overview.documentExample.clientLibraries.label', + { defaultMessage: 'Client Libraries' } + )} + </EuiButton> + } + > + <EuiContextMenuPanel + size="s" + items={libraries.map((item) => { + return ( + <EuiContextMenuItem key={item.key} href={item.href} target="_blank"> + <EuiText> + <p>{item.text}</p> + </EuiText> + </EuiContextMenuItem> + ); + })} + /> + </EuiPopover> + ); +}; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.test.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.test.ts new file mode 100644 index 0000000000000..596ec459bc992 --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.test.ts @@ -0,0 +1,153 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { LogicMounter, mockFlashMessageHelpers } from '../../../../../__mocks__/kea_logic'; + +import { HttpError, Status } from '../../../../../../../common/types/api'; +import { GenerateApiKeyLogic } from '../../../../api/generate_api_key/generate_api_key_logic'; + +import { GenerateApiKeyModalLogic } from './generate_api_key_modal.logic'; + +const DEFAULT_VALUES = { + apiKey: '', + data: undefined, + isLoading: false, + isSuccess: false, + keyName: '', + status: Status.IDLE, +}; + +describe('IndicesLogic', () => { + const { mount: apiLogicMount } = new LogicMounter(GenerateApiKeyLogic); + const { mount } = new LogicMounter(GenerateApiKeyModalLogic); + + beforeEach(() => { + jest.clearAllMocks(); + apiLogicMount(); + mount(); + }); + + it('has expected default values', () => { + expect(GenerateApiKeyModalLogic.values).toEqual(DEFAULT_VALUES); + }); + + describe('actions', () => { + describe('setKeyName', () => { + it('sets keyName value to the reducer', () => { + const keyName = 'test-key-name 8888*^7896&*^*&'; + expect(GenerateApiKeyModalLogic.values).toEqual(DEFAULT_VALUES); + GenerateApiKeyModalLogic.actions.setKeyName(keyName); + expect(GenerateApiKeyModalLogic.values).toEqual({ + ...DEFAULT_VALUES, + keyName, + }); + }); + }); + }); + + describe('reducers', () => { + describe('keyName', () => { + it('updates when setKeyName action is triggered', () => { + const keyName = 'test-key-name'; + expect(GenerateApiKeyModalLogic.values).toEqual(DEFAULT_VALUES); + GenerateApiKeyModalLogic.actions.setKeyName(keyName); + expect(GenerateApiKeyModalLogic.values).toEqual({ + ...DEFAULT_VALUES, + keyName, + }); + }); + }); + }); + + describe('listeners', () => { + it('calls clearFlashMessages on new makeRequest', () => { + GenerateApiKeyModalLogic.actions.makeRequest({ indexName: 'test', keyName: 'test' }); + expect(mockFlashMessageHelpers.clearFlashMessages).toHaveBeenCalledTimes(1); + }); + + it('calls flashAPIErrors on apiError', () => { + GenerateApiKeyModalLogic.actions.apiError({} as HttpError); + expect(mockFlashMessageHelpers.flashAPIErrors).toHaveBeenCalledTimes(1); + expect(mockFlashMessageHelpers.flashAPIErrors).toHaveBeenCalledWith({}); + }); + }); + + describe('selectors', () => { + describe('apiKey', () => { + it('updates when apiSuccess listener triggered', () => { + expect(GenerateApiKeyModalLogic.values).toEqual(DEFAULT_VALUES); + GenerateApiKeyLogic.actions.apiSuccess({ + apiKey: { + api_key: 'some-api-key-123123', + encoded: 'encoded-api-key123123==', + id: 'api_key_id', + name: 'test-key-123', + }, + }); + + expect(GenerateApiKeyModalLogic.values).toEqual({ + apiKey: 'encoded-api-key123123==', + data: { + apiKey: { + api_key: 'some-api-key-123123', + encoded: 'encoded-api-key123123==', + id: 'api_key_id', + name: 'test-key-123', + }, + }, + isLoading: false, + isSuccess: true, + keyName: '', + status: Status.SUCCESS, + }); + }); + }); + + describe('isLoading', () => { + it('should update with API status', () => { + expect(GenerateApiKeyModalLogic.values).toEqual(DEFAULT_VALUES); + GenerateApiKeyModalLogic.actions.makeRequest({ indexName: 'test', keyName: 'test' }); + + expect(GenerateApiKeyModalLogic.values).toEqual({ + ...DEFAULT_VALUES, + isLoading: true, + status: Status.LOADING, + }); + }); + }); + + describe('isSuccess', () => { + it('should update with API status', () => { + expect(GenerateApiKeyModalLogic.values).toEqual(DEFAULT_VALUES); + GenerateApiKeyLogic.actions.apiSuccess({ + apiKey: { + api_key: 'some-api-key-123123', + encoded: 'encoded-api-key123123==', + id: 'api_key_id', + name: 'test-key-123', + }, + }); + + expect(GenerateApiKeyModalLogic.values).toEqual({ + apiKey: 'encoded-api-key123123==', + data: { + apiKey: { + api_key: 'some-api-key-123123', + encoded: 'encoded-api-key123123==', + id: 'api_key_id', + name: 'test-key-123', + }, + }, + isLoading: false, + isSuccess: true, + keyName: '', + status: Status.SUCCESS, + }); + }); + }); + }); +}); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.ts new file mode 100644 index 0000000000000..654a984a171ca --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/generate_api_key_modal.logic.ts @@ -0,0 +1,59 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { kea, MakeLogicType } from 'kea'; + +import { HttpError, Status } from '../../../../../../../common/types/api'; + +import { flashAPIErrors, clearFlashMessages } from '../../../../../shared/flash_messages'; + +import { GenerateApiKeyLogic } from '../../../../api/generate_api_key/generate_api_key_logic'; + +interface GenerateApiKeyModalActions { + apiError(error: HttpError): HttpError; + makeRequest: typeof GenerateApiKeyLogic.actions.makeRequest; + setKeyName(keyName: string): { keyName: string }; +} + +interface GenerateApiKeyModalValues { + apiKey: string; + data: typeof GenerateApiKeyLogic.values.data; + isLoading: boolean; + isSuccess: boolean; + keyName: string; + status: typeof GenerateApiKeyLogic.values.status; +} + +export const GenerateApiKeyModalLogic = kea< + MakeLogicType<GenerateApiKeyModalValues, GenerateApiKeyModalActions> +>({ + actions: { + setKeyName: (keyName) => ({ keyName }), + }, + connect: { + actions: [GenerateApiKeyLogic, ['makeRequest', 'apiError']], + values: [GenerateApiKeyLogic, ['data', 'status']], + }, + listeners: () => ({ + apiError: (e) => flashAPIErrors(e), + makeRequest: () => clearFlashMessages(), + }), + path: ['enterprise_search', 'search_index', 'generate_api_key_modal'], + reducers: () => ({ + keyName: [ + '', + { + setKeyName: (_, { keyName }) => keyName, + }, + ], + }), + selectors: ({ selectors }) => ({ + apiKey: [() => [selectors.data], (data) => data?.apiKey?.encoded || ''], + isLoading: [() => [selectors.status], (status) => status === Status.LOADING], + isSuccess: [() => [selectors.status], (status) => status === Status.SUCCESS], + }), +}); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.test.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.test.tsx new file mode 100644 index 0000000000000..325d52ab2d2fd --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.test.tsx @@ -0,0 +1,91 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { setMockValues, setMockActions } from '../../../../../__mocks__/kea_logic'; + +import React from 'react'; + +import { shallow } from 'enzyme'; + +import { EuiModal, EuiFieldText } from '@elastic/eui'; + +const mockActions = { makeRequest: jest.fn(), setKeyName: jest.fn() }; + +const mockValues = { apiKey: '', isLoading: false, isSuccess: false, keyName: '' }; + +import { ApiKey } from '../../../api_key/api_key'; + +import { GenerateApiKeyModal } from './modal'; + +const onCloseMock = jest.fn(); +describe('GenerateApiKeyModal', () => { + beforeEach(() => { + jest.clearAllMocks(); + setMockValues(mockValues); + setMockActions(mockActions); + }); + + it('renders the empty modal', () => { + const wrapper = shallow( + <GenerateApiKeyModal indexName="test-index-123" onClose={onCloseMock} /> + ); + expect(wrapper.find(EuiModal)).toHaveLength(1); + + wrapper.find(EuiModal).prop('onClose')(); + expect(onCloseMock).toHaveBeenCalled(); + }); + + describe('Modal content', () => { + it('renders API key name form', () => { + const wrapper = shallow( + <GenerateApiKeyModal indexName="test-index-123" onClose={onCloseMock} /> + ); + expect(wrapper.find(EuiFieldText)).toHaveLength(1); + expect(wrapper.find('[data-test-subj="generateApiKeyButton"]')).toHaveLength(1); + }); + + it('sets keyName name on form', () => { + const wrapper = shallow( + <GenerateApiKeyModal indexName="test-index-123" onClose={onCloseMock} /> + ); + const textField = wrapper.find(EuiFieldText); + expect(textField).toHaveLength(1); + textField.simulate('change', { currentTarget: { value: 'changeEvent-key-name' } }); + expect(mockActions.setKeyName).toHaveBeenCalledWith('changeEvent-key-name'); + }); + + it('should trigger api call from the form', () => { + setMockValues({ ...mockValues, indexName: 'test-123', keyName: ' with-spaces ' }); + const wrapper = shallow( + <GenerateApiKeyModal indexName="test-index-123" onClose={onCloseMock} /> + ); + expect(wrapper.find(EuiFieldText)).toHaveLength(1); + wrapper.find('[data-test-subj="generateApiKeyButton"]').simulate('click'); + + expect(mockActions.makeRequest).toHaveBeenCalledWith({ + indexName: 'test-index-123', + keyName: 'with-spaces', + }); + }); + it('renders created API key results', () => { + setMockValues({ + ...mockValues, + apiKey: 'apiKeyFromBackend123123==', + indexName: 'test-123', + isSuccess: true, + keyName: 'keyname', + }); + const wrapper = shallow( + <GenerateApiKeyModal indexName="test-index-123" onClose={onCloseMock} /> + ); + expect(wrapper.find(EuiFieldText)).toHaveLength(0); + expect(wrapper.find('[data-test-subj="generateApiKeyButton"]')).toHaveLength(0); + expect(wrapper.find(ApiKey)).toHaveLength(1); + expect(wrapper.find(ApiKey).prop('apiKey')).toEqual('apiKeyFromBackend123123=='); + }); + }); +}); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.tsx new file mode 100644 index 0000000000000..7ab10db5d9ccf --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/generate_api_key_modal/modal.tsx @@ -0,0 +1,158 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; + +import { useValues, useActions } from 'kea'; + +import { + EuiModal, + EuiModalHeader, + EuiModalHeaderTitle, + EuiModalBody, + EuiModalFooter, + EuiFlexGroup, + EuiFlexItem, + EuiPanel, + EuiButton, + EuiButtonEmpty, + EuiButtonIcon, + EuiFieldText, + EuiFormRow, + EuiText, + EuiSpacer, + EuiLink, +} from '@elastic/eui'; + +import { i18n } from '@kbn/i18n'; + +import { ApiKey } from '../../../api_key/api_key'; + +import { GenerateApiKeyModalLogic } from './generate_api_key_modal.logic'; + +interface GenerateApiKeyModalProps { + indexName: string; + onClose(): void; +} + +export const GenerateApiKeyModal: React.FC<GenerateApiKeyModalProps> = ({ indexName, onClose }) => { + const { keyName, apiKey, isLoading, isSuccess } = useValues(GenerateApiKeyModalLogic); + const { setKeyName, makeRequest } = useActions(GenerateApiKeyModalLogic); + + return ( + <EuiModal onClose={onClose}> + <EuiModalHeader> + <EuiModalHeaderTitle> + {i18n.translate('xpack.enterpriseSearch.content.overview.generateApiKeyModal.title', { + defaultMessage: 'Generate API Key', + })} + </EuiModalHeaderTitle> + </EuiModalHeader> + <EuiModalBody> + <> + <EuiText size="m"> + <p> + {i18n.translate('xpack.enterpriseSearch.content.overview.generateApiKeyModal.info', { + defaultMessage: + "Before you can start posting documents to your Elasticsearch index you'll need to create at least one API key.", + })} +   + <EuiLink href={/* TODO link to docs */ '#'} external> + {i18n.translate( + 'xpack.enterpriseSearch.content.overview.generateApiKeyModal.learnMore', + { defaultMessage: 'Learn more about API keys' } + )} + </EuiLink> + </p> + </EuiText> + <EuiSpacer /> + <EuiPanel hasShadow={false} color="primary"> + <EuiFlexGroup direction="column"> + <EuiFlexItem> + <EuiFlexGroup direction="row" alignItems="flexEnd"> + {!isSuccess ? ( + <> + <EuiFlexItem> + <EuiFormRow label="Name your API key" fullWidth> + <EuiFieldText + fullWidth + placeholder="Type a name for your API key" + onChange={(event) => setKeyName(event.currentTarget.value)} + isLoading={isLoading} + /> + </EuiFormRow> + </EuiFlexItem> + + <EuiFlexItem grow={false}> + <EuiButton + data-test-subj="generateApiKeyButton" + iconSide="left" + iconType="plusInCircle" + fill + onClick={() => { + makeRequest({ + indexName, + keyName: keyName.trim(), + }); + }} + disabled={keyName.trim().length <= 0} + > + {i18n.translate( + 'xpack.enterpriseSearch.content.overview.generateApiKeyModal.generateButton', + { + defaultMessage: 'Generate API key', + } + )} + </EuiButton> + </EuiFlexItem> + </> + ) : ( + <ApiKey + apiKey={apiKey} + label={keyName} + actions={ + <EuiButtonIcon + iconType="download" + href={encodeURI(`data:text/csv;charset=utf-8,${apiKey}`)} + download={`${keyName}.csv`} + /> + } + /> + )} + </EuiFlexGroup> + </EuiFlexItem> + <EuiFlexItem> + <EuiFlexGroup direction="row"> + <EuiFlexItem> + <EuiText size="s" color="#006bb8"> + <p> + {i18n.translate( + 'xpack.enterpriseSearch.content.overview.generateApiKeyModal.apiKeyWarning', + { + defaultMessage: + "Elastic does not store API keys. Once generated, you'll only be able to view the key one time. Make sure you save it somewhere secure. If you lose access to it you'll need to generate a new API key from this screen.", + } + )} + </p> + </EuiText> + </EuiFlexItem> + </EuiFlexGroup> + </EuiFlexItem> + </EuiFlexGroup> + </EuiPanel> + </> + </EuiModalBody> + <EuiModalFooter> + <EuiButtonEmpty onClick={onClose}> + {i18n.translate('xpack.enterpriseSearch.content.overview.generateApiKeyModal.cancel', { + defaultMessage: 'Cancel', + })} + </EuiButtonEmpty> + </EuiModalFooter> + </EuiModal> + ); +}; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.logic.ts new file mode 100644 index 0000000000000..2e13e60006822 --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.logic.ts @@ -0,0 +1,33 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { kea, MakeLogicType } from 'kea'; + +interface HeaderActionsLogicValues { + isSearchEnginesPopoverOpen: boolean; +} + +interface HeaderActionsLogicActions { + toggleSearchEnginesPopover: void; +} + +export const HeaderActionsLogic = kea< + MakeLogicType<HeaderActionsLogicValues, HeaderActionsLogicActions> +>({ + actions: { + toggleSearchEnginesPopover: true, + }, + path: ['enterprise_search', 'search_index', 'header'], + reducers: () => ({ + isSearchEnginesPopoverOpen: [ + false, + { + toggleSearchEnginesPopover: (state) => !state, + }, + ], + }), +}); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.tsx new file mode 100644 index 0000000000000..a03f2736a8584 --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/header_actions/header_actions.tsx @@ -0,0 +1,85 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; + +import { useActions, useValues } from 'kea'; + +import { + EuiButton, + EuiPopover, + EuiContextMenuPanel, + EuiContextMenuItem, + EuiText, +} from '@elastic/eui'; + +import { i18n } from '@kbn/i18n'; + +import { APP_SEARCH_PLUGIN } from '../../../../../../../common/constants'; +import { ENGINE_CREATION_PATH } from '../../../../../app_search/routes'; +import { KibanaLogic } from '../../../../../shared/kibana'; + +import { HeaderActionsLogic } from './header_actions.logic'; + +const SearchEnginesPopover: React.FC = () => { + const { isSearchEnginesPopoverOpen } = useValues(HeaderActionsLogic); + const { toggleSearchEnginesPopover } = useActions(HeaderActionsLogic); + + return ( + <EuiPopover + isOpen={isSearchEnginesPopoverOpen} + closePopover={toggleSearchEnginesPopover} + button={ + <EuiButton iconSide="right" iconType="arrowDown" onClick={toggleSearchEnginesPopover}> + {i18n.translate('xpack.enterpriseSearch.content.index.searchEngines.label', { + defaultMessage: 'Search Engines', + })} + </EuiButton> + } + > + <EuiContextMenuPanel + size="s" + items={[ + <EuiContextMenuItem + icon="eye" + onClick={() => { + KibanaLogic.values.navigateToUrl(APP_SEARCH_PLUGIN.URL, { + shouldNotCreateHref: true, + }); + }} + > + <EuiText> + <p> + {i18n.translate('xpack.enterpriseSearch.content.index.searchEngines.viewEngines', { + defaultMessage: 'View App Search engines', + })} + </p> + </EuiText> + </EuiContextMenuItem>, + <EuiContextMenuItem + icon="plusInCircle" + onClick={() => { + KibanaLogic.values.navigateToUrl(APP_SEARCH_PLUGIN.URL + ENGINE_CREATION_PATH, { + shouldNotCreateHref: true, + }); + }} + > + <EuiText> + <p> + {i18n.translate('xpack.enterpriseSearch.content.index.searchEngines.createEngine', { + defaultMessage: 'Create a new App Search engine', + })} + </p> + </EuiText> + </EuiContextMenuItem>, + ]} + /> + </EuiPopover> + ); +}; + +export const headerActions = [<SearchEnginesPopover />]; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout.tsx new file mode 100644 index 0000000000000..b16528b00dc9a --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout.tsx @@ -0,0 +1,78 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; + +import { useActions } from 'kea'; + +import { + EuiButton, + EuiLink, + EuiText, + EuiCallOut, + EuiFlexGroup, + EuiFlexItem, + EuiSpacer, +} from '@elastic/eui'; + +import { i18n } from '@kbn/i18n'; + +import { IndexCreatedCalloutLogic } from './callout_logic'; + +interface IndexCreatedCalloutProps { + indexName: string; +} + +export const IndexCreatedCallout: React.FC<IndexCreatedCalloutProps> = ({ indexName }) => { + const { dismissIndexCreatedCallout } = useActions(IndexCreatedCalloutLogic); + return ( + <EuiCallOut + color="success" + iconType="check" + title={i18n.translate('xpack.enterpriseSearch.content.index.indexCreatedCallout.title', { + defaultMessage: 'Elasticsearch index created successfully', + })} + > + <EuiText size="m"> + {i18n.translate('xpack.enterpriseSearch.content.index.indexCreatedCallout.info', { + defaultMessage: + 'You can use App Search engines to build a search experience for your new Elasticsearch index.', + })} + <EuiLink external href={/* TODO */ '#'}> + {i18n.translate('xpack.enterpriseSearch.content.index.readDocumentation.link', { + defaultMessage: 'Read the documentation', + })} + </EuiLink> + </EuiText> + <EuiSpacer /> + <EuiFlexGroup> + <EuiFlexItem grow={false}> + <EuiButton + fill + color="success" + onClick={() => { + // TODO bind it to AppSearch + // eslint-disable-next-line + console.log(indexName); + }} + > + {i18n.translate('xpack.enterpriseSearch.content.index.createAppSearchEngine.button', { + defaultMessage: 'Create an App Search engine', + })} + </EuiButton> + </EuiFlexItem> + <EuiFlexItem grow={false}> + <EuiButton color="success" iconType="cross" onClick={dismissIndexCreatedCallout}> + {i18n.translate('xpack.enterpriseSearch.content.index.dismiss.button', { + defaultMessage: 'Dismiss', + })} + </EuiButton> + </EuiFlexItem> + </EuiFlexGroup> + </EuiCallOut> + ); +}; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout_logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout_logic.ts new file mode 100644 index 0000000000000..d8421137a859d --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/index_created_callout/callout_logic.ts @@ -0,0 +1,36 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { kea, MakeLogicType } from 'kea'; + +interface IndexCreatedCalloutLogicValues { + isCalloutVisible: boolean; +} + +interface IndexCreatedCalloutLogicActions { + dismissIndexCreatedCallout: void; + showIndexCreatedCallout: void; +} + +export const IndexCreatedCalloutLogic = kea< + MakeLogicType<IndexCreatedCalloutLogicValues, IndexCreatedCalloutLogicActions> +>({ + actions: { + dismissIndexCreatedCallout: true, + showIndexCreatedCallout: true, + }, + path: ['enterprise_search', 'search_index', 'index_created_callout'], + reducers: () => ({ + isCalloutVisible: [ + false, + { + dismissIndexCreatedCallout: () => false, + showIndexCreatedCallout: () => true, + }, + ], + }), +}); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/manage_api_keys_popover/popover.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/manage_api_keys_popover/popover.tsx new file mode 100644 index 0000000000000..b4b7e9bb038de --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/components/manage_api_keys_popover/popover.tsx @@ -0,0 +1,77 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import React from 'react'; + +import { useActions, useValues } from 'kea'; + +import { + EuiPopover, + EuiButton, + EuiContextMenuPanel, + EuiContextMenuItem, + EuiText, +} from '@elastic/eui'; + +import { i18n } from '@kbn/i18n'; + +import { KibanaLogic } from '../../../../../shared/kibana'; + +import { OverviewLogic } from '../../overview.logic'; + +export const ManageKeysPopover: React.FC = () => { + const { isManageKeysPopoverOpen } = useValues(OverviewLogic); + const { toggleManageApiKeyPopover, openGenerateModal } = useActions(OverviewLogic); + + return ( + <EuiPopover + isOpen={isManageKeysPopoverOpen} + closePopover={toggleManageApiKeyPopover} + button={ + <EuiButton fill iconType="arrowDown" iconSide="right" onClick={toggleManageApiKeyPopover}> + {i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.generateApiKeyButton.label', + { defaultMessage: 'Manage API keys' } + )} + </EuiButton> + } + > + <EuiContextMenuPanel + size="s" + items={[ + <EuiContextMenuItem + icon="eye" + onClick={() => + KibanaLogic.values.navigateToUrl('/app/management/security/api_keys', { + shouldNotCreateHref: true, + }) + } + > + <EuiText> + <p> + {i18n.translate( + 'xpack.enterpriseSearch.content.overview.documementExample.generateApiKeyButton.viewAll', + { defaultMessage: 'View all API keys' } + )} + </p> + </EuiText> + </EuiContextMenuItem>, + <EuiContextMenuItem icon="plusInCircle" onClick={openGenerateModal}> + <EuiText> + <p> + {i18n.translate( + 'xpack.enterpriseSearch.content.overview.documementExample.generateApiKeyButton.createNew', + { defaultMessage: 'Create a new API key' } + )} + </p> + </EuiText> + </EuiContextMenuItem>, + ]} + /> + </EuiPopover> + ); +}; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/generate_api_key_panel.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/generate_api_key_panel.tsx index c3148876608e6..0f2436d776eb4 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/generate_api_key_panel.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/generate_api_key_panel.tsx @@ -7,60 +7,100 @@ import React from 'react'; +import { useActions, useValues } from 'kea'; + import { + EuiCodeBlock, EuiFlexGroup, EuiFlexItem, EuiPanel, - EuiText, - EuiButtonIcon, - EuiButton, - EuiCodeBlock, + EuiSpacer, + EuiTitle, } from '@elastic/eui'; -import { getEnterpriseSearchUrl } from '../../../shared/enterprise_search_url'; +import { i18n } from '@kbn/i18n'; + +import { useCloudDetails } from '../../../shared/cloud_details/cloud_details'; import { DOCUMENTS_API_JSON_EXAMPLE } from '../new_index/constants'; +import { ClientLibrariesPopover } from './components/client_libraries_popover/popover'; +import { GenerateApiKeyModal } from './components/generate_api_key_modal/modal'; +import { ManageKeysPopover } from './components/manage_api_keys_popover/popover'; + +import { OverviewLogic } from './overview.logic'; + +const getDeploymentUrls = (cloudId: string) => { + const [host, kibanaHost, elasticHost] = window.atob(cloudId); + return { + elasticUrl: `https://${elasticHost}.${host}`, + kibanaUrl: `https://${kibanaHost}.${host}`, + }; +}; export const GenerateApiKeyPanel: React.FC = () => { - const searchIndexApiUrl = getEnterpriseSearchUrl('/api/ent/v1/search_indices/'); - const apiKey = 'Create an API Key'; + const { apiKey, isGenerateModalOpen, indexData } = useValues(OverviewLogic); + const { closeGenerateModal } = useActions(OverviewLogic); + + const cloudContext = useCloudDetails(); + const searchIndexApiUrl = cloudContext.cloudId + ? getDeploymentUrls(cloudContext.cloudId).elasticUrl + : '<elasticsearch-host>:<elasticsearch-port>/'; + + const apiKeyExample = apiKey || '<Create an API Key>'; return ( - <EuiFlexGroup> - <EuiFlexItem> - <EuiPanel> - <EuiFlexGroup direction="column"> - <EuiFlexItem> - <EuiFlexGroup justifyContent="spaceBetween" alignItems="center"> - <EuiFlexItem> - <EuiText> - <h2>Indexing by API</h2> - </EuiText> - </EuiFlexItem> - <EuiFlexItem grow={false}> - <EuiFlexGroup justifyContent="flexEnd" alignItems="center"> - <EuiFlexItem> - <EuiButtonIcon iconType="iInCircle" /> - </EuiFlexItem> - <EuiFlexItem> - <EuiButton>Generate an API key</EuiButton> - </EuiFlexItem> - </EuiFlexGroup> - </EuiFlexItem> - </EuiFlexGroup> - </EuiFlexItem> - <EuiFlexItem> - <EuiCodeBlock language="bash" fontSize="m" isCopyable> - {`\ -curl -X POST '${searchIndexApiUrl}${name}/document' \\ --H 'Content-Type: application/json' \\ --H 'Authorization: Bearer ${apiKey}' \\ --d '${JSON.stringify(DOCUMENTS_API_JSON_EXAMPLE, null, 2)}' + <> + {isGenerateModalOpen && ( + <GenerateApiKeyModal indexName={indexData.index.name} onClose={closeGenerateModal} /> + )} + <EuiFlexGroup> + <EuiFlexItem> + <EuiPanel> + <EuiFlexGroup direction="column"> + <EuiFlexItem> + <EuiFlexGroup justifyContent="spaceBetween" alignItems="center"> + <EuiFlexItem> + {indexData.index.name[0] !== '.' && ( + <EuiTitle size="s"> + <h2> + {i18n.translate( + 'xpack.enterpriseSearch.content.overview.documentExample.title', + { defaultMessage: 'Adding documents to your index' } + )} + </h2> + </EuiTitle> + )} + </EuiFlexItem> + <EuiFlexItem grow={false}> + <EuiFlexGroup justifyContent="flexEnd" alignItems="center"> + <EuiFlexItem> + <ClientLibrariesPopover /> + </EuiFlexItem> + <EuiFlexItem> + <ManageKeysPopover /> + </EuiFlexItem> + </EuiFlexGroup> + </EuiFlexItem> + </EuiFlexGroup> + </EuiFlexItem> + {indexData.index.name[0] !== '.' && ( + <> + <EuiSpacer /> + <EuiFlexItem> + <EuiCodeBlock language="bash" fontSize="m" isCopyable> + {`\ +curl -X POST '${searchIndexApiUrl}${indexData.index.name}/_doc' \\ + -H 'Content-Type: application/json' \\ + -H 'Authorization: ApiKey ${apiKeyExample}' \\ + -d '${JSON.stringify(DOCUMENTS_API_JSON_EXAMPLE, null, 2)}' `} - </EuiCodeBlock> - </EuiFlexItem> - </EuiFlexGroup> - </EuiPanel> - </EuiFlexItem> - </EuiFlexGroup> + </EuiCodeBlock> + </EuiFlexItem> + </> + )} + </EuiFlexGroup> + </EuiPanel> + </EuiFlexItem> + </EuiFlexGroup> + </> ); }; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.logic.ts b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.logic.ts new file mode 100644 index 0000000000000..bc8b7a402eddc --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.logic.ts @@ -0,0 +1,91 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { kea, MakeLogicType } from 'kea'; + +import { Status } from '../../../../../common/types/api'; + +import { GenerateApiKeyLogic } from '../../api/generate_api_key/generate_api_key_logic'; +import { FetchIndexApiLogic, IndexData } from '../../api/index/fetch_index_api_logic'; + +interface OverviewLogicActions { + apiReset: typeof GenerateApiKeyLogic.actions.apiReset; + closeGenerateModal: void; + openGenerateModal: void; + toggleClientsPopover: void; + toggleManageApiKeyPopover: void; +} + +interface OverviewLogicValues { + apiKey: string; + apiKeyData: typeof GenerateApiKeyLogic.values.data; + apiKeyStatus: typeof GenerateApiKeyLogic.values.status; + data: typeof FetchIndexApiLogic.values.data; + indexData: IndexData; + isClientsPopoverOpen: boolean; + isGenerateModalOpen: boolean; + isLoading: boolean; + isManageKeysPopoverOpen: boolean; + isSuccess: boolean; + status: typeof FetchIndexApiLogic.values.status; +} + +export const OverviewLogic = kea<MakeLogicType<OverviewLogicValues, OverviewLogicActions>>({ + actions: { + closeGenerateModal: true, + openGenerateModal: true, + toggleClientsPopover: true, + toggleManageApiKeyPopover: true, + }, + connect: { + actions: [GenerateApiKeyLogic, ['apiReset']], + values: [ + FetchIndexApiLogic, + ['data', 'status'], + GenerateApiKeyLogic, + ['data as apiKeyData', 'status as apiKeyStatus'], + ], + }, + listeners: ({ actions }) => ({ + openGenerateModal: () => { + actions.apiReset(); + }, + }), + path: ['enterprise_search', 'search_index', 'overview'], + reducers: () => ({ + isClientsPopoverOpen: [ + false, + { + toggleClientsPopover: (state) => !state, + }, + ], + isGenerateModalOpen: [ + false, + { + closeGenerateModal: () => false, + openGenerateModal: () => true, + }, + ], + isManageKeysPopoverOpen: [ + false, + { + openGenerateModal: () => false, + toggleManageApiKeyPopover: (state) => !state, + }, + ], + }), + selectors: ({ selectors }) => ({ + apiKey: [ + () => [selectors.apiKeyStatus, selectors.apiKeyData], + (apiKeyStatus, apiKeyData) => + apiKeyStatus === Status.SUCCESS ? apiKeyData.apiKey.api_key : '', + ], + indexData: [() => [selectors.data], (data) => data], + isLoading: [() => [selectors.status], (status) => status === Status.LOADING], + isSuccess: [() => [selectors.status], (status) => status === Status.SUCCESS], + }), +}); diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.tsx index 774783f9da473..691ecd973a910 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/overview.tsx @@ -13,19 +13,18 @@ import { EuiSpacer } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; -import { FetchIndexApiLogic } from '../../api/index/fetch_index_api_logic'; - import { CrawlDetailsFlyout } from './crawler/crawl_details_flyout/crawl_details_flyout'; import { CrawlRequestsPanel } from './crawler/crawl_requests_panel/crawl_requests_panel'; import { CrawlerTotalStats } from './crawler_total_stats'; import { GenerateApiKeyPanel } from './generate_api_key_panel'; +import { OverviewLogic } from './overview.logic'; import { TotalStats } from './total_stats'; export const SearchIndexOverview: React.FC = () => { - const { data } = useValues(FetchIndexApiLogic); + const { indexData } = useValues(OverviewLogic); - const isCrawler = typeof data?.crawler !== 'undefined'; - const isConnector = typeof data?.connector !== 'undefined'; + const isCrawler = typeof indexData?.crawler !== 'undefined'; + const isConnector = typeof indexData?.connector !== 'undefined'; const isApi = !(isCrawler || isConnector); return ( @@ -52,7 +51,6 @@ export const SearchIndexOverview: React.FC = () => { } /> )} - <EuiSpacer /> {isApi && <GenerateApiKeyPanel />} {isCrawler && ( <> diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/search_index.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/search_index.tsx index 0c0e2e2925be0..786fec0b96adb 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/search_index.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/search_index.tsx @@ -24,6 +24,9 @@ import { EnterpriseSearchContentPageTemplate } from '../layout/page_template'; import { baseBreadcrumbs } from '../search_indices'; +import { headerActions } from './components/header_actions/header_actions'; +import { IndexCreatedCallout } from './components/index_created_callout/callout'; +import { IndexCreatedCalloutLogic } from './components/index_created_callout/callout_logic'; import { ConnectorConfiguration } from './connector/connector_configuration'; import { ConnectorSchedulingComponent } from './connector/connector_scheduling'; import { AutomaticCrawlScheduler } from './crawler/automatic_crawl_scheduler/automatic_crawl_scheduler'; @@ -50,11 +53,13 @@ export enum SearchIndexTabId { export const SearchIndex: React.FC = () => { const { makeRequest, apiReset } = useActions(FetchIndexApiLogic); const { data: indexData, status: indexApiStatus } = useValues(FetchIndexApiLogic); - const { indexName } = useValues(IndexNameLogic); + const { isCalloutVisible } = useValues(IndexCreatedCalloutLogic); const { tabId = SearchIndexTabId.OVERVIEW } = useParams<{ tabId?: string; }>(); + const { indexName } = useValues(IndexNameLogic); + useEffect(() => { makeRequest({ indexName }); return apiReset; @@ -144,11 +149,17 @@ export const SearchIndex: React.FC = () => { isLoading={indexApiStatus === Status.LOADING || indexApiStatus === Status.IDLE} pageHeader={{ pageTitle: indexName, - rightSideItems: indexData?.crawler ? [<CrawlerStatusIndicator />] : [], + rightSideItems: [ + ...headerActions, + ...(indexData?.crawler ? [<CrawlerStatusIndicator />] : []), + ], }} > - <EuiTabbedContent tabs={tabs} selectedTab={selectedTab} onTabClick={onTabClick} /> - {indexData?.crawler && <CrawlCustomSettingsFlyout />} + <> + {isCalloutVisible && <IndexCreatedCallout indexName={indexName} />} + <EuiTabbedContent tabs={tabs} selectedTab={selectedTab} onTabClick={onTabClick} /> + {indexData?.crawler && <CrawlCustomSettingsFlyout />} + </> </EnterpriseSearchContentPageTemplate> ); }; diff --git a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/total_stats.tsx b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/total_stats.tsx index b3ed64e1b6e9f..72d20d032d0fb 100644 --- a/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/total_stats.tsx +++ b/x-pack/plugins/enterprise_search/public/applications/enterprise_search_content/components/search_index/total_stats.tsx @@ -13,23 +13,23 @@ import { EuiFlexGroup, EuiFlexItem, EuiPanel, EuiStat, EuiStatProps } from '@ela import { i18n } from '@kbn/i18n'; -import { Status } from '../../../../../common/types/api'; - import { CustomFormattedTimestamp } from '../../../shared/custom_formatted_timestamp/custom_formatted_timestamp'; -import { FetchIndexApiLogic } from '../../api/index/fetch_index_api_logic'; + +import { OverviewLogic } from './overview.logic'; interface TotalStatsProps { additionalItems?: EuiStatProps[]; ingestionType: string; + lastUpdated?: string; } export const TotalStats: React.FC<TotalStatsProps> = ({ ingestionType, additionalItems = [] }) => { - const { data, status } = useValues(FetchIndexApiLogic); - const documentCount = data?.index.total.docs.count ?? 0; + const { indexData, isSuccess } = useValues(OverviewLogic); + const documentCount = indexData?.index.total.docs.count ?? 0; const lastUpdated = ( <CustomFormattedTimestamp timestamp={Date.now() - 1000 * 60 * 12 /* TODO: Implement this */} /> ); - const isLoading = status !== Status.SUCCESS; + const isLoading = !isSuccess; const stats: EuiStatProps[] = [ { description: i18n.translate( diff --git a/x-pack/plugins/enterprise_search/public/applications/shared/cloud_details/cloud_details.ts b/x-pack/plugins/enterprise_search/public/applications/shared/cloud_details/cloud_details.ts new file mode 100644 index 0000000000000..b46a7f9c130fb --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/shared/cloud_details/cloud_details.ts @@ -0,0 +1,23 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useValues } from 'kea'; + +import { KibanaLogic } from '../kibana'; + +export interface CloudDetails { + cloudId: string | undefined; + deploymentUrl: string | undefined; +} + +export const useCloudDetails = (): CloudDetails => { + const { cloud } = useValues(KibanaLogic); + return { + cloudId: cloud?.cloudId, + deploymentUrl: cloud?.deploymentUrl, + }; +}; diff --git a/x-pack/plugins/enterprise_search/public/applications/shared/doc_links/__mocks__/doc_links.mock.ts b/x-pack/plugins/enterprise_search/public/applications/shared/doc_links/__mocks__/doc_links.mock.ts new file mode 100644 index 0000000000000..7529b22fe1336 --- /dev/null +++ b/x-pack/plugins/enterprise_search/public/applications/shared/doc_links/__mocks__/doc_links.mock.ts @@ -0,0 +1,16 @@ +/* + * 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; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { docLinksServiceMock } from '@kbn/core/public/mocks'; + +const mockLinks = { + DOC_LINK_VERSION: docLinksServiceMock.createStartContract().DOC_LINK_VERSION, + ELASTIC_WEBSITE_URL: docLinksServiceMock.createStartContract().ELASTIC_WEBSITE_URL, + links: docLinksServiceMock.createStartContract().links, +}; + +jest.mock('../doc_links', () => ({ docLinks: mockLinks })); diff --git a/x-pack/plugins/enterprise_search/public/applications/shared/doc_links/doc_links.ts b/x-pack/plugins/enterprise_search/public/applications/shared/doc_links/doc_links.ts index 7d27d10a6ca85..9132dbdfb05b2 100644 --- a/x-pack/plugins/enterprise_search/public/applications/shared/doc_links/doc_links.ts +++ b/x-pack/plugins/enterprise_search/public/applications/shared/doc_links/doc_links.ts @@ -42,7 +42,9 @@ class DocLinks { public clientsNetIntroduction: string; public clientsNetNest: string; public clientsNetSingleNode: string; + public clientsPerlGuide: string; public clientsPhpConnecting: string; + public clientsPhpGuide: string; public clientsPhpInstallation: string; public clientsPhpOverview: string; public clientsPythonAuthentication: string; @@ -130,7 +132,9 @@ class DocLinks { this.clientsNetIntroduction = ''; this.clientsNetNest = ''; this.clientsNetSingleNode = ''; + this.clientsPerlGuide = ''; this.clientsPhpConnecting = ''; + this.clientsPhpGuide = ''; this.clientsPhpInstallation = ''; this.clientsPhpOverview = ''; this.clientsPythonAuthentication = ''; @@ -220,7 +224,9 @@ class DocLinks { this.clientsNetIntroduction = docLinks.links.clients.netIntroduction; this.clientsNetNest = docLinks.links.clients.netNest; this.clientsNetSingleNode = docLinks.links.clients.netSingleNode; + this.clientsPerlGuide = docLinks.links.clients.perlGuide; this.clientsPhpConnecting = docLinks.links.clients.phpConnecting; + this.clientsPhpGuide = docLinks.links.clients.phpGuide; this.clientsPhpInstallation = docLinks.links.clients.phpInstallation; this.clientsPhpOverview = docLinks.links.clients.phpOverview; this.clientsPythonAuthentication = docLinks.links.clients.pythonAuthentication; diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index 4a8dba1ccb061..e700da7e067e5 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -32026,4 +32026,4 @@ "xpack.watcher.watchEdit.thresholdWatchExpression.aggType.fieldIsRequiredValidationMessage": "此字段必填。", "xpack.watcher.watcherDescription": "通过创建、管理和监测警报来检测数据中的更改。" } -} \ No newline at end of file +} From 969c4979a59d6982d6479e4828fda5fbd64da6c1 Mon Sep 17 00:00:00 2001 From: Kyle Pollich <kyle.pollich@elastic.co> Date: Mon, 18 Jul 2022 12:35:04 -0400 Subject: [PATCH 111/111] [Fleet] Add dev docs around Fleet's relationship to integrations (#133449) * Add first pass for dev docs around integrations * wip * Finish up integrations overview * Add note re: index templates/fields Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> --- .../fleet/dev_docs/integrations_overview.md | 165 ++++++++++++++++++ 1 file changed, 165 insertions(+) create mode 100644 x-pack/plugins/fleet/dev_docs/integrations_overview.md diff --git a/x-pack/plugins/fleet/dev_docs/integrations_overview.md b/x-pack/plugins/fleet/dev_docs/integrations_overview.md new file mode 100644 index 0000000000000..b6ce0f5ce9917 --- /dev/null +++ b/x-pack/plugins/fleet/dev_docs/integrations_overview.md @@ -0,0 +1,165 @@ +# Overview of Integrations + +Elastic Agent integrations are mechanisms for installing assets that provide an opinionated "out of the box" experience for ingesting data from various pieces of software, third party services, and even internal Elastic products. Fleet provides an interface for installing and managing these integrations. Integrations tell Elastic Agent where and how to retrieve data, and how it should be ingested into Elasticsearch. + +In terms of what an integration actually _is_, it's a set of mostly YML files in a particular directory structure with particular naming conventions. These conventions are captured in a specification maintained by Elastic called the [package spec](https://github.com/elastic/package-spec/). + +This document will detail some of the key files and fields defined by the package spec that we'll commonly deal with in Fleet, and will attempt to provide an informed mental model around integrations. We'll use Fleet's integration policy editor UI to show how integrations' configuration files are translated into the Fleet interface we present to users. + +## References + +- https://github.com/elastic/package-spec +- https://github.com/elastic/integrations/tree/main/packages + +## Top level `manifest.yml` + +🔗 [Package spec reference](https://github.com/elastic/package-spec/blob/main/versions/1/integration/manifest.spec.yml) + +- Basic metadata for the integration like name, title, version, description, categories, etc +- Kibana compatibility spec +- Screenshots and icon assets + +### `policy_templates` + +🔗 [Package spec reference](https://github.com/elastic/package-spec/blob/main/versions/1/integration/manifest.spec.yml#L186-L273) + +The top level `manifest.yml` file defines a set of `policy_templates` which define a grouping of fields used to configure the integration. These `policy_templates` control what’s rendered in Fleet UI’s “policy editor” when creating or editing integration policies. + +Most integrations will only specify a single `policy_template` as they don’t require this level of structure. For integrations that export many “sub-integrations,” however, they rely on defining multiple templates. + +For example, Nginx defines only a single `policy_template` - aptly named `nginx`: + +```yml +# https://github.com/elastic/integrations/blob/main/packages/nginx/manifest.yml +policy_templates: + - name: nginx + title: Nginx logs and metrics + description: Collect logs and metrics from Nginx instances + inputs: + # ... +``` + +This results in a policy editor UI that looks like this: + +![Nginx policy editor screenshot](https://user-images.githubusercontent.com/6766512/171722222-b7e663d4-5668-4925-88df-ddabd9f590a5.png) + +In contrast, the AWS integration defines many `policy_templates`, as it allows users to configure policy values for many distinct services like EC2, S3, or RDS. See the `policy_templates` definition for AWS [here](https://github.com/elastic/integrations/blob/main/packages/aws/manifest.yml#L77). + +The AWS policy editor has a section for each provided `policy_template` value, e.g. + +![AWS policy editor screenshot](https://user-images.githubusercontent.com/6766512/171722802-3f2705a1-71b6-4747-b5fb-c48ea069c597.png) + +Each policy template is also exposed as its own distinct integration, and can be installed or managed separately as if it were a first-class integration: + +![AWS integrations screenshot](https://user-images.githubusercontent.com/6766512/171723125-4d34a42c-de5b-4699-9683-99951d4f5bb1.png) + +#### `inputs` + +🔗 [Package spec reference](https://github.com/elastic/package-spec/blob/main/versions/1/integration/manifest.spec.yml#L221-L261) + +Each `policy_template` entry defines a set of `inputs`. An `input` is essentially a named grouping of fields related to a particular type of data to be ingested. +Each `input` declares a `type` that typically maps to a Beats input like [httpjson](https://www.elastic.co/guide/en/beats/filebeat/current/filebeat-input-httpjson.html) or [filestream](https://www.elastic.co/guide/en/beats/filebeat/current/filebeat-input-filestream.html). Elastic Agent manages Beats under the hood, +so these `inputs` are how we can configure the individual Beats that Agent is managing. + +For example, the Nginx integration defines three inputs: + +1. `logfile` +2. `httpjson` +3. `nginx/metrics` + +These inputs appear in the policy editor UI as separate fieldsets, e.g. + +![Nginx inputs screenshot](https://user-images.githubusercontent.com/6766512/171724709-724bd7a1-bbcf-4c6a-bc36-f3aeac2c06f8.png) + +Each input can define a list of `vars` that will allow a user to configure variables via form fields in the Fleet policy editor UI. + +For example, on the Nginx integration's `httpjson` input, there are several "input level variables" configure, which are rendered as below: + +![image](https://user-images.githubusercontent.com/6766512/171725972-351f3cd3-de86-49cf-81bc-6aa6dd4dec89.png) + +These input level variables are defined in the Nginx integration [here](https://github.com/elastic/integrations/blob/main/packages/nginx/manifest.yml#L43). + +It's important to note that integration also define variables at the data stream level, which we'll get into later in this doc. In the screenshot above, for example, the section beneath the "Settings" section of the `httpjson` input contains data stream variables for the streams configured as part of the `httpjson` input. + +## `data_stream` directory + +Each integration includes a `data_stream` directory that contains configuration for, well, [data streams](https://www.elastic.co/guide/en/elasticsearch/reference/current/data-streams.html). + +Data streams are a construct in Elasticsearch designed for storing "append-only" time series data across multiple backing indices. They give Elastic Agent an easy and performant way to ingest logs and metrics data into Elasticsearch. + +Inside of the `data_stream` directory, each data stream is defined as its own directory. For example, the Nginx integration's `data_stream` [directory](https://github.com/elastic/integrations/tree/main/packages/nginx/data_stream) contains three data streams: + +1. `access` +2. `error` +3. `substatus` + +Elastic Agent data streams conform to a [naming schema](https://www.elastic.co/blog/an-introduction-to-the-elastic-data-stream-naming-scheme) of `{type}-{dataset}-{namespace}`. The `type` of a data stream is either `logs` or `metrics`. The `dataset` of a datastream is controlled in most cases by an interpolation of the integration's `name` field and the directory name containing the data stream's `manifest.yml` file. The `namespace` value is provided by the user for the purpose of grouping or organizing data. + +Each data stream directory contains a `manifest.yml` file that controls the configuration for the data stream, as well as Elasticsearch/Kibana assets, configuration for Agent, and more. Generally, though, the `manifest.yml` file is the most critical one in a given data stream directory. + +In a data stream's `manifest.yml` file, the integration defines a list of `streams`. Each item in that `streams` list is tied to a single `input`, and defines its own list of `vars` that controls the set of form fields that appear in the policy editor UI. + +For example, the Nginx integration's `access` data stream defines an entry in its `streams` list tied to the `logfile` input mentioned above that includes variables like `paths` and `tags`. The variables appear as form fields in the policy editor UI as below: + +![Nginx data streams screenshot](https://user-images.githubusercontent.com/6766512/171729648-3936f0a8-2487-4862-8732-b0b93748274f.png) + +The "Nginx access logs" fieldset we see in the policy editor UI is defined [here](https://github.com/elastic/integrations/blob/main/packages/nginx/data_stream/access/manifest.yml#L4-L40) in the `data_streams/access/manifest.yml` file within the Nginx integration. It's `input` value is set to `logfile`, so it appears under the "Collect logs from Nginx instances" section in the policy editor. The `title` and `description` values control what appears on the left-hand side to describe the fieldset. + +### Data stream assets + +Each data stream directory may contain an `elasticsearch` or `kibana` directory that contains assets (like ingest pipelines or Kibana dashboards) for a given +stack component. These assets are usually YML or JSON files that Fleet passes off to the corresponding stack component to install. For example, the Nginx integration's `data_stream/access` directory contains an `elasticsearch/ingest_pipeline` directory that contains the following files: + +- `default.yml` +- `third-party.yml` + +These files represent two ingest pipelines that ship with the Nginx integration to provide out-of-the-box mappings, field processing, etc for Nginx data. + +For more information on data streams, see Fleet's dev docs [here](https://github.com/elastic/kibana/blob/main/x-pack/plugins/fleet/dev_docs/data_streams.md). + +### `agent/stream` directory + +Each data stream contains an `agent/stream` directory that includes YML files for configuring agent. These are template files that are compiled by Fleet when +generating the full agent policy. + +_TODO: Document this in more detail_ + +### `fields` directory + +The `fields` directory contains YML files that define the [mappings](https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping.html) for a given data stream. There may be any number of `fields` files based on the integration maintainers preferred organization for their mappings. For example, many integrations +contain a `base-fields.yml` file for common mappings, an `ecs.yml` file for [ECS](https://www.elastic.co/guide/en/ecs/current/index.html)-compliant fields, an +`agent.yml` file for mappings specific to the actual agent process, and a `fields.yml` file for everything else. + +The mappings defined by `fields` files are used by Fleet to generate an [index template](https://www.elastic.co/guide/en/elasticsearch/reference/current/index-templates.html) for each data stream. This index template composes all of the mappings and settings and ensures that all documents ingested by +the data stream are indexed as configured. + +## `docs` directory + +Contains the README file rendered on the integrations detail page for the integration. + +## `img` directory + +Contains screenshots rendered on the integrations detail page for the integration. + +## `kibana` directory + +Contains top level Kibana assets (dashboards, visualizations, saved searches etc) for the integration. + +## Relationship diagram + +Reference the following diagram to understand the relationship between the various components of an integration: + +```mermaid +erDiagram + Integration ||--|{ PolicyTemplate : "Many policy templates" + Integration ||--|{ DataStream : "Many data streams" + + PolicyTemplate ||--|{ Input : "Many inputs" + + DataStream ||--|{ Input : "Many inputs" + + Integration {} + PolicyTemplate {} + Input {} + DataStream {} +```