Merge branch 'master' into export-dashboard

This commit is contained in:
Torkel Ödegaard 2016-05-28 17:17:51 +02:00
commit 53bb264375
12 changed files with 207 additions and 8 deletions

View File

@ -0,0 +1,16 @@
FROM ubuntu:xenial
ENV DEBIAN_FRONTEND noninteractive
RUN apt-get -y update
RUN apt-get -y install collectd curl python-pip
# add a fake mtab for host disk stats
ADD etc_mtab /etc/mtab
ADD collectd.conf.tpl /etc/collectd/collectd.conf.tpl
RUN pip install envtpl
ADD start_container /usr/bin/start_container
RUN chmod +x /usr/bin/start_container
CMD start_container

View File

@ -0,0 +1,37 @@
collectd-write-graphite
=======================
Basic collectd-based server monitoring. Sends stats to Graphite.
Collectd metrics:
* CPU used/free/idle/etc
* Free disk (via mounting hosts '/' into container, eg: -v /:/hostfs:ro)
* Disk performance
* Load average
* Memory used/free/etc
* Uptime
* Network interface
* Swap
Environment variables
---------------------
* `HOST_NAME`
- Will be sent to Graphite
- Required
* `GRAPHITE_HOST`
- Graphite IP or hostname
- Required
* `GRAPHITE_PORT`
- Graphite port
- Optional, defaults to 2003
* `GRAPHITE_PREFIX`
- Graphite prefix
- Optional, defaults to collectd.
* `REPORT_BY_CPU`
- Report per-CPU metrics if true, global sum of CPU metrics if false (details: [collectd.conf man page](https://collectd.org/documentation/manpages/collectd.conf.5.shtml#plugin_cpu))
- Optional, defaults to false.
* `COLLECT_INTERVAL`
- Collection interval and thus resolution of metrics
- Optional, defaults to 10

View File

@ -0,0 +1,76 @@
Hostname "{{ HOST_NAME }}"
FQDNLookup false
Interval {{ COLLECT_INTERVAL | default("10") }}
Timeout 2
ReadThreads 5
LoadPlugin cpu
LoadPlugin df
LoadPlugin load
LoadPlugin memory
LoadPlugin disk
LoadPlugin interface
LoadPlugin uptime
LoadPlugin swap
LoadPlugin write_graphite
<Plugin cpu>
ReportByCpu {{ REPORT_BY_CPU | default("false") }}
</Plugin>
<Plugin df>
# expose host's mounts into container using -v /:/host:ro (location inside container does not matter much)
# ignore rootfs; else, the root file-system would appear twice, causing
# one of the updates to fail and spam the log
FSType rootfs
# ignore the usual virtual / temporary file-systems
FSType sysfs
FSType proc
FSType devtmpfs
FSType devpts
FSType tmpfs
FSType fusectl
FSType cgroup
FSType overlay
FSType debugfs
FSType pstore
FSType securityfs
FSType hugetlbfs
FSType squashfs
FSType mqueue
MountPoint "/etc/resolv.conf"
MountPoint "/etc/hostname"
MountPoint "/etc/hosts"
IgnoreSelected true
ReportByDevice false
ReportReserved true
ReportInodes true
</Plugin>
<Plugin "disk">
Disk "/^[hs]d[a-z]/"
IgnoreSelected false
</Plugin>
<Plugin interface>
Interface "lo"
Interface "/^veth.*/"
Interface "/^docker.*/"
IgnoreSelected true
</Plugin>
<Plugin "write_graphite">
<Carbon>
Host "{{ GRAPHITE_HOST }}"
Port "{{ GRAPHITE_PORT | default("2003") }}"
Prefix "{{ GRAPHITE_PREFIX | default("collectd.") }}"
EscapeCharacter "_"
SeparateInstances true
StoreRates true
AlwaysAppendDS false
</Carbon>
</Plugin>

View File

@ -0,0 +1 @@
hostfs /.dockerinit ext4 ro,relatime,user_xattr,barrier=1,data=ordered 0 0

View File

@ -0,0 +1,11 @@
collectd:
build: blocks/collectd
environment:
HOST_NAME: myserver
GRAPHITE_HOST: graphite
GRAPHITE_PORT: 2003
GRAPHITE_PREFIX: collectd.
REPORT_BY_CPU: 'false'
COLLECT_INTERVAL: 10
links:
- graphite

View File

@ -0,0 +1,5 @@
#!/bin/bash
envtpl /etc/collectd/collectd.conf.tpl
collectd -f

View File

@ -244,7 +244,7 @@ function pluginDirectiveLoader($compile, datasourceSrv, $rootScope, $q, $http, $
registerPluginComponent(scope, elem, attrs, componentInfo);
}).catch(err => {
$rootScope.appEvent('alert-error', ['Plugin Error', err.message || err]);
console.log('Plugin componnet error', err);
console.log('Plugin component error', err);
});
}
};

View File

@ -12,9 +12,21 @@ function($, _) {
kbn.round_interval = function(interval) {
switch (true) {
// 0.3s
case (interval <= 300):
return 100; // 0.1s
// 0.015s
case (interval <= 15):
return 10; // 0.01s
// 0.035s
case (interval <= 35):
return 20; // 0.02s
// 0.075s
case (interval <= 75):
return 50; // 0.05s
// 0.15s
case (interval <= 150):
return 100; // 0.1s
// 0.35s
case (interval <= 350):
return 200; // 0.2s
// 0.75s
case (interval <= 750):
return 500; // 0.5s
@ -133,7 +145,7 @@ function($, _) {
return str;
};
kbn.interval_regex = /(\d+(?:\.\d+)?)([Mwdhmsy])/;
kbn.interval_regex = /(\d+(?:\.\d+)?)(ms|[Mwdhmsy])/;
// histogram & trends
kbn.intervals_in_seconds = {
@ -143,7 +155,8 @@ function($, _) {
d: 86400,
h: 3600,
m: 60,
s: 1
s: 1,
ms: 0.001
};
kbn.calculateInterval = function(range, resolution, userInterval) {

View File

@ -25,6 +25,7 @@ function (angular, _) {
{value: "interval", text: "Interval"},
{value: "datasource", text: "Data source"},
{value: "custom", text: "Custom"},
{value: "constant", text: "Constant"},
];
$scope.refreshOptions = [
@ -141,15 +142,34 @@ function (angular, _) {
$scope.current = angular.copy(replacementDefaults);
};
$scope.showSelectionOptions = function() {
if ($scope.current) {
if ($scope.current.type === 'query') {
return true;
}
if ($scope.current.type === 'custom') {
return true;
}
}
return false;
};
$scope.typeChanged = function () {
if ($scope.current.type === 'interval') {
$scope.current.query = '1m,10m,30m,1h,6h,12h,1d,7d,14d,30d';
$scope.current.refresh = 0;
}
if ($scope.current.type === 'query') {
$scope.current.query = '';
}
if ($scope.current.type === 'constant') {
$scope.current.query = '';
$scope.current.refresh = 0;
$scope.current.hide = 2;
}
if ($scope.current.type === 'datasource') {
$scope.current.query = $scope.datasourceTypes[0].value;
$scope.current.regex = '';

View File

@ -152,6 +152,14 @@
</div>
</div>
<div ng-show="current.type === 'constant'" class="gf-form-group">
<h5 class="section-heading">Constant options</h5>
<div class="gf-form">
<span class="gf-form-label">Value</span>
<input type="text" class="gf-form-input" ng-model='current.query' ng-blur="runQuery()" placeholder="your metric prefix"></input>
</div>
</div>
<div ng-show="current.type === 'query'" class="gf-form-group">
<h5 class="section-heading">Query Options</h5>
@ -214,7 +222,7 @@
</div>
</div>
<div class="section gf-form-group" ng-hide="current.type === 'datasource'">
<div class="section gf-form-group" ng-show="showSelectionOptions()">
<h5 class="section-heading">Selection Options</h5>
<div class="section">
<gf-form-switch class="gf-form"

View File

@ -168,6 +168,11 @@ function (angular, _, kbn) {
return;
}
if (variable.type === 'constant') {
variable.options = [{text: variable.query, value: variable.query}];
return;
}
// extract options in comma seperated string
variable.options = _.map(variable.query.split(/[,]+/), function(text) {
return { text: text.trim(), value: text.trim() };
@ -175,6 +180,7 @@ function (angular, _, kbn) {
if (variable.type === 'interval') {
self.updateAutoInterval(variable);
return;
}
if (variable.type === 'custom' && variable.includeAll) {
@ -273,7 +279,7 @@ function (angular, _, kbn) {
if (currentOption) {
return self.setVariableValue(variable, currentOption, false);
} else {
if (!variable.options.length) { return; }
if (!variable.options.length) { return $q.when(null); }
return self.setVariableValue(variable, variable.options[0]);
}
}

View File

@ -147,5 +147,11 @@ define([
var str = kbn.calculateInterval(range, 1000, '>10s');
expect(str).to.be('20m');
});
it('10s 900 resolution and user low limit in ms', function() {
var range = { from: dateMath.parse('now-10s'), to: dateMath.parse('now') };
var str = kbn.calculateInterval(range, 900, '>15ms');
expect(str).to.be('15ms');
});
});
});