Add metric display
This commit is contained in:
parent
9156526ce0
commit
1b42954bf2
@ -25,6 +25,9 @@
|
||||
"added-label": "Added",
|
||||
"link-label": "Learn more"
|
||||
},
|
||||
"metric": {
|
||||
"settings-label": "Settings"
|
||||
},
|
||||
"cpu_agg_usage": {
|
||||
"title": "Aggregated CPU usage",
|
||||
"description": "CPU usages accross all of the CPU cores."
|
||||
|
@ -51,6 +51,7 @@
|
||||
"redux-thunk": "^2.1.0",
|
||||
"reselect": "^2.5.4",
|
||||
"styled-components": "^1.3.0",
|
||||
"svg-react-loader": "^0.3.7",
|
||||
"understood": "^1.0.1",
|
||||
"url-loader": "^0.5.7"
|
||||
},
|
||||
|
@ -5,6 +5,7 @@ const actions = require('@state/actions');
|
||||
const AddMetrics = require('./add-metrics');
|
||||
const Button = require('@ui/components/button');
|
||||
const Column = require('@ui/components/column');
|
||||
const MetricCharts = require('./metric-charts');
|
||||
const Monitors = require('./monitors');
|
||||
const PropTypes = require('@root/prop-types');
|
||||
const Row = require('@ui/components/row');
|
||||
@ -35,9 +36,13 @@ const Metrics = ({
|
||||
</Column>
|
||||
</Row>
|
||||
<Monitors />
|
||||
<MetricCharts
|
||||
datasets={metrics.datasets}
|
||||
onSettingsClick={toggleMonitorView}
|
||||
/>
|
||||
<AddMetrics
|
||||
metricTypes={metricTypes}
|
||||
metrics={metrics}
|
||||
metrics={metrics.types}
|
||||
onAddMetric={addMetric}
|
||||
/>
|
||||
</div>
|
||||
|
89
frontend/src/containers/metrics/metric-charts.js
Normal file
89
frontend/src/containers/metrics/metric-charts.js
Normal file
@ -0,0 +1,89 @@
|
||||
const React = require('react');
|
||||
const moment = require('moment');
|
||||
const PropTypes = require('@root/prop-types');
|
||||
const Metric = require('@ui/components/metric');
|
||||
const ReactIntl = require('react-intl');
|
||||
|
||||
const {
|
||||
FormattedMessage
|
||||
} = ReactIntl;
|
||||
|
||||
const {
|
||||
MetricGraph,
|
||||
MetricCloseButton,
|
||||
MetricHeader,
|
||||
MetricSelect,
|
||||
MetricSettingsButton,
|
||||
MetricTitle,
|
||||
MetricView
|
||||
} = Metric;
|
||||
|
||||
const MetricCharts = ({
|
||||
// metricTypes,
|
||||
// metrics,
|
||||
// onAddMetric,
|
||||
datasets,
|
||||
duration = 360,
|
||||
durations = [
|
||||
360,
|
||||
720,
|
||||
1440,
|
||||
2880
|
||||
],
|
||||
onDurationChange = () => {},
|
||||
onSettingsClick = () => {},
|
||||
onRemoveMetric = () => {}
|
||||
// and another one here to come...
|
||||
}) => {
|
||||
|
||||
const optionList = durations.map(duration => (
|
||||
<option key={duration} value={duration}>
|
||||
{moment.duration(duration, 'minutes').humanize()}
|
||||
</option>
|
||||
));
|
||||
|
||||
const metricList = datasets.map((dataset) => {
|
||||
// TODO
|
||||
// - yMeasurement '%' or not
|
||||
// - yMin & yMax should all come from the metric type description
|
||||
|
||||
return (
|
||||
<MetricView key={dataset.uuid + Math.random()}>
|
||||
<MetricHeader>
|
||||
<MetricTitle>{dataset.uuid}</MetricTitle>
|
||||
<MetricSelect onChange={onDurationChange} value={durations[0]}>
|
||||
{optionList}
|
||||
</MetricSelect>
|
||||
<MetricSettingsButton onClick={onSettingsClick}>
|
||||
<FormattedMessage id={'metrics.metric.settings-label'} />
|
||||
</MetricSettingsButton>
|
||||
<MetricCloseButton onClick={onRemoveMetric} />
|
||||
</MetricHeader>
|
||||
<MetricGraph
|
||||
data={dataset.data}
|
||||
duration={duration}
|
||||
yMax={100}
|
||||
yMeasurement='%'
|
||||
yMin={0}
|
||||
/>
|
||||
</MetricView>
|
||||
);
|
||||
});
|
||||
|
||||
return (
|
||||
<div>
|
||||
{metricList}
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
MetricCharts.propTypes = {
|
||||
datasets: React.PropTypes.arrayOf(PropTypes.Dataset),
|
||||
duration: React.PropTypes.number,
|
||||
durations: React.PropTypes.arrayOf(React.PropTypes.number),
|
||||
onDurationChange: React.PropTypes.func.isRequired,
|
||||
onRemoveMetric: React.PropTypes.func.isRequired,
|
||||
onSettingsClick: React.PropTypes.func.isRequired
|
||||
};
|
||||
|
||||
module.exports = MetricCharts;
|
@ -28,7 +28,7 @@ const mapStateToProps = (state, {
|
||||
const mapDispatchToProps = (dispatch) => ({
|
||||
addMetric: (service) => (metric) => dispatch(addMetric({
|
||||
id: metric,
|
||||
service: service
|
||||
service: service.uuid
|
||||
}))
|
||||
});
|
||||
|
||||
|
@ -48,7 +48,6 @@
|
||||
},
|
||||
"monitors": {
|
||||
"ui": {
|
||||
"active": "dca08514-72e5-46ce-ad91-e68b3b0914d4",
|
||||
"page": "create"
|
||||
}
|
||||
},
|
||||
@ -69,6 +68,12 @@
|
||||
"net_agg_bytes_in",
|
||||
"net_agg_bytes_out",
|
||||
"time_of_day"
|
||||
],
|
||||
"durations": [
|
||||
360,
|
||||
720,
|
||||
1440,
|
||||
2880
|
||||
]
|
||||
},
|
||||
"data": {
|
||||
|
@ -89,9 +89,11 @@ const instancesByServiceId = (serviceId) => createSelector(
|
||||
);
|
||||
|
||||
const metricsByServiceId = (serviceId) => createSelector(
|
||||
[metricTypes, serviceById(serviceId)],
|
||||
(metricTypes, service) =>
|
||||
metricTypes.filter((i) => i.service === service.uuid)
|
||||
[metricTypes, serviceById(serviceId), metricDatasets],
|
||||
(metricTypes, service, metrics) => ({
|
||||
types: metricTypes.filter((i) => i.service === service.uuid),
|
||||
datasets: datasets(metrics, service.metrics)
|
||||
})
|
||||
);
|
||||
|
||||
const metricTypeByUuid = (metricTypeUuid) => createSelector(
|
||||
|
@ -2,7 +2,10 @@ const React = require('react');
|
||||
const Styled = require('styled-components');
|
||||
const fns = require('../../shared/functions');
|
||||
const constants = require('../../shared/constants');
|
||||
const CloseIcon = require('!babel!svg-react!./close.svg?name=CloseIcon');
|
||||
const CloseIcon =
|
||||
require(
|
||||
'!babel-loader!svg-react-loader!./close.svg?name=CloseIcon'
|
||||
);
|
||||
|
||||
const {
|
||||
default: styled
|
||||
|
@ -46,6 +46,7 @@ class Graph extends React.Component {
|
||||
}]
|
||||
},
|
||||
options: {
|
||||
animation: false,
|
||||
layout: {
|
||||
padding: 10
|
||||
},
|
||||
|
@ -4,7 +4,9 @@ const fns = require('../../shared/functions');
|
||||
const constants = require('../../shared/constants');
|
||||
const Button = require('../button');
|
||||
const SettingsIcon =
|
||||
require('!babel!svg-react!./icon-settings.svg?name=SettingsIcon');
|
||||
require(
|
||||
'!babel-loader!svg-react-loader!./icon-settings.svg?name=SettingsIcon'
|
||||
);
|
||||
|
||||
const {
|
||||
default: styled
|
||||
@ -48,9 +50,10 @@ const StyledIcon = styled(SettingsIcon)`
|
||||
|
||||
const AddMetricButton = ({
|
||||
children,
|
||||
metric,
|
||||
onClick
|
||||
}) => {
|
||||
const onButtonClick = (e) => onClick();
|
||||
const onButtonClick = (e) => onClick(metric);
|
||||
return (
|
||||
<StyledButton
|
||||
name='add-metric-button'
|
||||
@ -64,6 +67,7 @@ const AddMetricButton = ({
|
||||
|
||||
AddMetricButton.propTypes = {
|
||||
children: React.PropTypes.node,
|
||||
metric: React.PropTypes.string,
|
||||
onClick: React.PropTypes.func,
|
||||
};
|
||||
|
||||
|
@ -19,6 +19,7 @@ const {
|
||||
const Container = styled.div`
|
||||
position: relative;
|
||||
box-sizing: border-box;
|
||||
margin: ${remcalc(24)} 0;
|
||||
width: 100%;
|
||||
max-width: ${remcalc(940)};
|
||||
box-shadow: ${boxes.bottomShaddow};
|
||||
|
13
ui/yarn.lock
13
ui/yarn.lock
@ -1555,12 +1555,9 @@ chart.js@^2.4.0:
|
||||
chartjs-color "^2.0.0"
|
||||
moment "^2.10.6"
|
||||
|
||||
chartjs-chart-box-plot@^1.0.0-9:
|
||||
version "1.0.0-9"
|
||||
resolved "https://registry.yarnpkg.com/chartjs-chart-box-plot/-/chartjs-chart-box-plot-1.0.0-9.tgz#bd392c689301e71b13f602818629f5a0965eaddb"
|
||||
dependencies:
|
||||
react "^15.4.1"
|
||||
react-dom "^15.4.1"
|
||||
chartjs-chart-box-plot@prerelease:
|
||||
version "1.0.0-18"
|
||||
resolved "https://registry.yarnpkg.com/chartjs-chart-box-plot/-/chartjs-chart-box-plot-1.0.0-18.tgz#66a671af5ea37155b40d85e89dc6cbae38b90330"
|
||||
|
||||
chartjs-color-string@^0.4.0:
|
||||
version "0.4.0"
|
||||
@ -5412,7 +5409,7 @@ react-docgen@^2.12.1:
|
||||
node-dir "^0.1.10"
|
||||
recast "^0.11.5"
|
||||
|
||||
react-dom@^15.4.1, react-dom@^15.4.2:
|
||||
react-dom@^15.4.2:
|
||||
version "15.4.2"
|
||||
resolved "https://registry.yarnpkg.com/react-dom/-/react-dom-15.4.2.tgz#015363f05b0a1fd52ae9efdd3a0060d90695208f"
|
||||
dependencies:
|
||||
@ -5487,7 +5484,7 @@ react-stubber@^1.0.0:
|
||||
dependencies:
|
||||
babel-runtime "^6.5.0"
|
||||
|
||||
react@^15.4.1, react@^15.4.2:
|
||||
react@^15.4.2:
|
||||
version "15.4.2"
|
||||
resolved "https://registry.yarnpkg.com/react/-/react-15.4.2.tgz#41f7991b26185392ba9bae96c8889e7e018397ef"
|
||||
dependencies:
|
||||
|
Loading…
Reference in New Issue
Block a user