diff --git a/docs/mkdocs.yml b/docs/mkdocs.yml index c1e6b1a79..27fb6bbb6 100644 --- a/docs/mkdocs.yml +++ b/docs/mkdocs.yml @@ -51,6 +51,7 @@ nav: - Creating Your First Clan: guides/getting-started/index.md - Create USB Installer (optional): guides/getting-started/installer.md - Add Machines: guides/getting-started/add-machines.md + - Add Services: guides/getting-started/add-services.md - Secrets & Facts: guides/getting-started/secrets.md - Deploy Machine: guides/getting-started/deploy.md - Continuous Integration: guides/getting-started/check.md diff --git a/docs/site/guides/clanServices.md b/docs/site/guides/clanServices.md index a1ed6f82b..465098122 100644 --- a/docs/site/guides/clanServices.md +++ b/docs/site/guides/clanServices.md @@ -1,6 +1,6 @@ # Using `clanServices` -Clan’s `clanServices` system is a composable way to define and deploy services across machines. It replaces the legacy `clanModules` approach and introduces better structure, flexibility, and reuse. +Clan’s `clanServices` system is a composable way to define and deploy services across machines. This guide shows how to **instantiate** a `clanService`, explains how service definitions are structured in your inventory, and how to pick or create services from modules exposed by flakes. @@ -10,30 +10,40 @@ The term **Multi-host-modules** was introduced previously in the [nixus reposito ## Overview -A `clanService` is used in: +Services are used in `inventory.instances`, and then they attach to *roles* and *machines* — meaning you decide which machines run which part of the service. + +For example: ```nix -inventory.instances. +inventory.instances = { + borgbackup = { + roles.client.machines = [ "laptop" "server1" ]; + roles.server.machines = [ "backup-box" ]; + }; +} ``` -Each instance includes a reference to a **module specification** — this is how Clan knows which service module to use and where it came from. -You can reference services from any flake input, allowing you to compose services from multiple flake sources. +This says: “Run borgbackup as a *client* on my *laptop* and *server1*, and as a *server* on *backup-box*.” -These operate on a strict *role-based membership model*, meaning machines are added by assigning them specific *roles*. +## Module source specification + +Each instance includes a reference to a **module specification** — this is how Clan knows which service module to use and where it came from. +Usually one would just use `imports` but we needd to make the `module source` configurable via Python API. +By default it is not required to specify the `module`, in which case it defaults to the preprovided services of clan-core. --- -## Basic Example +## Override Example Example of instantiating a `borgbackup` service using `clan-core`: ```nix inventory.instances = { - # Instance Name: Arbitrary unique name for this 'borgbackup' instance + # Instance Name: Different name for this 'borgbackup' instance borgbackup-example = { module = { - name = "borgbackup"; # <-- Name of the module - input = "clan-core"; # <-- The flake input where the service is defined + name = "borgbackup"; # <-- Name of the module (optional) + input = "clan-core"; # <-- The flake input where the service is defined (optional) }; # Participation of the machines is defined via roles # Right side needs to be an attribute set. Its purpose will become clear later diff --git a/docs/site/guides/getting-started/add-machines.md b/docs/site/guides/getting-started/add-machines.md index 7f9f7671a..4f8bb3614 100644 --- a/docs/site/guides/getting-started/add-machines.md +++ b/docs/site/guides/getting-started/add-machines.md @@ -10,15 +10,6 @@ See the complete [list](../../guides/more-machines.md#automatic-registration) of ## Create a machine -=== "CLI (imperative)" - - ```sh - clan machines create jon - ``` - - The imperative command might create a machine folder in `machines/jon` - And might persist information in `inventory.json` - === "flake.nix (flake-parts)" ```{.nix hl_lines=12-15} @@ -80,37 +71,54 @@ See the complete [list](../../guides/more-machines.md#automatic-registration) of } ``` +=== "CLI (imperative)" + + ```sh + clan machines create jon + ``` + + The imperative command might create a machine folder in `machines/jon` + And might persist information in `inventory.json` + + ### Configuring a machine -Inside of the `flake.nix` file: +!!! Note + The option: `inventory.machines.` is used to define metadata about the machine + That includes for example `deploy.targethost` `machineClass` or `tags` -```nix title="flake.nix" -clan { + The option: `machines.` is used to add extra *nixosConfiguration* to a machine + +```{.nix .annotate title="flake.nix" hl_lines="3-13 18-22"} +clan = { inventory.machines = { jon = { # Define targetHost here # Required before deployment - deploy.targetHost = "root@ip"; + deploy.targetHost = "root@jon"; # (1) # Define tags here - tags = [ "desktop" "backup" ]; + tags = [ ]; + }; + sara = { + deploy.targetHost = "root@sara"; + tags = [ ]; }; }; -} -``` - - -```nix title="flake.nix" -clan { # Define additional nixosConfiguration here # Or in /machines/jon/configuration.nix (autoloaded) machines = { jon = { config, pkgs, ... }: { - environment.systemPackages = with pkgs; [ firefox ]; + users.users.root.openssh.authorizedKeys.keys = [ + "ssh-ed25519 AAAAC3NzaC..." # elided (2) + ]; }; }; } ``` +1. It is required to define a *targetHost* for each machine before deploying. Best practice has been, to use the zerotier ip/hostname or the ip from the from overlay network you decided to use. +2. Add your *ssh key* here - That will ensure you can always login to your machine via *ssh* in case something goes wrong. + ### (Optional): Renaming Machine For renaming jon to your own machine name, you can use the following command: diff --git a/docs/site/guides/getting-started/add-services.md b/docs/site/guides/getting-started/add-services.md new file mode 100644 index 000000000..6a0b08cc6 --- /dev/null +++ b/docs/site/guides/getting-started/add-services.md @@ -0,0 +1,118 @@ +# How to add services + +A service in clan is a self-contained, reusable unit of system configuration that provides a specific piece of functionality across one or more machines. + +Think of it as a recipe for running a tool — like automatic backups, VPN networking, monitoring, etc. + +In Clan Services are multi-Host & role-based: + +- Roles map machines to logical service responsibilities, enabling structured, clean deployments. + +- You can use tags instead of explicit machine names. + +To learn more: [Guide about clanService](../clanServices.md) + +!!! Important + It is recommended to add at least one networking service such as `zerotier` that allows to reach all your clan machines from your setup computer across the globe. + +## Configure a Zerotier Network (recommended) + +```{.nix title="flake.nix" hl_lines="20-28"} +{ + inputs.clan-core.url = "https://git.clan.lol/clan/clan-core/archive/main.tar.gz"; + inputs.nixpkgs.follows = "clan-core/nixpkgs"; + inputs.flake-parts.follows = "clan-core/flake-parts"; + inputs.flake-parts.inputs.nixpkgs-lib.follows = "clan-core/nixpkgs"; + + outputs = + inputs@{ flake-parts, ... }: + flake-parts.lib.mkFlake { inherit inputs; } { + imports = [ inputs.clan-core.flakeModules.default ]; + clan = { + inventory.machines = { + jon = { + targetHost = "root@jon"; + }; + sara = { + targetHost = "root@jon"; + }; + }; + inventory.instances = { + zerotier = { # (1) + # Defines 'jon' as the controller + roles.controller.machines.jon = {}; + # Defines all machines as networking peer. + # The 'all' tag is a clan builtin. + roles.peer.tags.all = {}; + }; + } + }; + + systems = [ + "x86_64-linux" + "aarch64-linux" + "x86_64-darwin" + "aarch64-darwin" + ]; + }; +} +``` + +1. See [reference/clanServices](../../reference/clanServices/index.md) for all available services and how to configure them. + Or read [authoring/clanServices](../authoring/clanServices/index.md) if you want to bring your own + +## Adding more recommended defaults + +Adding the following services is recommended for most users: + +```{.nix title="flake.nix" hl_lines="25-35"} +{ + inputs.clan-core.url = "https://git.clan.lol/clan/clan-core/archive/main.tar.gz"; + inputs.nixpkgs.follows = "clan-core/nixpkgs"; + inputs.flake-parts.follows = "clan-core/flake-parts"; + inputs.flake-parts.inputs.nixpkgs-lib.follows = "clan-core/nixpkgs"; + + outputs = + inputs@{ flake-parts, ... }: + flake-parts.lib.mkFlake { inherit inputs; } { + imports = [ inputs.clan-core.flakeModules.default ]; + clan = { + inventory.machines = { + jon = { + targetHost = "root@jon"; + }; + sara = { + targetHost = "root@jon"; + }; + }; + inventory.instances = { + zerotier = { + roles.controller.machines.jon = {}; + roles.peer.tags.all = {}; + }; + admin = { # (1) + roles.default.tags.all = { }; + roles.default.settings = { + allowedKeys = { + "my-user" = "ssh-ed25519 AAAAC3N..."; # elided + }; + }; + }; + state-version = { # (2) + roles.default.tags.all = { }; + }; + }; + }; + systems = [ + "x86_64-linux" + "aarch64-linux" + "x86_64-darwin" + "aarch64-darwin" + ]; + }; +} +``` + +1. The `admin` service will generate a **root-password** and **add your ssh-key** that allows for convienient administration. + +2. The `state-version` service will generate a [nixos state version](https://wiki.nixos.org/wiki/FAQ/When_do_I_update_stateVersion) for each system once it is deployed. \ No newline at end of file diff --git a/docs/site/guides/getting-started/deploy.md b/docs/site/guides/getting-started/deploy.md index 242a80bc1..5101044b1 100644 --- a/docs/site/guides/getting-started/deploy.md +++ b/docs/site/guides/getting-started/deploy.md @@ -31,7 +31,7 @@ Now that you have created a new machine, we will walk through how to install it. === "flake.nix (flake-parts)" - ```nix + ```{.nix hl_lines="22"} { inputs.clan-core.url = "https://git.clan.lol/clan/clan-core/archive/main.tar.gz"; inputs.nixpkgs.follows = "clan-core/nixpkgs"; @@ -63,7 +63,7 @@ Now that you have created a new machine, we will walk through how to install it. === "flake.nix (classic)" - ```nix + ```{.nix hl_lines="14"} { inputs.clan-core.url = "https://git.clan.lol/clan/clan-core/archive/main.tar.gz"; inputs.nixpkgs.follows = "clan-core/nixpkgs"; @@ -133,31 +133,32 @@ In this example we would copy `nvme-eui.e8238fa6bf530001001b448b4aec2929` Edit the following fields inside the `./machines//configuration.nix` - - ```nix title="./machines/jon/configuration.nix" hl_lines="13 18 22 26" - { - imports = [ - # contains your disk format and partitioning configuration. - ../../modules/disko.nix - # this file is shared among all machines - ../../modules/shared.nix - # enables GNOME desktop (optional) - ../../modules/gnome.nix - ]; + - # Put your username here for login - users.users.user.name = "__YOUR_USERNAME__"; +```nix title="./machines/jon/configuration.nix" hl_lines="12 15 19" +{ + imports = [ + # contains your disk format and partitioning configuration. + ../../modules/disko.nix + # this file is shared among all machines + ../../modules/shared.nix + # enables GNOME desktop (optional) + ../../modules/gnome.nix + ]; - # Replace this __CHANGE_ME__ with the copied result of the lsblk command - disko.devices.disk.main.device = "/dev/disk/by-id/__CHANGE_ME__"; + # Put your username here for login + users.users.user.name = "__YOUR_USERNAME__"; - # IMPORTANT! Add your SSH key here - # e.g. > cat ~/.ssh/id_ed25519.pub - users.users.root.openssh.authorizedKeys.keys = [ "__YOUR_SSH_KEY__" ]; + # Replace this __CHANGE_ME__ with the copied result of the lsblk command + disko.devices.disk.main.device = "/dev/disk/by-id/__CHANGE_ME__"; - # ... - } - ``` + # IMPORTANT! Add your SSH key here + # e.g. > cat ~/.ssh/id_ed25519.pub + users.users.root.openssh.authorizedKeys.keys = [ "__YOUR_SSH_KEY__" ]; + + # ... +} +``` !!! Info "Replace `__YOUR_USERNAME__` with the ip of your machine, if you use avahi you can also use your hostname" !!! Info "Replace `__CHANGE_ME__` with the appropriate `ID-LINK` identifier, such as `nvme-eui.e8238fa6bf530001001b448b4aec2929`" diff --git a/docs/site/guides/getting-started/secrets.md b/docs/site/guides/getting-started/secrets.md index e6792f22c..5c7dbc30d 100644 --- a/docs/site/guides/getting-started/secrets.md +++ b/docs/site/guides/getting-started/secrets.md @@ -1,4 +1,8 @@ +Setting up secrets is **Required** for any *machine deployments* or *vm runs* - You need to complete the steps: [Create Admin Keypair](#create-your-admin-keypair) and [Add Your Public Key(s)](#add-your-public-keys) + +--- + Clan enables encryption of secrets (such as passwords & keys) ensuring security and ease-of-use among users. By default, Clan uses the [sops](https://github.com/getsops/sops) format