Skip to content

Commit

Permalink
backport of #59 #63 #64 #65 along with improvements
Browse files Browse the repository at this point in the history
(cherry picked from commit 853ba49)

Fix field format issue, update to new release

(cherry picked from commit 6faea74)

(cherry picked from commit dc06ba9)
  • Loading branch information
Pierre Padovani committed May 6, 2018
1 parent 752bfae commit 5b7bba4
Show file tree
Hide file tree
Showing 16 changed files with 241 additions and 85 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,4 @@ node_modules
/build/
.idea
.DS_Store
.project
7 changes: 6 additions & 1 deletion public/nested_support/agg_types/buckets/terms.js
Original file line number Diff line number Diff line change
Expand Up @@ -183,6 +183,11 @@ Terms.AggTypesBucketsTermsProvider = function(Private) {
routeBasedNotifier.warning('Sorting in Ascending order by Count in Terms aggregations is deprecated');
}
order._count = dir;
if (agg.params.countByParent) {
order['count_' + agg.id] = dir;
} else {
order._count = dir;
}
return;
}

Expand All @@ -192,7 +197,7 @@ Terms.AggTypesBucketsTermsProvider = function(Private) {
}

// if the target aggregation is nested, refer to it by its nested location
if (orderAgg.nestedPath || orderAgg.reverseNested) {
if ((!orderAgg.params.field.nestedPath && agg.params.field.nestedPath) || orderAgg.params.field.nestedPath !== agg.params.field.nestedPath) {
orderAggId = 'nested_' + orderAggId + '>' + orderAggId;
}

Expand Down
4 changes: 4 additions & 0 deletions public/nested_support/agg_types/index.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
import './agg_type';
import './param_types/field';
import './metrics/metric_agg_type';
import './metrics/percentiles';
import './metrics/percentile_ranks';
import './metrics/std_deviation';
import './metrics/top_hit';
import './buckets/terms';
import './buckets/filters';
import './buckets/create_filter/date_histogram';
17 changes: 17 additions & 0 deletions public/nested_support/agg_types/metrics/percentile_ranks.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import valuesEditor from 'ui/agg_types/controls/percentile_ranks.html';
import 'ui/number_list';
import { AggTypesMetricsMetricAggTypeProvider } from 'ui/agg_types/metrics/metric_agg_type';
import { AggTypesMetricsGetResponseAggConfigClassProvider } from 'ui/agg_types/metrics/get_response_agg_config_class';
import { RegistryFieldFormatsProvider } from 'ui/registry/field_formats';
import { getPercentileValue } from './percentiles_get_value';
import { uiModules } from 'ui/modules';
import { AggTypesMetricsPercentileRanksProvider } from 'ui/agg_types/metrics/percentile_ranks';

let app = uiModules.get('kibana/courier');

app.run(function(config, Private) {
const PercentileRanksAggType = Private(AggTypesMetricsPercentileRanksProvider);
PercentileRanksAggType.getValue = function (agg, bucket) {
return getPercentileValue(agg, bucket) / 100;
}
});
15 changes: 15 additions & 0 deletions public/nested_support/agg_types/metrics/percentiles.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import { ordinalSuffix } from 'ui/utils/ordinal_suffix';
import percentsEditor from 'ui/agg_types/controls/percentiles.html';
import 'ui/number_list';
import { AggTypesMetricsMetricAggTypeProvider } from 'ui/agg_types/metrics/metric_agg_type';
import { AggTypesMetricsGetResponseAggConfigClassProvider } from 'ui/agg_types/metrics/get_response_agg_config_class';
import { getPercentileValue } from './percentiles_get_value';
import { uiModules } from 'ui/modules';
import { AggTypesMetricsPercentilesProvider } from 'ui/agg_types/metrics/percentiles';

let app = uiModules.get('kibana/courier');

app.run(function(config, Private) {
const PercentilesAggType = Private(AggTypesMetricsPercentilesProvider);
PercentilesAggType.getValue = getPercentileValue;
});
11 changes: 11 additions & 0 deletions public/nested_support/agg_types/metrics/percentiles_get_value.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import { find } from 'lodash';

export function getPercentileValue(agg, bucket) {
let valueBucket = bucket;
if (bucket['nested_' + agg.parentId]) {
valueBucket = bucket['nested_' + agg.parentId];
}
const values = valueBucket[agg.parentId] && valueBucket[agg.parentId].values;
const percentile = find(values, value => agg.key === value.key);
return percentile ? percentile.value : NaN;
}
18 changes: 18 additions & 0 deletions public/nested_support/agg_types/metrics/std_deviation.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import _ from 'lodash';
import { AggTypesMetricsMetricAggTypeProvider } from 'ui/agg_types/metrics/metric_agg_type';
import { AggTypesMetricsGetResponseAggConfigClassProvider } from 'ui/agg_types/metrics/get_response_agg_config_class';
import { uiModules } from 'ui/modules';
import { AggTypesMetricsStdDeviationProvider } from 'ui/agg_types/metrics/std_deviation';

let app = uiModules.get('kibana/courier');

app.run(function(config, Private) {
const StdDeviationAggType = Private(AggTypesMetricsStdDeviationProvider);
StdDeviationAggType.getValue = function (agg, bucket) {
let valueBucket = bucket;
if (bucket['nested_' + agg.parentId]) {
valueBucket = bucket['nested_' + agg.parentId];
}
return _.get(valueBucket[agg.parentId], agg.valProp());
};
});
51 changes: 51 additions & 0 deletions public/nested_support/agg_types/metrics/top_hit.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
import _ from 'lodash';
import { AggTypesMetricsMetricAggTypeProvider } from 'ui/agg_types/metrics/metric_agg_type';
import topSortEditor from 'ui/agg_types/controls/top_sort.html';
import aggregateAndSizeEditor from 'ui/agg_types/controls/top_aggregate_and_size.html';
import { uiModules } from 'ui/modules';
import { AggTypesMetricsTopHitProvider } from 'ui/agg_types/metrics/top_hit';

let app = uiModules.get('kibana/courier');

app.run(function(config, Private) {
const TopHitType = Private(AggTypesMetricsTopHitProvider);
TopHitType.getValue = function (agg, bucket) {
let valueBucket = bucket;
if (bucket['nested_' + agg.parentId]) {
valueBucket = bucket['nested_' + agg.parentId];
}
const hits = _.get(valueBucket, `${agg.id}.hits.hits`);
if (!hits || !hits.length) {
return null;
}
const path = agg.params.field.name;

let values = _(hits).map(hit => {
return path === '_source' ? hit._source : agg.vis.indexPattern.flattenHit(hit, true)[path];
})
.flatten()
.value();

if (values.length === 1) {
values = values[0];
}

if (_.isArray(values)) {
if (!_.compact(values).length) {
return null;
}
switch (agg.params.aggregate.val) {
case 'max':
return _.max(values);
case 'min':
return _.min(values);
case 'sum':
return _.sum(values);
case 'average':
return _.sum(values) / values.length;
}
}
return values;
}
});

2 changes: 1 addition & 1 deletion public/nested_support/doc_view/structure.html
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@
<td style="padding-left: 15px" colspan="2" style="width: 100%">
<div id="expanded-data" ng-if="visible(field + '_', pos)" >
<div ng-repeat="(pos, subObj) in (subObj ? subObj[field] : flattened[field]) track by $index"
ng-init="subFormattedArray = (subFormatted ? subFormatted[field] : formatted[field]); fieldPrefix = field" style="border-style: ridge;">
ng-init="subFormattedArray = (subFormatted ? subFormatted[field] : formatted[field]); fieldPrefix = field" style="border-style: ridge; margin-top: 10px; border-width: 2px">
<table class="table table-condensed table-bordered">
<tbody ng-repeat="(field, value) in subObj track by field" ng-if="true"
onLoad="subFormatted = subFormattedArray[pos]" ng-include="'tree_item.html'">
Expand Down
140 changes: 66 additions & 74 deletions public/nested_support/doc_view/structure.js
Original file line number Diff line number Diff line change
@@ -1,88 +1,80 @@
import _ from 'lodash';
import {DocViewsRegistryProvider} from 'ui/registry/doc_views';
import { uiModules } from 'ui/modules';

import tableHtml from './structure.html';

DocViewsRegistryProvider.register(function () {
return {
title: 'Structure',
order: 5,
directive: {
template: tableHtml,
scope: {
hit: '=',
indexPattern: '=',
filter: '=',
columns: '=',
onAddColumn: '=',
onRemoveColumn: '='
},
controller: function ($scope) {
$scope.mapping = $scope.indexPattern.fields.byName;
$scope.flattened = $scope.indexPattern.flattenHit($scope.hit);
$scope.formatted = $scope.indexPattern.formatHit($scope.hit, true);
$scope.fields = _.keys($scope.flattened).sort();
$scope.visible = {};

$scope.canToggleColumns = function canToggleColumn() {
return (
_.isFunction($scope.onAddColumn)
&& _.isFunction($scope.onRemoveColumn)
);
};
uiModules.get('kibana')
.run(function (config, Private) {
const docViews = Private(DocViewsRegistryProvider);
docViews.byName.Table.directive.template = tableHtml;
docViews.byName.Table.directive.controller = structureController;
});

$scope.toggleColumn = function toggleColumn(columnName) {
if ($scope.columns.includes(columnName)) {
$scope.onRemoveColumn(columnName);
} else {
$scope.onAddColumn(columnName);
}
};
function structureController($scope) {
$scope.mapping = $scope.indexPattern.fields.byName;
$scope.flattened = $scope.indexPattern.flattenHit($scope.hit, false);
$scope.formatted = $scope.indexPattern.formatHit($scope.hit, true);
$scope.fields = _.keys($scope.flattened).sort();
$scope.visible = {};

$scope.visible = function (field, pos) {
let key = field;
if (pos !== undefined) {
key += pos;
}
return $scope.visible[key];
};
$scope.canToggleColumns = function canToggleColumn() {
return (
_.isFunction($scope.onAddColumn)
&& _.isFunction($scope.onRemoveColumn)
);
};

$scope.toggleVisible = function (field, pos) {
let key = field;
if (pos !== undefined) {
key += pos;
}
if ($scope.visible[key] === undefined) {
$scope.visible[key] = key;
} else {
$scope.visible[key] = undefined;
}
};
$scope.toggleColumn = function toggleColumn(columnName) {
if ($scope.columns.includes(columnName)) {
$scope.onRemoveColumn(columnName);
} else {
$scope.onAddColumn(columnName);
}
};

$scope.showArrayInObjectsWarning = function (row, field) {
let value = $scope.flattened[field];
if (row !== undefined) {
value = row[field];
}
return _.isArray(value) && typeof value[0] === 'object';
};
$scope.visible = function (field, pos) {
let key = field;
if (pos !== undefined) {
key += pos;
}
return $scope.visible[key];
};

$scope.rowSummary = function (row, fieldName, pos) {
const partials = $scope.hit.$$_partialFormatted;
let key = fieldName;
let text = '';
if (pos !== undefined) {
key += pos;
}
if (partials && partials[key] != null) {
text = partials[key];
} else {
text = partials[key] = $scope.indexPattern._legacyFormatField($scope.hit, fieldName);
}
$scope.toggleVisible = function (field, pos) {
let key = field;
if (pos !== undefined) {
key += pos;
}
if ($scope.visible[key] === undefined) {
$scope.visible[key] = key;
} else {
$scope.visible[key] = undefined;
}
};

$scope.showArrayInObjectsWarning = function (row, field) {
let value = $scope.flattened[field];
if (row !== undefined) {
value = row[field];
}
return _.isArray(value) && typeof value[0] === 'object';
};

return _.trunc(text, {'length': 200});
};
}
$scope.rowSummary = function (row, fieldName, pos) {
const partials = $scope.hit.$$_partialFormatted;
let key = fieldName;
let text = '';
if (pos !== undefined) {
key += pos;
}
if (partials && partials[key] != null) {
text = partials[key];
} else {
text = partials[key] = $scope.indexPattern.formatField($scope.hit, fieldName);
}

return _.trunc(text, {'length': 200});
};
});
}
3 changes: 2 additions & 1 deletion public/nested_support/filter_manager/index.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import './filter_manager';
import './lib/phrase';
import './lib/range';
import './lib/range';
import './lib/exists';
27 changes: 27 additions & 0 deletions public/nested_support/filter_manager/lib/exists.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import * as existsLib from 'ui/filter_manager/lib/exists';

existsLib.buildExistsFilter = function(field, indexPattern) {
if (field.nestedPath) {
return {
meta: {
index: indexPattern.id
},
nested: {
path: field.nestedPath,
query: {
exists: {
field: field.name
}
}
}
};
}
return {
meta: {
index: indexPattern.id
},
exists: {
field: field.name
}
};
};
8 changes: 6 additions & 2 deletions public/nested_support/index_patterns/_flatten_hit.js
Original file line number Diff line number Diff line change
Expand Up @@ -78,8 +78,12 @@ export function IndexPatternsNestedFlattenHitProvider(config) {
}

return function flattenHitWrapper(indexPattern) {
return function cachedFlatten(hit, deep = false) {
return hit.$$_flattened || (hit.$$_flattened = flattenHit(indexPattern, hit, deep));
return function cachedFlatten(hit, deep = true) {
if (deep) {
return hit.$$_flattened_deep || (hit.$$_flattened_deep = flattenHit(indexPattern, hit, deep));
} else {
return hit.$$_flattened || (hit.$$_flattened = flattenHit(indexPattern, hit, deep));
}
};
};
}
7 changes: 4 additions & 3 deletions public/nested_support/index_patterns/_format_hit.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ export function nestedFormatHit(indexPattern, defaultFormat) {
function convert(hit, val, fieldName, recurse) {
const field = indexPattern.fields.byName[fieldName];
if (!field) {
if (val.constructor === Array && recurse) {
if (val && val.constructor === Array && recurse) {
let pArr = [];
_.forEach(val, function (item) {
let pStore = {};
Expand Down Expand Up @@ -41,7 +41,7 @@ export function nestedFormatHit(indexPattern, defaultFormat) {
const partials = (recurse ? hit.$$_partialStructured : hit.$$_partialFormatted) || (recurse ? hit.$$_partialStructured = {}: hit.$$_partialFormatted = {});
const cache = (recurse ? hit.$$_structured = {} : hit.$$_formatted = {});

_.forOwn(indexPattern.flattenHit(hit), function (val, fieldName) {
_.forOwn(indexPattern.flattenHit(hit, false), function (val, fieldName) {
// sync the formatted and partial cache
// const formatted = partials[fieldName] == null ? convert(hit, val, fieldName) : partials[fieldName];
const formatted = partials[fieldName] == null ? convert(hit, val, fieldName, recurse) : partials[fieldName];
Expand All @@ -61,7 +61,8 @@ export function nestedFormatHit(indexPattern, defaultFormat) {
partials = hit.$$_partialFormatted = {};
}

const val = fieldName === '_source' ? hit._source : indexPattern.flattenHit(hit)[fieldName];
const deep = indexPattern.fields.byName[fieldName] != undefined;
const val = fieldName === '_source' ? hit._source : indexPattern.flattenHit(hit, deep)[fieldName];
return partials[fieldName] = convert(hit, val, fieldName, false);
};

Expand Down
Loading

0 comments on commit 5b7bba4

Please sign in to comment.