mirror of
https://github.com/zaphar/Heracles.git
synced 2025-07-25 13:29:48 -04:00
Compare commits
6 Commits
79bf02e1ff
...
94b05b1437
Author | SHA1 | Date | |
---|---|---|---|
![]() |
94b05b1437 | ||
![]() |
668015ed17 | ||
![]() |
63b4f810c2 | ||
![]() |
fe162968e5 | ||
847413f4f5 | |||
18eb50fbbd |
19
default.nix
19
default.nix
@ -1,11 +1,12 @@
|
||||
let
|
||||
lock = builtins.fromJSON (builtins.readFile ./flake.lock);
|
||||
lock = builtins.fromJSON (builtins.readFile ./flake.lock);
|
||||
in
|
||||
(import (
|
||||
fetchTarball {
|
||||
url = "https://github.com/edolstra/flake-compat/archive/${lock.nodes.flake-compat.locked.rev}.tar.gz";
|
||||
sha256 = lock.nodes.flake-compat.locked.narHash;
|
||||
}
|
||||
) {
|
||||
src = ./.;
|
||||
}).defaultNix
|
||||
(import (
|
||||
fetchTarball {
|
||||
url = "https://github.com/edolstra/flake-compat/archive/${lock.nodes.flake-compat.locked.rev}.tar.gz";
|
||||
sha256 = lock.nodes.flake-compat.locked.narHash;
|
||||
}
|
||||
) {
|
||||
src = ./.;
|
||||
})
|
||||
.defaultNix
|
||||
|
@ -8,10 +8,8 @@
|
||||
- source: http://heimdall:9001 # Prometheus source uri for this plot
|
||||
query: 'sum by (instance)(irate(node_cpu_seconds_total{job="nodestats"}[5m]))' # The PromQL query for this plot
|
||||
meta: # metadata for this plot
|
||||
name_label: instance # Grab a trace name from the query tags
|
||||
name_format: "`${labels.instance}`" # javascript template literal to format the trace name
|
||||
#d3_tick_format: "~%" # d3 tick format override for this plot's yaxis
|
||||
#name_prefix: "Prefix" # A prefix for this sublots trace names
|
||||
#name_suffix: "Suffix" # A suffix for this subplots trace names
|
||||
#named_axis: "y" # yaxis name to use for this subplots traces
|
||||
span: # The span for this range query
|
||||
end: now # Where the span ends. RFC3339 format with special handling for the now keyword
|
||||
@ -32,16 +30,14 @@
|
||||
sum by (instance)(irate(node_cpu_seconds_total{mode="system",job="nodestats"}[5m])) / sum by (instance)(irate(node_cpu_seconds_total{job="nodestats"}[5m]))
|
||||
meta:
|
||||
d3_tick_format: "~%"
|
||||
name_label: instance
|
||||
name_prefix: "System"
|
||||
name_format: "`${labels.instance} system`"
|
||||
named_axis: "y"
|
||||
- source: http://heimdall:9001
|
||||
query: |
|
||||
sum by (instance)(irate(node_cpu_seconds_total{mode="user",job="nodestats"}[5m])) / sum by (instance)(irate(node_cpu_seconds_total{job="nodestats"}[5m]))
|
||||
meta:
|
||||
d3_tick_format: "~%"
|
||||
name_label: instance
|
||||
name_suffix: "User"
|
||||
name_format: "`${labels.instance} user`"
|
||||
named_axis: "y"
|
||||
- title: Node memory
|
||||
query_type: Scalar
|
||||
@ -49,4 +45,4 @@
|
||||
- source: http://heimdall:9001
|
||||
query: 'node_memory_MemFree_bytes{job="nodestats"}'
|
||||
meta:
|
||||
name_label: instance
|
||||
name_format: "`${labels.instance}`"
|
||||
|
235
flake.nix
235
flake.nix
@ -6,149 +6,126 @@
|
||||
inputs.nixpkgs.follows = "nixpkgs";
|
||||
};
|
||||
naersk.url = "github:nix-community/naersk";
|
||||
flake-compat = { url = github:edolstra/flake-compat; flake = false; };
|
||||
flake-utils.url = "github:numtide/flake-utils";
|
||||
flake-compat = {
|
||||
url = github:edolstra/flake-compat;
|
||||
flake = false;
|
||||
};
|
||||
flake-utils.url = "github:numtide/flake-utils";
|
||||
};
|
||||
|
||||
outputs = {nixpkgs, flake-utils, naersk, rust-overlay, ...}:
|
||||
|
||||
outputs = {
|
||||
nixpkgs,
|
||||
flake-utils,
|
||||
naersk,
|
||||
rust-overlay,
|
||||
...
|
||||
}:
|
||||
flake-utils.lib.eachDefaultSystem (system: let
|
||||
overlays = [
|
||||
rust-overlay.overlays.default
|
||||
];
|
||||
pkgs = import nixpkgs { inherit system overlays; };
|
||||
pkgs = import nixpkgs {inherit system overlays;};
|
||||
rust-bin = pkgs.rust-bin.stable."1.71.0".default;
|
||||
naersk-lib = pkgs.callPackage naersk {
|
||||
rustc = rust-bin;
|
||||
cargo = rust-bin;
|
||||
rustc = rust-bin;
|
||||
cargo = rust-bin;
|
||||
};
|
||||
heracles = naersk-lib.buildPackage {
|
||||
name = "heracles";
|
||||
verion = "0.0.1";
|
||||
src = ./.;
|
||||
nativeBuildInputs = [ pkgs.pkg-config ];
|
||||
buildInputs = (
|
||||
if pkgs.stdenv.isDarwin then
|
||||
with pkgs.darwin.apple_sdk.frameworks; [ Security SystemConfiguration ]
|
||||
else
|
||||
[ pkgs.openssl ]) ++ [rust-bin];
|
||||
name = "heracles";
|
||||
verion = "0.0.1";
|
||||
src = ./.;
|
||||
nativeBuildInputs = [pkgs.pkg-config];
|
||||
buildInputs =
|
||||
(
|
||||
if pkgs.stdenv.isDarwin
|
||||
then with pkgs.darwin.apple_sdk.frameworks; [Security SystemConfiguration]
|
||||
else [pkgs.openssl]
|
||||
)
|
||||
++ [rust-bin];
|
||||
};
|
||||
in
|
||||
{
|
||||
in {
|
||||
packages.default = heracles;
|
||||
}) // {
|
||||
nixosModule = {config, pkgs, lib}: with lib; {
|
||||
options = {
|
||||
services.heracles.enable = mkEnableOption "enable heracles service";
|
||||
services.heracles.listen = mkOption {
|
||||
description = "[host]:port address for heracles to listen on";
|
||||
default = "localhost:8080";
|
||||
defaultText = "localhost:8080";
|
||||
};
|
||||
formatter = pkgs.alejandra;
|
||||
})
|
||||
// {
|
||||
nixosModules.default = {
|
||||
config,
|
||||
pkgs,
|
||||
lib,
|
||||
}: {
|
||||
options = {
|
||||
services.heracles.enable = lib.mkEnableOption "enable heracles service";
|
||||
services.heracles.listen = lib.mkOption {
|
||||
description = "[host]:port address for heracles to listen on";
|
||||
default = "localhost:8080";
|
||||
defaultText = "localhost:8080";
|
||||
type = lib.types.string;
|
||||
};
|
||||
|
||||
services.heracles.settings = mkOption {
|
||||
description = "heracles dashboard Configuration";
|
||||
default = [
|
||||
services.heracles.settings = lib.mkOption {
|
||||
description = "heracles dashboard Configuration";
|
||||
type = lib.types.listOf lib.types.attrs;
|
||||
default = [];
|
||||
defaultText = lib.literalExpression ''
|
||||
[
|
||||
{
|
||||
title = "A dashboard";
|
||||
graphs = [
|
||||
{
|
||||
title = "Graph title";
|
||||
query_type = "Range";
|
||||
# yaxis formatting default for this graph
|
||||
d3_tick_format = "~s";
|
||||
plots = [
|
||||
{
|
||||
title = "A dashboard";
|
||||
graphs = [
|
||||
{
|
||||
title = "Graph title";
|
||||
query_type = "Range";
|
||||
# yaxis formatting default for this graph
|
||||
d3_tick_format = "~s";
|
||||
plots = [
|
||||
{
|
||||
source = "http://heimdall:9001";
|
||||
query = ''
|
||||
sum by (instance)(irate(node_cpu_seconds_total{job="nodestats"}[5m]))
|
||||
'';
|
||||
meta = {
|
||||
name_label = "instance";
|
||||
name_prefix = "trace name prefix";
|
||||
name_suffix = "trace name suffix";
|
||||
named_axis = "y";
|
||||
# yaxis formatting for this subplot
|
||||
d3_tick_format = "~s";
|
||||
};
|
||||
}
|
||||
];
|
||||
# span for this graph.
|
||||
span = {
|
||||
end = "now";
|
||||
duration = "1d";
|
||||
step_duration = "10min";
|
||||
};
|
||||
}
|
||||
];
|
||||
# default span for dashboard
|
||||
span = {
|
||||
end = "now";
|
||||
duration = "1d";
|
||||
step_duration = "10min";
|
||||
};
|
||||
source = "http://heimdall:9001";
|
||||
query = \'\'
|
||||
sum by (instance)(irate(node_cpu_seconds_total{job="nodestats"}[5m]))
|
||||
\'\';
|
||||
meta = {
|
||||
name_function = "''${labels.instance}";
|
||||
named_axis = "y";
|
||||
# yaxis formatting for this subplot
|
||||
d3_tick_format = "~s";
|
||||
};
|
||||
}
|
||||
];
|
||||
defaultText = ''
|
||||
[
|
||||
{
|
||||
title = "A dashboard";
|
||||
graphs = [
|
||||
{
|
||||
title = "Graph title";
|
||||
query_type = "Range";
|
||||
# yaxis formatting default for this graph
|
||||
d3_tick_format = "~s";
|
||||
plots = [
|
||||
{
|
||||
source = "http://heimdall:9001";
|
||||
query = \'\'
|
||||
sum by (instance)(irate(node_cpu_seconds_total{job="nodestats"}[5m]))
|
||||
\'\';
|
||||
meta = {
|
||||
name_label = "instance";
|
||||
name_prefix = "trace name prefix";
|
||||
name_suffix = "trace name suffix";
|
||||
named_axis = "y";
|
||||
# yaxis formatting for this subplot
|
||||
d3_tick_format = "~s";
|
||||
};
|
||||
}
|
||||
];
|
||||
# span for this graph.
|
||||
span = {
|
||||
end = "now";
|
||||
duration = "1d";
|
||||
step_duration = "10min";
|
||||
};
|
||||
}
|
||||
];
|
||||
# default span for dashboard
|
||||
span = {
|
||||
end = "now";
|
||||
duration = "1d";
|
||||
step_duration = "10min";
|
||||
};
|
||||
}
|
||||
]
|
||||
'';
|
||||
};
|
||||
};
|
||||
|
||||
config = mkIf config.services.heracles.enable {
|
||||
environment.etc."heracles.yaml" = {
|
||||
text = (generators.toYAML {} config.services.heracles.settings);
|
||||
};
|
||||
systemd.services.heracles = {
|
||||
wantedBy = [ "multi-user.target" "default.target" ];
|
||||
wants = [ "network.target" ];
|
||||
after = [ "network-online.target" ];
|
||||
serviceConfig = {
|
||||
Restart = "on-failure";
|
||||
RestartSec = "30s";
|
||||
ExecStart = "${pkgs.heracles}/bin/heracles --listen ${config.services.heracles.listen} --config=${config.environment.etc."heracles.yaml".target}";
|
||||
};
|
||||
};
|
||||
};
|
||||
];
|
||||
# span for this graph.
|
||||
span = {
|
||||
end = "now";
|
||||
duration = "1d";
|
||||
step_duration = "10min";
|
||||
};
|
||||
}
|
||||
];
|
||||
# default span for dashboard
|
||||
span = {
|
||||
end = "now";
|
||||
duration = "1d";
|
||||
step_duration = "10min";
|
||||
};
|
||||
}
|
||||
]
|
||||
'';
|
||||
};
|
||||
};
|
||||
|
||||
config = let
|
||||
cfg = config.services.heracles;
|
||||
cfgFile = pkgs.writeText "heracles.yaml" (builtins.toJSON cfg.settings);
|
||||
in
|
||||
lib.mkIf cfg.enable {
|
||||
systemd.services.heracles = {
|
||||
wantedBy = ["multi-user.target" "default.target"];
|
||||
wants = ["network.target"];
|
||||
after = ["network-online.target"];
|
||||
serviceConfig = {
|
||||
Restart = "on-failure";
|
||||
RestartSec = "30s";
|
||||
ExecStart = "${pkgs.heracles}/bin/heracles --listen ${cfg.listen} --config=${cfgFile}";
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
}
|
||||
|
@ -117,9 +117,7 @@ pub struct DataPoint {
|
||||
|
||||
#[derive(Serialize, Deserialize, Debug, Clone)]
|
||||
pub struct PlotMeta {
|
||||
name_prefix: Option<String>,
|
||||
name_suffix: Option<String>,
|
||||
name_label: Option<String>,
|
||||
name_format: Option<String>,
|
||||
named_axis: Option<String>,
|
||||
d3_tick_format: Option<String>,
|
||||
}
|
||||
|
@ -160,19 +160,17 @@ class TimeseriesGraph extends HTMLElement {
|
||||
yaxis: yaxis,
|
||||
yhoverformat: meta["d3_tick_format"],
|
||||
};
|
||||
const namePrefix = meta["name_prefix"];
|
||||
const nameSuffix = meta["name_suffix"];
|
||||
const nameLabel = meta["name_label"];
|
||||
var name = "";
|
||||
if (namePrefix) {
|
||||
name = namePrefix + "-";
|
||||
};
|
||||
if (nameLabel && labels[nameLabel]) {
|
||||
name = name + labels[nameLabel];
|
||||
};
|
||||
if (nameSuffix) {
|
||||
name = name + " - " + nameSuffix;
|
||||
};
|
||||
const formatter = meta.name_format
|
||||
if (formatter) {
|
||||
name = eval(formatter);
|
||||
} else {
|
||||
var names = [];
|
||||
for (const value of labels) {
|
||||
names.push(value);
|
||||
}
|
||||
name = names.join(" ");
|
||||
}
|
||||
if (name) { trace.name = name; }
|
||||
for (const point of series) {
|
||||
trace.x.push(new Date(point.timestamp * 1000));
|
||||
@ -190,17 +188,22 @@ class TimeseriesGraph extends HTMLElement {
|
||||
type: "bar",
|
||||
x: [],
|
||||
y: [],
|
||||
yaxis: yaxis,
|
||||
yhoverformat: meta["d3_tick_format"],
|
||||
};
|
||||
let nameLabel = meta["name_label"];
|
||||
if (nameLabel && labels[nameLabel]) {
|
||||
trace.name = labels[nameLabel];
|
||||
};
|
||||
if (nameLabel && labels[nameLabel]) {
|
||||
trace.x.push(labels[nameLabel]);
|
||||
};
|
||||
const formatter = meta.name_format;
|
||||
var name = "";
|
||||
if (formatter) {
|
||||
name = eval(formatter);
|
||||
} else {
|
||||
var names = [];
|
||||
for (const value of labels) {
|
||||
names.push(value);
|
||||
}
|
||||
name = names.join(" ");
|
||||
}
|
||||
if (name) { trace.name = name; }
|
||||
trace.y.push(series.value);
|
||||
trace.x.push(trace.name);
|
||||
traces.push(trace);
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user