Merge pull request 'Docs: improve module author guide code examples, code structuring' (#2233) from hsjobeki/clan-core:hsjobeki-main into main
This commit is contained in:
@@ -6,13 +6,17 @@ This site will guide you through authoring your first module. Explaining which c
|
||||
Under construction
|
||||
:fontawesome-solid-road-barrier: :fontawesome-solid-road-barrier: :fontawesome-solid-road-barrier:
|
||||
|
||||
!!! Note
|
||||
Currently ClanModules should be contributed to the [clan-core repository](https://git.clan.lol/clan/clan-core) via a PR.
|
||||
|
||||
Ad-hoc loading of custom modules is not recommended / supported yet.
|
||||
|
||||
## Bootstrapping the `clanModule`
|
||||
|
||||
A ClanModule is a specific subset of a [NixOS Module](https://nix.dev/tutorials/module-system/index.html), but it has some constraints and might be used via the [Inventory](../manual/inventory.md) interface.
|
||||
In fact a `ClanModule` can be thought of as a layer of abstraction on-top of NixOS and/or other ClanModules. It may configure sane defaults and provide an ergonomic interface that is easy to use and can also be used via a UI that is under development currently.
|
||||
|
||||
Because ClanModules should be configurable via `json` all of its interface (`options`) must be serializable.
|
||||
|
||||
Currently ClanModules should be contributed to the [clan-core repository](https://git.clan.lol/clan/clan-core). Ad-hoc loading of custom modules is not recommended / supported yet.
|
||||
Because ClanModules should be configurable via `json`/`API` all of its interface (`options`) must be serializable.
|
||||
|
||||
!!! Tip
|
||||
ClanModules interface can be checked by running the json schema converter as follows.
|
||||
@@ -35,10 +39,11 @@ clanModules/borgbackup
|
||||
```
|
||||
|
||||
!!! Tip
|
||||
This format is strictly required for `features = [ "inventory" ]`.
|
||||
Some module authors might decide to opt-out of [inventory](../manual/inventory.md) usage.
|
||||
`README.md` is always required. See section [Readme](#readme) for further details.
|
||||
|
||||
The next step is to register the module via the `clanModules` attribute.
|
||||
The `roles` folder is strictly required for `features = [ "inventory" ]`.
|
||||
|
||||
The clanModule must be registered via the `clanModules` attribute in `clan-core`
|
||||
|
||||
```nix title="clanModules/flake-module.nix"
|
||||
--8<-- "clanModules/flake-module.nix:0:6"
|
||||
@@ -48,7 +53,7 @@ The next step is to register the module via the `clanModules` attribute.
|
||||
|
||||
## Readme
|
||||
|
||||
The `README.md` is a required file. It MUST contain frontmatter in [`toml`](https://toml.io) format.
|
||||
The `README.md` is a required file for all modules. It MUST contain frontmatter in [`toml`](https://toml.io) format.
|
||||
|
||||
```markdown
|
||||
---
|
||||
@@ -62,9 +67,11 @@ See the [frontmatter reference](#frontmatter-reference) for all supported attrib
|
||||
|
||||
## Roles
|
||||
|
||||
Each `.nix` file in the `roles` directory is added as a role to the service.
|
||||
If the module declares to implement `features = [ "inventory" ]` then it MUST contain a roles directory.
|
||||
|
||||
Other files can be placed alongside the `.nix` files
|
||||
Each `.nix` file in the `roles` directory is added as a role to the inventory service.
|
||||
|
||||
Other files can also be placed alongside the `.nix` files
|
||||
|
||||
```sh
|
||||
└── roles
|
||||
@@ -74,6 +81,37 @@ Other files can be placed alongside the `.nix` files
|
||||
|
||||
Adds the roles: `client` and `server`
|
||||
|
||||
??? Tip "Good to know"
|
||||
Sometimes a `ClanModule` should be usable via both clan's `inventory` concept but also natively as a NixOS module.
|
||||
|
||||
> In the long term, we want most modules to implement support for the inventory,
|
||||
> but we are also aware that there are certain low-level modules that always serve as a backend for other higher-level inventory modules.
|
||||
> These modules may not want to implement inventory interfaces as they are always used directly by other modules.
|
||||
|
||||
This can be achieved by placing an additional `default.nix` into the root of the ClanModules directory as shown:
|
||||
|
||||
```sh
|
||||
# ModuleA
|
||||
├── README.md
|
||||
├── default.nix
|
||||
└── roles
|
||||
└── default.nix
|
||||
```
|
||||
|
||||
```nix title="default.nix"
|
||||
{...}:{
|
||||
imports = [ ./roles/default.nix ];
|
||||
}
|
||||
```
|
||||
|
||||
By utilizing this pattern the module (`moduleA`) can then be imported into any regular NixOS module via:
|
||||
|
||||
```nix
|
||||
{...}:{
|
||||
imports = [ clanModules.moduleA ];
|
||||
}
|
||||
```
|
||||
|
||||
## Organizing the ClanModule
|
||||
|
||||
Each `{role}.nix` is included into the machine if the machine is declared to have the role.
|
||||
@@ -86,6 +124,32 @@ roles.client.machines = ["MachineA"];
|
||||
|
||||
Then `roles/client.nix` will be added to the machine `MachineA`.
|
||||
|
||||
This behavior makes it possible to split the interface and common code paths when using multiple roles.
|
||||
In the concrete example of `borgbackup` this allows a `server` to declare a different interface than the corresponding `client`.
|
||||
|
||||
The client offers configuration option, to exclude certain local directories from being backed up:
|
||||
|
||||
```nix title="roles/client.nix"
|
||||
# Example client interface
|
||||
options.clan.borgbackup.exclude = ...
|
||||
```
|
||||
|
||||
The server doesn't offer any configuration option. Because everything is set-up automatically.
|
||||
|
||||
```nix title="roles/server.nix"
|
||||
# Example server interface
|
||||
options.clan.borgbackup = {};
|
||||
```
|
||||
|
||||
Assuming that there is a common code path or a common interface between `server` and `client` this can be structured as:
|
||||
|
||||
```nix title="roles/server.nix, roles/client.nix"
|
||||
{...}: {
|
||||
# ...
|
||||
imports = [ ../common.nix ];
|
||||
}
|
||||
```
|
||||
|
||||
## Frontmatter Reference
|
||||
|
||||
`description` (**Required** `String`)
|
||||
@@ -125,4 +189,6 @@ Then `roles/client.nix` will be added to the machine `MachineA`.
|
||||
|
||||
!!! warning "Important"
|
||||
Every ClanModule, that specifies `features = [ "inventory" ]` MUST have at least one role.
|
||||
Many modules use `roles/default.nix` which registers the role `default`
|
||||
Many modules use `roles/default.nix` which registers the role `default`.
|
||||
|
||||
If you are a clan module author and your module has only one role where you cannot determine the name, then we would like you to follow the convention.
|
||||
Reference in New Issue
Block a user