Merge pull request #223749 from Alexis211/add-wgautomesh

wgautomesh: init at 0.1.0
This commit is contained in:
Ryan Lahfa 2023-04-19 08:26:09 +02:00 committed by GitHub
commit 2fa5e844de
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 198 additions and 0 deletions

View file

@ -9245,6 +9245,13 @@
githubId = 2057309; githubId = 2057309;
name = "Sergey Sofeychuk"; name = "Sergey Sofeychuk";
}; };
lx = {
email = "alex@adnab.me";
github = "Alexis211";
githubId = 101484;
matrix = "@lx:deuxfleurs.fr";
name = "Alex Auvolat";
};
lxea = { lxea = {
email = "nix@amk.ie"; email = "nix@amk.ie";
github = "lxea"; github = "lxea";

View file

@ -107,6 +107,8 @@ In addition to numerous new and upgraded packages, this release has the followin
- [trurl](https://github.com/curl/trurl), a command line tool for URL parsing and manipulation. - [trurl](https://github.com/curl/trurl), a command line tool for URL parsing and manipulation.
- [wgautomesh](https://git.deuxfleurs.fr/Deuxfleurs/wgautomesh), a simple utility to help connect wireguard nodes together in a full mesh topology. Available as [services.wgautomesh](options.html#opt-services.wgautomesh.enable).
- [woodpecker-agents](https://woodpecker-ci.org/), a simple CI engine with great extensibility. Available as [services.woodpecker-agents](#opt-services.woodpecker-agents.agents._name_.enable). - [woodpecker-agents](https://woodpecker-ci.org/), a simple CI engine with great extensibility. Available as [services.woodpecker-agents](#opt-services.woodpecker-agents.agents._name_.enable).
- [woodpecker-server](https://woodpecker-ci.org/), a simple CI engine with great extensibility. Available as [services.woodpecker-server](#opt-services.woodpecker-server.enable). - [woodpecker-server](https://woodpecker-ci.org/), a simple CI engine with great extensibility. Available as [services.woodpecker-server](#opt-services.woodpecker-server.enable).

View file

@ -1044,6 +1044,7 @@
./services/networking/wg-netmanager.nix ./services/networking/wg-netmanager.nix
./services/networking/webhook.nix ./services/networking/webhook.nix
./services/networking/wg-quick.nix ./services/networking/wg-quick.nix
./services/networking/wgautomesh.nix
./services/networking/wireguard.nix ./services/networking/wireguard.nix
./services/networking/wpa_supplicant.nix ./services/networking/wpa_supplicant.nix
./services/networking/wstunnel.nix ./services/networking/wstunnel.nix

View file

@ -0,0 +1,161 @@
{ lib, config, pkgs, ... }:
with lib;
let
cfg = config.services.wgautomesh;
settingsFormat = pkgs.formats.toml { };
configFile =
# Have to remove nulls manually as TOML generator will not just skip key
# if value is null
settingsFormat.generate "wgautomesh-config.toml"
(filterAttrs (k: v: v != null)
(mapAttrs
(k: v:
if k == "peers"
then map (e: filterAttrs (k: v: v != null) e) v
else v)
cfg.settings));
runtimeConfigFile =
if cfg.enableGossipEncryption
then "/run/wgautomesh/wgautomesh.toml"
else configFile;
in
{
options.services.wgautomesh = {
enable = mkEnableOption (mdDoc "the wgautomesh daemon");
logLevel = mkOption {
type = types.enum [ "trace" "debug" "info" "warn" "error" ];
default = "info";
description = mdDoc "wgautomesh log level.";
};
enableGossipEncryption = mkOption {
type = types.bool;
default = true;
description = mdDoc "Enable encryption of gossip traffic.";
};
gossipSecretFile = mkOption {
type = types.path;
description = mdDoc ''
File containing the shared secret key to use for gossip encryption.
Required if `enableGossipEncryption` is set.
'';
};
enablePersistence = mkOption {
type = types.bool;
default = true;
description = mdDoc "Enable persistence of Wireguard peer info between restarts.";
};
openFirewall = mkOption {
type = types.bool;
default = true;
description = mdDoc "Automatically open gossip port in firewall (recommended).";
};
settings = mkOption {
type = types.submodule {
freeformType = settingsFormat.type;
options = {
interface = mkOption {
type = types.str;
description = mdDoc ''
Wireguard interface to manage (it is NOT created by wgautomesh, you
should use another NixOS option to create it such as
`networking.wireguard.interfaces.wg0 = {...};`).
'';
example = "wg0";
};
gossip_port = mkOption {
type = types.port;
description = mdDoc ''
wgautomesh gossip port, this MUST be the same number on all nodes in
the wgautomesh network.
'';
default = 1666;
};
lan_discovery = mkOption {
type = types.bool;
default = true;
description = mdDoc "Enable discovery of peers on the same LAN using UDP broadcast.";
};
upnp_forward_external_port = mkOption {
type = types.nullOr types.port;
default = null;
description = mdDoc ''
Public port number to try to redirect to this machine's Wireguard
daemon using UPnP IGD.
'';
};
peers = mkOption {
type = types.listOf (types.submodule {
options = {
pubkey = mkOption {
type = types.str;
description = mdDoc "Wireguard public key of this peer.";
};
address = mkOption {
type = types.str;
description = mdDoc ''
Wireguard address of this peer (a single IP address, multliple
addresses or address ranges are not supported).
'';
example = "10.0.0.42";
};
endpoint = mkOption {
type = types.nullOr types.str;
description = mdDoc ''
Bootstrap endpoint for connecting to this Wireguard peer if no
other address is known or none are working.
'';
default = null;
example = "wgnode.mydomain.example:51820";
};
};
});
default = [ ];
description = mdDoc "wgautomesh peer list.";
};
};
};
default = { };
description = mdDoc "Configuration for wgautomesh.";
};
};
config = mkIf cfg.enable {
services.wgautomesh.settings = {
gossip_secret_file = mkIf cfg.enableGossipEncryption "$CREDENTIALS_DIRECTORY/gossip_secret";
persist_file = mkIf cfg.enablePersistence "/var/lib/wgautomesh/state";
};
systemd.services.wgautomesh = {
path = [ pkgs.wireguard-tools ];
environment = { RUST_LOG = "wgautomesh=${cfg.logLevel}"; };
description = "wgautomesh";
serviceConfig = {
Type = "simple";
ExecStart = "${getExe pkgs.wgautomesh} ${runtimeConfigFile}";
Restart = "always";
RestartSec = "30";
LoadCredential = mkIf cfg.enableGossipEncryption [ "gossip_secret:${cfg.gossipSecretFile}" ];
ExecStartPre = mkIf cfg.enableGossipEncryption [
''${pkgs.envsubst}/bin/envsubst \
-i ${configFile} \
-o ${runtimeConfigFile}''
];
DynamicUser = true;
StateDirectory = "wgautomesh";
StateDirectoryMode = "0700";
RuntimeDirectory = "wgautomesh";
AmbientCapabilities = "CAP_NET_ADMIN";
CapabilityBoundingSet = "CAP_NET_ADMIN";
};
wantedBy = [ "multi-user.target" ];
};
networking.firewall.allowedUDPPorts =
mkIf cfg.openFirewall [ cfg.settings.gossip_port ];
};
}

View file

@ -0,0 +1,25 @@
{ lib
, fetchFromGitea
, rustPlatform
}:
rustPlatform.buildRustPackage rec {
pname = "wgautomesh";
version = "0.1.0";
src = fetchFromGitea {
domain = "git.deuxfleurs.fr";
owner = "Deuxfleurs";
repo = "wgautomesh";
rev = "v${version}";
sha256 = "FiFEpYLSJg52EtBXaZ685ICbaIyY9URrDt0bS0HPi0Q=";
};
cargoHash = "sha256-DGDVjQ4fr4/F1RE0qVc5CWcXrrCEswCF7rQQwlKzMPA=";
meta = with lib; {
description = "A simple utility to help connect wireguard nodes together in a full mesh topology";
homepage = "https://git.deuxfleurs.fr/Deuxfleurs/wgautomesh";
license = licenses.agpl3Only;
maintainers = [ maintainers.lx ];
};
}

View file

@ -13465,6 +13465,8 @@ with pkgs;
inherit (darwin.apple_sdk.frameworks) Security; inherit (darwin.apple_sdk.frameworks) Security;
}; };
wgautomesh = callPackage ../tools/networking/wgautomesh { };
woff2 = callPackage ../development/web/woff2 { }; woff2 = callPackage ../development/web/woff2 { };
woodpecker-agent = callPackage ../development/tools/continuous-integration/woodpecker/agent.nix { }; woodpecker-agent = callPackage ../development/tools/continuous-integration/woodpecker/agent.nix { };