Docs: move {flake, facts-vars} migration guides into 'migrations' folder

This commit is contained in:
Johannes Kirschbauer
2025-05-18 18:56:03 +02:00
parent 04146eeac9
commit b36d641e71
4 changed files with 7 additions and 7 deletions

View File

@@ -54,7 +54,7 @@ clan --help
### Step 2: Initialize Your Project
If you want to migrate an existing project, follow this [guide](../../manual/migration-guide.md).
If you want to migrate an existing project, follow this [guide](../migrations/migration-guide.md).
Set the foundation of your Clan project by initializing it as follows:

View File

@@ -0,0 +1,127 @@
# Migrate modules from `facts` to `vars`.
For a high level overview about `vars` see our [blog post](https://clan.lol/blog/vars/).
This guide will help you migrate your modules that still use our [`facts`](../../manual/secrets.md) backend
to the [`vars`](../../manual/vars-backend.md) backend.
The `vars` [module](../../reference/clan-core/vars.md) and the clan [command](../../reference/cli/vars.md) work in tandem, they should ideally be kept in sync.
## Keep Existing Values
In order to keep existing values and move them from `facts` to `vars`
we will need to set the corresponding option in the vars module:
```
migrateFact = "fact-name"
```
This will now check on `vars` generation if there is an existing `fact` with the
name already present and if that is the case will migrate it to `vars`.
Let us look at the mapping a little closer.
Suppose we have the following fact: `facts.services.vaultwarden.secret.admin`.
This would read as follows: The `vaultwarden` `fact` service has the `admin` secret.
In order to migrate this fact we would need to have the following `vars` configuration:
```nix
vars.generators.vaultwarden = {
migrateFact = "vaultwarden";
files.admin = {};
};
```
And this would read as follows: The vaultwarden `vars` module generates the admin file.
## Prompts
Because prompts can be a necessity for certain systems `vars` have a shorthand for defining them.
A prompt is a request for user input. Let us look how user input used to be handled in facts:
```nix
facts.services.forgejo-api = {
secret.token = {};
generator.prompt = "Please insert your forgejo api token";
generator.script = "cp $prompt_value > $secret/token";
};
```
To have analogous functionality in `vars`:
```nix
vars.generators.forgejo-api = {
prompts.token = {
description = "Please insert your forgejo api token"
persist = true;
};
};
```
This does not only simplify prompting, it also now allows us to define multiple prompts in one generator.
A more analogous way to the `fact` method is available, in case the module author needs more flexibility with the prompt input:
```nix
vars.generators.forgejo-api = {
files.token = {};
prompts.token.description = "Please insert your forgejo api token";
script = "cp $prompts/<name> $out/<name>";
};
```
## Migration of a complete module
Let us look closer at how we would migrate an existing generator for syncthing.
This is the `fact` module of syncthing:
```nix
facts.services.syncthing = {
secret.key = {};
secret.cert = {};
public.id = {};
generator.path = [
pkgs.coreutils
pkgs.gnugrep
pkgs.syncthing
];
generator.script = ''
syncthing generate --config "$out"
mv "$out"/key.pem "$secret"/key
mv "$out"/cert.pem "$secret"/cert
cat "$out"/config.xml | grep -oP '(?<=<device id=")[^"]+' | uniq > "$public"/id
'';
};
```
This would be the corresponding `vars` module, which also will migrate existing facts.
```nix
vars.generators.syncthing = {
migrateFact = "syncthing";
files.key = {};
files.cert = {};
files.id.secret = false;
runtimeInputs = [
pkgs.coreutils
pkgs.gnugrep
pkgs.syncthing
];
script = ''
syncthing generate --config "$out"
mv "$out"/key.pem "$out"/key
mv "$out"/cert.pem "$out"/cert
cat "$out"/config.xml | grep -oP '(?<=<device id=")[^"]+' | uniq > "$out"/id
'';
};
```
Most of the usage patterns stay the same, but `vars` have a more ergonomic interface.
There are not two different ways to define files anymore (public/secret).
Now files are defined under the `files` attribute and are secret by default.
## Happy Migration
We hope this gives you a clear path to start and finish your migration from `facts` to `vars`.
Please do not hesitate reaching out if something is still unclear - either through [matrix](https://matrix.to/#/#clan:clan.lol) or through our git [forge](https://git.clan.lol/clan/clan-core).

View File

@@ -0,0 +1,181 @@
# Migrate existing NixOS configurations
This guide will help you migrate your existing Nix configurations into Clan.
!!! Warning
Migrating instead of starting new can be trickier and might lead to bugs or
unexpected issues. We recommend following the [Getting Started](../getting-started/index.md) guide first. Once you have a working setup, you can easily transfer your Nix configurations over.
## Back up your existing configuration!
Before you start, it is strongly recommended to back up your existing
configuration in any form you see fit. If you use version control to manage
your configuration changes, it is also a good idea to follow the migration
guide in a separte branch until everything works as expected.
## Starting Point
We assume you are already using NixOS flakes to manage your configuration. If
not, migrate to a flake-based setup following the official [NixOS
documentation](https://nix.dev/manual/nix/2.25/command-ref/new-cli/nix3-flake.html).
The snippet below shows a common Nix flake. For this example we will assume you
have have two hosts: **berlin** and **cologne**.
```nix
{
inputs.nixpkgs.url = "github:nixos/nixpkgs/nixos-unstable";
outputs = { self, nixpkgs, ... }: {
nixosConfigurations = {
berlin = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [./machines/berlin/configuration.nix];
};
cologne = nixpkgs.lib.nixosSystem {
system = "x86_64-linux";
modules = [./machines/cologne/configuration.nix];
};
};
};
}
```
## Add clan-core Input
Add `clan-core` to your flake as input. It will provide everything we need to
manage your configurations with clan.
```nix
inputs.clan-core = {
url = "git+https://git.clan.lol/clan/clan-core";
# Don't do this if your machines are on nixpkgs stable.
inputs.nixpkgs.follows = "nixpkgs";
};
```
## Update Outputs
To be able to access our newly added dependency, it has to be added to the
output parameters.
```diff
- outputs = { self, nixpkgs, ... }:
+ outputs = { self, nixpkgs, clan-core }:
```
The existing `nixosConfigurations` output of your flake will be created by
clan. In addition, a new `clanInternals` output will be added. Since both of
these are provided by the output of `lib.buildClan`, a common syntax is to use a
`let...in` statement to create your clan and access it's parameters in the flake
outputs.
For the provide flake example, your flake should now look like this:
```nix
{
inputs.nixpkgs.url = "github:nixos/nixpkgs/nixos-unstable";
inputs.clan-core = {
url = "git+https://git.clan.lol/clan/clan-core";
inputs.nixpkgs.follows = "nixpkgs";
};
outputs = { self, nixpkgs, clan-core, ... }:
let
clan = clan-core.lib.buildClan {
self = self; # this needs to point at the repository root
specialArgs = {};
meta.name = throw "Change me to something unique";
machines = {
berlin = {
nixpkgs.hostPlatform = "x86_64-linux";
imports = [ ./machines/berlin/configuration.nix ];
};
cologne = {
nixpkgs.hostPlatform = "x86_64-linux";
imports = [ ./machines/cologne/configuration.nix ];
};
};
};
in
{
nixosConfigurations = clan.nixosConfigurations;
inherit (clan) clanInternals;
clan = {
inherit (clan) templates;
};
};
}
```
Et voilà! Your existing hosts are now part of a clan. Existing Nix tooling
should still work as normal. To check that you didn't make any errors, run `nix
flake show` and verify both hosts are still recognized as if nothing had
changed. You should also see the new `clanInternals` output.
```
nix flake show
git+file:///my-nixos-config
├───clanInternals: unknown
└───nixosConfigurations
├───berlin: NixOS configuration
└───cologne: NixOS configuration
```
Of course you can also rebuild your configuration using `nixos-rebuild` and
veryify everything still works.
## Add Clan CLI devShell
At this point Clan is set up, but you can't use the CLI yet. To do so, it is
recommended to expose it via a `devShell` in your flake. It is also possible to
install it any other way you would install a package in Nix, but using a
developtment shell ensures the CLI's version will always be in sync with your
configuration.
A minimal example is provided below, add it to your flake outputs.
```nix
devShells."x86_64-linux".default = nixpkgs.legacyPackages."x86_64-linux".mkShell {
packages = [ clan-core.packages."x86_64-linux".clan-cli ];
};
```
To use the CLI, execute `nix develop` in the directory of your flake. The
resulting shell, provides you with the `clan` CLI tool. Since you will be using
it every time you interact with Clan, it is recommended to set up
[direnv](https://direnv.net/).
Verify everything works as expected by running `clan machines list`.
```
nix develop
[user@host:~/my-nixos-config]$ clan machines list
berlin
cologne
```
## Specify Targets
Clan needs to know where it can reach your hosts. For each of your hosts, set
`clan.core.networking.targetHost` to its adress or hostname.
```nix
# machines/berlin/configuration.nix
{
clan.core.networking.targetHost = "123.4.56.78";
}
```
## Next Steps
You are now fully set up. Use the CLI to manage your hosts or proceed to
configure further services. At this point you should be able to run commands
like `clan machines update berlin` to deploy a host.