Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

init grafana service #108

Merged
merged 11 commits into from
Feb 22, 2024
40 changes: 40 additions & 0 deletions doc/grafana.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
# Grafana Open Source
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Any reason why we can't just use Grafana here?

Copy link
Contributor Author

@conscious-puppet conscious-puppet Feb 22, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i copied the doc from here:

i think, they probably want to distinguish this from Grafana Cloud. I'll change* it to grafana, sure


Grafana open source is open source visualization and analytics software. It allows you to query, visualize, alert on, and explore your metrics, logs, and traces no matter where they are stored. It provides you with tools to turn your time-series database (TSDB) data into insightful graphs and visualizations.

## Getting Started

```nix
# In `perSystem.process-compose.<name>`
{
services.grafana."gf1".enable = true;
}
```

{#tips}
## Tips & Tricks

{#change-database}
### Changing Grafana database

By default, Grafana stores data in the `sqlite3` [database](https://grafana.com/docs/grafana/latest/setup-grafana/configure-grafana/#database). It also supports `mysql` and `postgres`.

To change the database to `postgres`, we can use the following config:

```nix
services.postgres.pg1 = {
enable = true;
listen_addresses = "127.0.0.1";
initialScript.after = "CREATE USER root SUPERUSER;";
};
services.grafana.gf1 = {
enable = true;
extraConf.database = with config.services.postgres.pg1; {
type = "postgres";
host = "${listen_addresses}:${builtins.toString port}";
name = "postgres"; # database name
};
};
settings.processes."gf1".depends_on."pg1".condition = "process_healthy";
};
```
1 change: 1 addition & 0 deletions doc/services.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ short-title: Services
- [ ] Redis
- [ ] Redis Cluster
- [ ] Zookeeper
- [ ] [[grafana]]#
- [ ] ...

[gh]: https://github.com/juspay/services-flake
1 change: 1 addition & 0 deletions nix/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -13,5 +13,6 @@ in
./redis-cluster.nix
./redis.nix
./zookeeper.nix
./grafana
];
}
99 changes: 99 additions & 0 deletions nix/grafana/default.nix
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Usually we create folder for a service when there are more than just the service definition file and test file. We can preserve the flat hierarchy here.

Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
{ pkgs, lib, name, config, ... }:
let
inherit (lib) types;
iniFormat = pkgs.formats.ini { };
in
{
options = {
description = ''
Configure grafana.
'';
enable = lib.mkEnableOption name;

package = lib.mkPackageOption pkgs "grafana" { };

http_port = lib.mkOption {
type = types.int;
description = "Which port to run grafana on.";
default = 3000;
};

domain = lib.mkOption {
type = types.str;
description = "The public facing domain name used to access grafana from a browser.";
default = "localhost";
};

protocol = lib.mkOption {
type = types.str;
description = "Protocol (http, https, h2, socket).";
default = "http";
};

dataDir = lib.mkOption {
type = types.str;
description = "Directory where grafana stores its logs and data.";
default = "./data/${name}";
};

extraConf = lib.mkOption {
type = iniFormat.type;
description = "Extra configuration for grafana.";
default = { };
example = ''
{
security.admin_user = "patato";
security.admin_password = "potato";
}
'';
};

outputs.settings = lib.mkOption {
type = types.deferredModule;
internal = true;
readOnly = true;
default = {
processes."${name}" =
let
grafanaConfig = lib.recursiveUpdate
config.extraConf
{
server = {
inherit (config) protocol http_port domain;
};
};
grafanaConfigIni = iniFormat.generate "defaults.ini" grafanaConfig;
startScript = pkgs.writeShellApplication {
name = "start-grafana";
runtimeInputs = [ config.package ];
text = ''
grafana server --config ${grafanaConfigIni} \
--homepath ${config.package}/share/grafana \
cfg:paths.data="$(readlink -m ${config.dataDir})"
'';
};
in
{
command = startScript;
readiness_probe = {
http_get = {
host = config.domain;
scheme = config.protocol;
port = config.http_port;
path = "/api/health";
};
initial_delay_seconds = 15;
period_seconds = 10;
timeout_seconds = 2;
success_threshold = 1;
failure_threshold = 5;
};
namespace = name;

# https://github.com/F1bonacc1/process-compose#-auto-restart-if-not-healthy
availability.restart = "on_failure";
};
};
};
};
}
32 changes: 32 additions & 0 deletions nix/grafana/grafana_test.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
{ pkgs, config, ... }: {
services.grafana."gf1" =
{
enable = true;
http_port = 3000;
extraConf = {
security.admin_user = "patato";
security.admin_password = "potato";
};
};

settings.processes.test =
let
cfg = config.services.grafana."gf1";
in
{
# Tests based on: https://github.com/NixOS/nixpkgs/blob/master/nixos/tests/grafana/basic.nix
command = pkgs.writeShellApplication {
runtimeInputs = [ cfg.package pkgs.gnugrep pkgs.curl pkgs.uutils-coreutils-noprefix ];
text =
''
ADMIN=${cfg.extraConf.security.admin_user}
PASSWORD=${cfg.extraConf.security.admin_password}
ROOT_URL="${cfg.protocol}://${cfg.domain}:${builtins.toString cfg.http_port}";
curl -sSfN -u $ADMIN:$PASSWORD $ROOT_URL/api/org/users -i
curl -sSfN -u $ADMIN:$PASSWORD $ROOT_URL/api/org/users | grep admin\@localhost
'';
name = "grafana-test";
};
depends_on."gf1".condition = "process_healthy";
};
}
1 change: 1 addition & 0 deletions test/flake.nix
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@
"${inputs.services-flake}/nix/redis_test.nix"
"${inputs.services-flake}/nix/redis-cluster_test.nix"
"${inputs.services-flake}/nix/zookeeper_test.nix"
"${inputs.services-flake}/nix/grafana/grafana_test.nix"
]);
};
};
Expand Down
Loading